diff --git a/.codeclimate.yml b/.codeclimate.yml index 4343c26245..f46194a7d8 100644 --- a/.codeclimate.yml +++ b/.codeclimate.yml @@ -34,11 +34,12 @@ plugins: duplication: enabled: true config: - count_threshold: 3 + count_threshold: 4 exclude_patterns: - - "**/test/*" - - "**/adapter-tests/*" - - "**/dist/*" - - "**/*.dist.js" + - "**/test/*" + - "**/adapter-tests/*" + - "**/dist/*" + - "**/*.dist.js" - "**/templates/*" - - "**/_**" \ No newline at end of file + - "**/_**" + - "**/adapter-commons/src/sort.ts" diff --git a/.eslintignore b/.eslintignore new file mode 100644 index 0000000000..c5848d653b --- /dev/null +++ b/.eslintignore @@ -0,0 +1,2 @@ +main/ +deno/ \ No newline at end of file diff --git a/.eslintrc.js b/.eslintrc.js index 127eaca585..4e79b48f8e 100644 --- a/.eslintrc.js +++ b/.eslintrc.js @@ -1,16 +1,3 @@ -/* -👋 Hi! This file was autogenerated by tslint-to-eslint-config. -https://github.com/typescript-eslint/tslint-to-eslint-config - -It represents the closest reasonable ESLint configuration to this -project's original TSLint configuration. - -We recommend eventually switching this configuration to extend from -the recommended rulesets in typescript-eslint. -https://github.com/typescript-eslint/tslint-to-eslint-config/blob/master/docs/FAQs.md - -Happy linting! 💖 -*/ module.exports = { "env": { "browser": true, @@ -19,8 +6,7 @@ module.exports = { "node": true }, "extends": [ - "plugin:@typescript-eslint/recommended", - "plugin:@typescript-eslint/recommended-requiring-type-checking" + "plugin:@typescript-eslint/recommended" ], "parser": "@typescript-eslint/parser", "parserOptions": { @@ -28,135 +14,21 @@ module.exports = { "sourceType": "module" }, "plugins": [ - "eslint-plugin-import", - "eslint-plugin-prefer-arrow", - "@typescript-eslint" + "@typescript-eslint", + "prettier" ], + "ignorePatterns": ["**/lib/", "**/dist/"], "rules": { - "prefer-rest-params": "off", - "prefer-spread": "off", - "@typescript-eslint/no-unsafe-member-access": "off", - "@typescript-eslint/no-unsafe-assignment": "off", - "@typescript-eslint/no-unsafe-argument": "off", - "@typescript-eslint/no-unsafe-member-access": "off", - "@typescript-eslint/no-unsafe-call": "off", - "@typescript-eslint/no-unsafe-return": "off", - "@typescript-eslint/no-floating-promises": "off", - "@typescript-eslint/restrict-template-expressions": "off", - "@typescript-eslint/explicit-module-boundary-types": "off", - "@typescript-eslint/require-await": "off", - "@typescript-eslint/ban-ts-comment": "off", - "@typescript-eslint/unbound-method": "off", - "@typescript-eslint/no-this-alias": "off", - "@typescript-eslint/prefer-regexp-exec": "off", - "@typescript-eslint/no-misused-promises": "off", - "@typescript-eslint/restrict-plus-operands": "off", - // ---- - "@typescript-eslint/adjacent-overload-signatures": "error", - "@typescript-eslint/array-type": [ - "error", - { - "default": "array" - } - ], - "@typescript-eslint/ban-types": "off", - "@typescript-eslint/consistent-type-assertions": "error", - "@typescript-eslint/dot-notation": "error", - "@typescript-eslint/explicit-member-accessibility": [ - "error", - { - "accessibility": "no-public" - } - ], - "@typescript-eslint/naming-convention": "off", - "@typescript-eslint/no-empty-function": "off", - "@typescript-eslint/no-empty-interface": "error", + "prettier/prettier": "error", "@typescript-eslint/no-explicit-any": "off", - "@typescript-eslint/no-misused-new": "error", - "@typescript-eslint/no-namespace": "error", - "@typescript-eslint/no-parameter-properties": "off", - "@typescript-eslint/no-unused-expressions": "error", - "@typescript-eslint/no-use-before-define": "off", - "@typescript-eslint/no-var-requires": "error", - "@typescript-eslint/prefer-for-of": "error", - "@typescript-eslint/prefer-function-type": "error", - "@typescript-eslint/prefer-namespace-keyword": "error", - "@typescript-eslint/quotes": [ - "error", - "single" - ], - "@typescript-eslint/triple-slash-reference": [ - "error", - { - "path": "always", - "types": "prefer-import", - "lib": "always" - } - ], - "@typescript-eslint/unified-signatures": "error", - "arrow-parens": [ - "off", - "always" - ], - "comma-dangle": "error", - "complexity": "off", - "constructor-super": "error", - "eqeqeq": [ - "error", - "smart" - ], - "guard-for-in": "error", - "id-blacklist": "off", - "id-match": "off", - "import/order": "off", - // "jsdoc/check-alignment": "error", - // "jsdoc/check-indentation": "error", - // "jsdoc/newline-after-description": "error", - "max-classes-per-file": "off", - "max-len": "off", - "new-parens": "error", - "no-bitwise": "error", - "no-caller": "error", - "no-cond-assign": "error", - "no-console": "error", - "no-debugger": "error", - "no-empty": "off", - "no-eval": "error", - "no-fallthrough": "off", - "no-invalid-this": "off", - "no-new-wrappers": "error", - "no-shadow": [ - "off", - { - "hoist": "all" - } - ], - "no-throw-literal": "error", - "no-trailing-spaces": "error", - "no-undef-init": "error", - "no-underscore-dangle": "off", - "no-unsafe-finally": "error", - "no-unused-labels": "error", - "no-var": "error", - "object-shorthand": "error", - "one-var": [ - "error", - "never" - ], - "prefer-arrow/prefer-arrow-functions": "off", - "prefer-const": "error", - "radix": "error", - "space-before-function-paren": "error", - "spaced-comment": [ - "error", - "always", - { - "markers": [ - "/" - ] + "@typescript-eslint/no-unused-vars": [ + "warn", // or "error" + { + "argsIgnorePattern": "^_", + "varsIgnorePattern": "^_", + "caughtErrorsIgnorePattern": "^_", + "ignoreRestSiblings": true } - ], - "use-isnan": "error", - "valid-typeof": "off" + ] } }; diff --git a/.github/contributing.md b/.github/contributing.md index 98df2ff804..57c8c8a011 100644 --- a/.github/contributing.md +++ b/.github/contributing.md @@ -8,7 +8,7 @@ Feathers embraces modularity and is broken up across multiple modules. You can f Before creating an issue please make sure you have checked out the docs, specifically the [FAQ](https://docs.feathersjs.com/help/faq.html) section. You might want to also try searching Github. It's pretty likely someone has already asked a similar question. -If you haven't found your answer please feel free to join our [slack channel](http://slack.feathersjs.com), create an issue on Github, or post on [Stackoverflow](http://stackoverflow.com) using the `feathersjs` tag. We try our best to monitor Stackoverflow but you're likely to get more immediate responses in Slack and Github. +If you haven't found your answer please feel free to join our [Discord server](https://discord.gg/qa8kez8QBx), create an issue on Github, or post on [Stackoverflow](http://stackoverflow.com) using the `feathersjs` tag. We try our best to monitor Stackoverflow but you're likely to get more immediate responses in Slack and Github. Issues can be reported in the [issue tracker](https://github.com/feathersjs/feathers/issues). Since feathers combines many modules it can be hard for us to assess the root cause without knowing which modules are being used and what your configuration looks like, so **it helps us immensely if you can link to a simple example that reproduces your issue**. @@ -16,7 +16,7 @@ Issues can be reported in the [issue tracker](https://github.com/feathersjs/feat We take security very seriously at Feathers. We welcome any peer review of our 100% open source code to ensure nobody's Feathers app is ever compromised or hacked. As a web application developer you are responsible for any security breaches. We do our very best to make sure Feathers is as secure as possible by default. -In order to give the community time to respond and upgrade we strongly urge you report all security issues to us. Send one of the core team members a PM in [Slack](http://slack.feathersjs.com) or email us at hello@feathersjs.com with details and we will respond ASAP. +In order to give the community time to respond and upgrade we strongly urge you report all security issues to us. Send one of the core team members a PM in [Discord](https://discord.gg/qa8kez8QBx) or email us at hello@feathersjs.com with details and we will respond ASAP. For full details refer to our [Security docs](https://docs.feathersjs.com/SECURITY.html). @@ -48,7 +48,7 @@ If you've written something awesome about Feathers, for the Feathers ecosystem, If you are looking to create a new plugin you also might want to check out the [Plugin Generator](https://github.com/feathersjs/generator-feathers-plugin) that can be used to scaffold plugins to be Feathers compliant from the start. -If you think your module would be a good core `feathersjs` module or `featherjs-ecosystem` module then please contact one of the Feathers maintainers in [Slack](http://slack.feathersjs.com) and we can discuss whether it belongs and how to get it there. :beers: +If you think your module would be a good core `feathersjs` module or `featherjs-ecosystem` module then please contact one of the Feathers maintainers on [Discord](https://discord.gg/qa8kez8QBx) and we can discuss whether it belongs and how to get it there. :beers: ## Contributor Code of Conduct diff --git a/.github/workflows/nodejs.yml b/.github/workflows/nodejs.yml index 1b770b7089..05d30a1eda 100644 --- a/.github/workflows/nodejs.yml +++ b/.github/workflows/nodejs.yml @@ -4,27 +4,44 @@ on: [push, pull_request] jobs: build: - runs-on: ubuntu-latest strategy: matrix: - node-version: [12.x, 14.x] + node-version: [14.x, 18.x] + + services: + postgres: + image: postgres:latest + env: + POSTGRES_DB: feathers + POSTGRES_PASSWORD: postgres + POSTGRES_PORT: 5432 + POSTGRES_USER: postgres + ports: + - 5432:5432 + options: >- + --health-cmd pg_isready + --health-interval 10s + --health-timeout 5s + --health-retries 5 steps: - - uses: actions/checkout@v2 - - name: Use Node.js ${{ matrix.node-version }} - uses: actions/setup-node@v1 - with: - node-version: ${{ matrix.node-version }} - - run: npm install -g codeclimate-test-reporter - - run: npm install - - run: npm test - env: - CI: true - - run: | - if [ "$CODECLIMATE_REPO_TOKEN" != "" ]; then - codeclimate-test-reporter < coverage/lcov.info - fi - env: - CODECLIMATE_REPO_TOKEN: ${{ secrets.codeclimate }} + - uses: actions/checkout@v2 + - name: Use Node.js ${{ matrix.node-version }} + uses: actions/setup-node@v1 + with: + node-version: ${{ matrix.node-version }} + - run: npm i npm -g + - run: npm install -g codeclimate-test-reporter + - run: npm install + - run: npm test + env: + CI: true + TEST_DB: postgres + - run: | + if [ "$CODECLIMATE_REPO_TOKEN" != "" ]; then + codeclimate-test-reporter < coverage/lcov.info + fi + env: + CODECLIMATE_REPO_TOKEN: ${{ secrets.codeclimate }} diff --git a/.github/workflows/update-dependencies.yml b/.github/workflows/update-dependencies.yml index fe24ee5a72..12adf89b11 100644 --- a/.github/workflows/update-dependencies.yml +++ b/.github/workflows/update-dependencies.yml @@ -1,6 +1,6 @@ name: Update dependencies -on: +on: schedule: - cron: '0 0 1 * *' workflow_dispatch: @@ -8,24 +8,23 @@ jobs: update-dependencies: runs-on: ubuntu-latest steps: - - uses: actions/checkout@v2 - - name: Use Node.js - uses: actions/setup-node@v1 - with: - node-version: '15.x' - - run: npm ci - - run: | - git config user.name "GitHub Actions Bot" - git config user.email "hello@feathersjs.com" - git checkout -b update-dependencies-$GITHUB_RUN_ID - - run: | - npm run update-dependencies - npm install - - run: | - git commit -am "chore(dependencies): Update dependencies" - git push origin update-dependencies-$GITHUB_RUN_ID - - run: | - gh pr create --title "chore(dependencies): Update all dependencies" --body "" - env: - GITHUB_TOKEN: ${{secrets.CI_ACCESS_TOKEN}} - \ No newline at end of file + - uses: actions/checkout@v2 + - name: Use Node.js + uses: actions/setup-node@v1 + with: + node-version: '18.x' + - run: npm ci + - run: | + git config user.name "GitHub Actions Bot" + git config user.email "hello@feathersjs.com" + git checkout -b update-dependencies-$GITHUB_RUN_ID + - run: | + npm run update-dependencies + npm install + - run: | + git commit -am "chore(dependencies): Update dependencies" + git push origin update-dependencies-$GITHUB_RUN_ID + - run: | + gh pr create --title "chore(dependencies): Update all dependencies" --body "" + env: + GITHUB_TOKEN: ${{secrets.CI_ACCESS_TOKEN}} diff --git a/.gitignore b/.gitignore index 04761aa03e..691dd762f6 100644 --- a/.gitignore +++ b/.gitignore @@ -41,3 +41,5 @@ dist/ # TypeScript compiled files packages/**/lib +packages/cli/test/build/*.tgz +*.sqlite diff --git a/.prettierrc b/.prettierrc new file mode 100644 index 0000000000..6907cbaf10 --- /dev/null +++ b/.prettierrc @@ -0,0 +1,8 @@ +{ + "tabWidth": 2, + "useTabs": false, + "printWidth": 110, + "semi": false, + "trailingComma": "none", + "singleQuote": true +} \ No newline at end of file diff --git a/.vscode/settings.json b/.vscode/settings.json index 1535e139ea..9eef5abd66 100644 --- a/.vscode/settings.json +++ b/.vscode/settings.json @@ -1,5 +1,9 @@ { "deno.enable": true, "deno.lint": true, - "deno.unstable": true + "deno.unstable": true, + "deno.enablePaths": [ + "./main", + "./deno" + ] } \ No newline at end of file diff --git a/CHANGELOG.md b/CHANGELOG.md index abea3b3d44..32348eb03e 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -3,949 +3,850 @@ All notable changes to this project will be documented in this file. See [Conventional Commits](https://conventionalcommits.org) for commit guidelines. -# [5.0.0-pre.16](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.15...v5.0.0-pre.16) (2022-01-12) - +# [5.0.0-pre.31](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.30...v5.0.0-pre.31) (2022-10-12) ### Bug Fixes -* **authentication-oauth:** OAuth redirect lost sometimes due to session store race ([#2514](https://github.com/feathersjs/feathers/issues/2514)) ([#2515](https://github.com/feathersjs/feathers/issues/2515)) ([6109c44](https://github.com/feathersjs/feathers/commit/6109c44428c6b8f6bb4e089be760ea1a4ef3d01e)) -* **schema:** Do not error for schemas without properties ([#2519](https://github.com/feathersjs/feathers/issues/2519)) ([96fdb47](https://github.com/feathersjs/feathers/commit/96fdb47d45fd88a8039aa9cc9ec8aebd98672b95)) -* **schema:** Fix resolver data type and use new validation feature in test fixture ([#2523](https://github.com/feathersjs/feathers/issues/2523)) ([1093f12](https://github.com/feathersjs/feathers/commit/1093f124b60524cbd9050fcf07ddaf1d558973da)) - +- **errors:** Allows to pass no error message ([#2794](https://github.com/feathersjs/feathers/issues/2794)) ([f3ddab6](https://github.com/feathersjs/feathers/commit/f3ddab637e269e67e852ffce07b060bab2b085c0)) +- **koa:** Only set error code for Feathers errors ([#2793](https://github.com/feathersjs/feathers/issues/2793)) ([d3ee41e](https://github.com/feathersjs/feathers/commit/d3ee41e27b0ea5d29b344d6584ab03e48d16e2b4)) ### Features -* **express, koa:** make transports similar ([#2486](https://github.com/feathersjs/feathers/issues/2486)) ([26aa937](https://github.com/feathersjs/feathers/commit/26aa937c114fb8596dfefc599b1f53cead69c159)) -* **schema:** Allow to use custom AJV and test with ajv-formats ([#2513](https://github.com/feathersjs/feathers/issues/2513)) ([ecfa4df](https://github.com/feathersjs/feathers/commit/ecfa4df29f029f6ca8517cacf518c14b46ffeb4e)) -* **schema:** Improve schema typing, validation and extensibility ([#2521](https://github.com/feathersjs/feathers/issues/2521)) ([8c1b350](https://github.com/feathersjs/feathers/commit/8c1b35052792e82d13be03c06583534284fbae82)) - -# [5.0.0-pre.15](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.14...v5.0.0-pre.15) (2021-11-27) +- **cli:** Generate full client test suite and improve typed client ([#2788](https://github.com/feathersjs/feathers/issues/2788)) ([57119b6](https://github.com/feathersjs/feathers/commit/57119b6bb2797f7297cf054268a248c093ecd538)) +- **cli:** Improve generated schema definitions ([#2783](https://github.com/feathersjs/feathers/issues/2783)) ([474a9fd](https://github.com/feathersjs/feathers/commit/474a9fda2107e9bcf357746320a8e00cda8182b6)) +# [5.0.0-pre.30](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.29...v5.0.0-pre.30) (2022-10-07) ### Bug Fixes -* **adapter-commons:** clean up in sort.ts and select function ([#2492](https://github.com/feathersjs/feathers/issues/2492)) ([c3ec8a4](https://github.com/feathersjs/feathers/commit/c3ec8a418bdc85506e3c5100015720a45454d8d3)) -* **adapter-commons:** Fix sorting for embedded objects ([#2488](https://github.com/feathersjs/feathers/issues/2488)) ([9c22f70](https://github.com/feathersjs/feathers/commit/9c22f70a838cb6341775d91705a7527c8fc5590e)) -* missing express types for Request, Response ([#2498](https://github.com/feathersjs/feathers/issues/2498)) ([ee67131](https://github.com/feathersjs/feathers/commit/ee67131bbaa24c54d3d781bdf8820015759ac488)) -* **typescript:** Overall typing improvements ([#2478](https://github.com/feathersjs/feathers/issues/2478)) ([b8eb804](https://github.com/feathersjs/feathers/commit/b8eb804158556d9651a8607e3c3fda15e0bfd110)) - +- **authentication-oauth:** Fix regression with prefix handling in OAuth ([#2773](https://github.com/feathersjs/feathers/issues/2773)) ([b1844b1](https://github.com/feathersjs/feathers/commit/b1844b1f27feeb7e66920ec9e318872857711834)) +- **core:** Ensure setup and teardown can be overriden and maintain hook functionality ([#2779](https://github.com/feathersjs/feathers/issues/2779)) ([ab580cb](https://github.com/feathersjs/feathers/commit/ab580cbcaa68d19144d86798c13bf564f9d424a6)) ### Features -* **authentication-oauth:** Allow dynamic oAuth redirect ([#2469](https://github.com/feathersjs/feathers/issues/2469)) ([b7143d4](https://github.com/feathersjs/feathers/commit/b7143d4c0fbe961e714f79512be04449b9bbd7d9)) -* **core:** add `context.http` and move `statusCode` there ([#2496](https://github.com/feathersjs/feathers/issues/2496)) ([b701bf7](https://github.com/feathersjs/feathers/commit/b701bf77fb83048aa1dffa492b3d77dd53f7b72b)) -* **core:** Improve legacy hooks integration ([08c8b40](https://github.com/feathersjs/feathers/commit/08c8b40999bf3889c61a4d4fad97a2c4f78bafc9)) -* **transport-commons:** Ability to register routes with custom params ([#2482](https://github.com/feathersjs/feathers/issues/2482)) ([497990a](https://github.com/feathersjs/feathers/commit/497990ae4a980e5a52a1f0f932db12cd0e6e254a)) +- **cli:** Add ability to `npm init feathers` ([#2755](https://github.com/feathersjs/feathers/issues/2755)) ([d734931](https://github.com/feathersjs/feathers/commit/d734931ffd4f983a05d9e771ce0e43b696c2bc0e)) +- **cli:** Improve CLI interface ([#2753](https://github.com/feathersjs/feathers/issues/2753)) ([c7e1b7e](https://github.com/feathersjs/feathers/commit/c7e1b7e80aacb84441908c3d73512d9cf7557f7e)) +- **core:** Allow to unregister services at runtime ([#2756](https://github.com/feathersjs/feathers/issues/2756)) ([d16601f](https://github.com/feathersjs/feathers/commit/d16601f2277dca5357866ffdefba2a611f6dc7fa)) +- **schema:** Make schemas validation library independent and add TypeBox support ([#2772](https://github.com/feathersjs/feathers/issues/2772)) ([44172d9](https://github.com/feathersjs/feathers/commit/44172d99b566d11d9ceda04f1d0bf72b6d05ce76)) +# [5.0.0-pre.29](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.28...v5.0.0-pre.29) (2022-09-16) +### Bug Fixes +- **authentication-oauth:** Fix oAuth origin and error handling ([#2752](https://github.com/feathersjs/feathers/issues/2752)) ([f7e1c33](https://github.com/feathersjs/feathers/commit/f7e1c33de1b7af0672a302d2ba6e15d997f0aa83)) +- **schema:** Fix for Ajv global collision bug [#2681](https://github.com/feathersjs/feathers/issues/2681) ([#2702](https://github.com/feathersjs/feathers/issues/2702)) ([0b2def6](https://github.com/feathersjs/feathers/commit/0b2def6ca483fad6ca22fcc4ea9873bc027925d8)) +- **socketio:** Reinitialize hooks on overriden setup method ([#2722](https://github.com/feathersjs/feathers/issues/2722)) ([5e8e7c4](https://github.com/feathersjs/feathers/commit/5e8e7c442238fdc929a0a36b8b8ca2b230ce761f)) +### Features -# [5.0.0-pre.14](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.13...v5.0.0-pre.14) (2021-10-13) +- Add CORS support to oAuth, Express, Koa and generated application ([#2744](https://github.com/feathersjs/feathers/issues/2744)) ([fd218f2](https://github.com/feathersjs/feathers/commit/fd218f289f8ca4c101e9938e8683e2efef6e8131)) +- **authentication-oauth:** Koa and transport independent oAuth authentication ([#2737](https://github.com/feathersjs/feathers/issues/2737)) ([9231525](https://github.com/feathersjs/feathers/commit/9231525a24bb790ba9c5d940f2867a9c727691c9)) +- **cli:** Add custom environment variable support to generated application ([#2751](https://github.com/feathersjs/feathers/issues/2751)) ([c7bf80d](https://github.com/feathersjs/feathers/commit/c7bf80d82c28c190e3f0136d51af5b7de1bc4868)) +- **cli:** Adding ClientService to CLI ([#2750](https://github.com/feathersjs/feathers/issues/2750)) ([1d45427](https://github.com/feathersjs/feathers/commit/1d45427988521ac028755cbe128685fcdf34f636)) -**Note:** Version bump only for package feathers +# [5.0.0-pre.28](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.27...v5.0.0-pre.28) (2022-08-03) +### Bug Fixes +- **authentication-client:** Properly handle missing token error ([#2700](https://github.com/feathersjs/feathers/issues/2700)) ([160746e](https://github.com/feathersjs/feathers/commit/160746e2bceb465fd1b6a003415f8ab38daba521)) +- **cli:** Improve generated application and client ([#2701](https://github.com/feathersjs/feathers/issues/2701)) ([bd55ffb](https://github.com/feathersjs/feathers/commit/bd55ffb812e89bf215f4515e7f137656ea888c3f)) +- **core:** Get hooks to work reliably with custom methods ([#2714](https://github.com/feathersjs/feathers/issues/2714)) ([8d7e04a](https://github.com/feathersjs/feathers/commit/8d7e04acd0f0e2af9f4c13efee652d296dd3bc51)) +- **knex:** Fix PostgreSQL integration issues and run CI tests against pg ([#2698](https://github.com/feathersjs/feathers/issues/2698)) ([1f71d78](https://github.com/feathersjs/feathers/commit/1f71d7884656c1494004931f4979ad59d23e4ee6)) +- **mongodb:** Ensure transactions are used properly in create ([#2699](https://github.com/feathersjs/feathers/issues/2699)) ([fe22615](https://github.com/feathersjs/feathers/commit/fe22615b7fa17d3c20ac26d6f82097917c9b63f6)) +# [5.0.0-pre.27](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.26...v5.0.0-pre.27) (2022-07-13) +### Bug Fixes -# [5.0.0-pre.13](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.12...v5.0.0-pre.13) (2021-10-13) +- **authentication-client:** Ensure reAuthenticate works in parallel with other requests ([#2690](https://github.com/feathersjs/feathers/issues/2690)) ([41b3761](https://github.com/feathersjs/feathers/commit/41b376106b47e2f40a8914db7a5ed2935e070c08)) +- **cli:** Fix flaky authentication migration and SQL id schema types ([#2676](https://github.com/feathersjs/feathers/issues/2676)) ([04ce9a5](https://github.com/feathersjs/feathers/commit/04ce9a53f4226cd6283f9dc241876e90ddf48618)) +- Freeze the resolver context ([#2685](https://github.com/feathersjs/feathers/issues/2685)) ([247dccb](https://github.com/feathersjs/feathers/commit/247dccb2eb72551962030321cb1c0ecb11b0181e)) +- **socketio-client:** Make Socket.io client event target compatible ([#2686](https://github.com/feathersjs/feathers/issues/2686)) ([716c49a](https://github.com/feathersjs/feathers/commit/716c49a270e4be5e5276192092c292f72ffcfa19)) -**Note:** Version bump only for package feathers +### Features +- **cli:** Add support for Prettier ([#2684](https://github.com/feathersjs/feathers/issues/2684)) ([83aa8f9](https://github.com/feathersjs/feathers/commit/83aa8f9f212cb122d831dca8858852b0ac9b4da8)) +- **cli:** Improve generated application folder structure ([#2678](https://github.com/feathersjs/feathers/issues/2678)) ([d114557](https://github.com/feathersjs/feathers/commit/d114557721e73d6302aa88c11e3726dbcbd5c92b)) +# [5.0.0-pre.26](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.25...v5.0.0-pre.26) (2022-06-22) +### Bug Fixes +- **cli:** Fix compilation folders that got mixed up ([fc4cb74](https://github.com/feathersjs/feathers/commit/fc4cb742f7f9164096d9319b13dfaaa5f54686a6)) -# [5.0.0-pre.12](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.11...v5.0.0-pre.12) (2021-10-12) +# [5.0.0-pre.25](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.24...v5.0.0-pre.25) (2022-06-22) -**Note:** Version bump only for package feathers +### Bug Fixes +- **cli:** Generator fixes to work with the new guide ([#2674](https://github.com/feathersjs/feathers/issues/2674)) ([b773fa5](https://github.com/feathersjs/feathers/commit/b773fa5dbd7ff450cfb2f7b93e64882592262712)) +# [5.0.0-pre.24](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.23...v5.0.0-pre.24) (2022-06-21) +### Bug Fixes +- **authentication-oauth:** Fix bug and properly set Grant defaults ([#2659](https://github.com/feathersjs/feathers/issues/2659)) ([cb93bb9](https://github.com/feathersjs/feathers/commit/cb93bb911fd92282424da2db805cd685b7e4a45b)) +- **authentication:** Add safe dispatch data for authentication requests ([#2662](https://github.com/feathersjs/feathers/issues/2662)) ([d8104a1](https://github.com/feathersjs/feathers/commit/d8104a19ee9181e6a5ea81014af29ff9a3c28a8a)) +- **schema:** Fix dispatch resovler hook to convert actually resolved data ([#2663](https://github.com/feathersjs/feathers/issues/2663)) ([f7e87db](https://github.com/feathersjs/feathers/commit/f7e87dbb9a0bc8d89aee47318dddbaa4d6ba5b91)) -# [5.0.0-pre.11](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.10...v5.0.0-pre.11) (2021-10-06) +### Features +- **authentication-local:** Add passwordHash property resolver ([#2660](https://github.com/feathersjs/feathers/issues/2660)) ([b41279b](https://github.com/feathersjs/feathers/commit/b41279b55eea3771a6fa4983a37be2413287bbc6)) +- **cli:** Add generators for new Knex SQL database adapter ([#2673](https://github.com/feathersjs/feathers/issues/2673)) ([0fb2c0f](https://github.com/feathersjs/feathers/commit/0fb2c0f629116f71184b8698c383af8cfd149688)) +- **cli:** Add hook generator ([#2667](https://github.com/feathersjs/feathers/issues/2667)) ([24e4bc0](https://github.com/feathersjs/feathers/commit/24e4bc04a67fadee0e6a96a8389d788faba5c305)) +- **cli:** Add support for JavaScript to the new CLI ([#2668](https://github.com/feathersjs/feathers/issues/2668)) ([ebac587](https://github.com/feathersjs/feathers/commit/ebac587f7d00dc7607c3f546352d79f79b89a5d4)) +- **cli:** Add typed client to a generated app ([#2669](https://github.com/feathersjs/feathers/issues/2669)) ([5b801b5](https://github.com/feathersjs/feathers/commit/5b801b5017ddc3eaa95622b539f51d605916bc86)) +- **cli:** Initial Feathers v5 CLI and Pinion generator ([#2578](https://github.com/feathersjs/feathers/issues/2578)) ([7f59ae7](https://github.com/feathersjs/feathers/commit/7f59ae7f1471895ba8a82aa4702f1a23f71b7682)) +- **knex:** Add KnexJS SQL database adapter to core ([#2671](https://github.com/feathersjs/feathers/issues/2671)) ([9380fff](https://github.com/feathersjs/feathers/commit/9380fff58596e8bb90b8bb098d2795b7eadfec20)) -### Bug Fixes +# [5.0.0-pre.23](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.22...v5.0.0-pre.23) (2022-06-06) -* **core:** Allow to return a new hook context in basic hooks ([#2462](https://github.com/feathersjs/feathers/issues/2462)) ([422b6fc](https://github.com/feathersjs/feathers/commit/422b6fc11cf9e42f4234f0823a0b06a4df50982d)) +### Bug Fixes +- **express:** Ensure Express options can be set before configuring REST transport ([#2655](https://github.com/feathersjs/feathers/issues/2655)) ([c9b8f74](https://github.com/feathersjs/feathers/commit/c9b8f74a0196acb99be44ac5e0fff3f1128288cd)) +- **schema:** Always resolve dispatch in resolveAll and add getDispatch method ([#2645](https://github.com/feathersjs/feathers/issues/2645)) ([145b366](https://github.com/feathersjs/feathers/commit/145b366435695438fbc8db9fdb161162ca9049ad)) +- **schema:** remove `default` from queryProperty schemas ([#2646](https://github.com/feathersjs/feathers/issues/2646)) ([940a2b6](https://github.com/feathersjs/feathers/commit/940a2b6868d2f77f81edb1661f6417ec2ea6e372)) ### Features -* **schema:** Allow resolvers to validate a schema ([#2465](https://github.com/feathersjs/feathers/issues/2465)) ([7d9590b](https://github.com/feathersjs/feathers/commit/7d9590bbe12b94b8b5a7987684f5d4968e426481)) - +- **client:** Improve client side custom method support ([#2654](https://github.com/feathersjs/feathers/issues/2654)) ([c138acf](https://github.com/feathersjs/feathers/commit/c138acf50affbe6b66177d084d3c7a3e9220f09f)) +- **core:** Rename async hooks to around hooks, allow usual registration format ([#2652](https://github.com/feathersjs/feathers/issues/2652)) ([2a485a0](https://github.com/feathersjs/feathers/commit/2a485a07929184261f27437fc0fdfe5a44694834)) +# [5.0.0-pre.22](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.21...v5.0.0-pre.22) (2022-05-24) +### Bug Fixes +- **schema:** Allows resolveData with different resolvers based on method ([#2644](https://github.com/feathersjs/feathers/issues/2644)) ([be71fa2](https://github.com/feathersjs/feathers/commit/be71fa2fe260e05b7dcc0d5f439e33f2e9ec2434)) -# [5.0.0-pre.10](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.9...v5.0.0-pre.10) (2021-09-19) - +# [5.0.0-pre.21](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.20...v5.0.0-pre.21) (2022-05-23) ### Bug Fixes -* **authentication-local:** adds error handling for undefined/null password field ([#2444](https://github.com/feathersjs/feathers/issues/2444)) ([4323f98](https://github.com/feathersjs/feathers/commit/4323f9859a66a7fe3f7f15d81476bd81b735c226)) - +- **authentication-oauth:** Fix regression using incorrect callback and redirect_uri ([#2631](https://github.com/feathersjs/feathers/issues/2631)) ([43d8a08](https://github.com/feathersjs/feathers/commit/43d8a082d7e1807f8a431c44a1dbd9b04c3af0d2)) +- **core:** Do not throw missing method error for regular hook methods ([#2636](https://github.com/feathersjs/feathers/issues/2636)) ([afe9a3b](https://github.com/feathersjs/feathers/commit/afe9a3b3d49897eff045ee237ca2937a6b975291)) +- **schema:** Add Combine helper to allow merging schema types that use ([#2637](https://github.com/feathersjs/feathers/issues/2637)) ([06d03e9](https://github.com/feathersjs/feathers/commit/06d03e91abb1347576c2351c12322d01c58473e5)) +- **typescript:** Make additional types generic to work with extended types ([#2625](https://github.com/feathersjs/feathers/issues/2625)) ([269fdec](https://github.com/feathersjs/feathers/commit/269fdecc5961092dc8608b3cbe16f433c80bfa96)) ### Features -* **schema:** Initial version of schema definitions and resolvers ([#2441](https://github.com/feathersjs/feathers/issues/2441)) ([c57a5cd](https://github.com/feathersjs/feathers/commit/c57a5cd56699a121647be4506d8f967e6d72ecae)) +- **schema:** Add resolveAll hook ([#2643](https://github.com/feathersjs/feathers/issues/2643)) ([85527d7](https://github.com/feathersjs/feathers/commit/85527d71cb78852880696e5d96abdcdf24593934)) +- **schema:** Add resolver for safe external data dispatching ([#2641](https://github.com/feathersjs/feathers/issues/2641)) ([72b980e](https://github.com/feathersjs/feathers/commit/72b980e05631136d30c8f1468dee45ec6a8d2503)) +- **schema:** Add schema resolver converter functionality ([#2640](https://github.com/feathersjs/feathers/issues/2640)) ([26d9e05](https://github.com/feathersjs/feathers/commit/26d9e05327d6e0144466cd57d6fcc11ac7ecb06a)) +# [5.0.0-pre.20](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.19...v5.0.0-pre.20) (2022-05-04) +### Bug Fixes +- **authentication-oauth:** Don't send origins in Grant's config, as it will be considered another provider ([#2617](https://github.com/feathersjs/feathers/issues/2617)) ([ae3dddd](https://github.com/feathersjs/feathers/commit/ae3dddd8a654924465512d56b4651413912c6932)) +- **configuration:** Only validate the initial configuration against the schema ([#2622](https://github.com/feathersjs/feathers/issues/2622)) ([386c5e2](https://github.com/feathersjs/feathers/commit/386c5e2e67bfad4fb4333f2e3e17f7d7e09ac27e)) +- **dependencies:** Lock monorepo package version numbers ([#2623](https://github.com/feathersjs/feathers/issues/2623)) ([5640c10](https://github.com/feathersjs/feathers/commit/5640c1020cc139994e695d658c08bad3494db507)) +### Features -# [5.0.0-pre.9](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.8...v5.0.0-pre.9) (2021-08-09) +- **schema:** Add querySyntax helper to create full query schemas ([#2621](https://github.com/feathersjs/feathers/issues/2621)) ([2bbb103](https://github.com/feathersjs/feathers/commit/2bbb103b2f3e30fb0fff935f92ad3276a1a67e41)) -**Note:** Version bump only for package feathers +# [5.0.0-pre.19](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.18...v5.0.0-pre.19) (2022-05-01) +### Bug Fixes +- **adapter-commons:** Clarify adapter query filtering ([#2607](https://github.com/feathersjs/feathers/issues/2607)) ([2dac771](https://github.com/feathersjs/feathers/commit/2dac771b0a3298d6dd25994d05186701b0617718)) +- **adapter-tests:** Ensure multi tests can run standalone ([#2608](https://github.com/feathersjs/feathers/issues/2608)) ([d7243f2](https://github.com/feathersjs/feathers/commit/d7243f20e84d9dde428ad8dfc7f48388ca569e6e)) +- **authentication-oauth:** Fix issue with overriding the default Grant configuration ([#2615](https://github.com/feathersjs/feathers/issues/2615)) ([b345857](https://github.com/feathersjs/feathers/commit/b3458578532f9750de2940aeb8afdc75cb0b46f2)) +- **authentication-oauth:** Make oAuth authentication work with cookie-session ([#2614](https://github.com/feathersjs/feathers/issues/2614)) ([9f10bfc](https://github.com/feathersjs/feathers/commit/9f10bfc75083d5bcabea77cfb385aa3965cdf6d6)) +- **client:** Fix @feathersjs/client types field ([#2596](https://github.com/feathersjs/feathers/issues/2596)) ([d719f54](https://github.com/feathersjs/feathers/commit/d719f54daee63daf9ed5cc762626ca15131086de)) +- **express:** Fix typo in types reference in package.json ([#2613](https://github.com/feathersjs/feathers/issues/2613)) ([eacf1b3](https://github.com/feathersjs/feathers/commit/eacf1b3474e6d9da69b8671244c23a75cff87d95)) +- **transport-commons:** Ensure socket queries are always plain objects ([#2597](https://github.com/feathersjs/feathers/issues/2597)) ([97313e1](https://github.com/feathersjs/feathers/commit/97313e121cfee4199f10012e95b8507557aa507e)) +### Features +- **mongodb:** Add feathers-mongodb adapter as @feathersjs/mongodb ([#2610](https://github.com/feathersjs/feathers/issues/2610)) ([6d43734](https://github.com/feathersjs/feathers/commit/6d43734a53db02c435cafc52a22dca414e5d0940)) +- **schema:** Allow hooks to run resolvers in sequence ([#2609](https://github.com/feathersjs/feathers/issues/2609)) ([d85c507](https://github.com/feathersjs/feathers/commit/d85c507c76d07e48fc8e7e28ff7de0ef435e0ef8)) +- **typescript:** Improve adapter typings ([#2605](https://github.com/feathersjs/feathers/issues/2605)) ([3b2ca0a](https://github.com/feathersjs/feathers/commit/3b2ca0a6a8e03e8390272c4d7e930b4bffdaacf5)) +- **typescript:** Improve params and query typeability ([#2600](https://github.com/feathersjs/feathers/issues/2600)) ([df28b76](https://github.com/feathersjs/feathers/commit/df28b7619161f1df5e700326f52cca1a92dc5d28)) -# [5.0.0-pre.8](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.7...v5.0.0-pre.8) (2021-08-09) +### BREAKING CHANGES -**Note:** Version bump only for package feathers +- **adapter-commons:** Changes the common adapter base class to use `sanitizeQuery` and `sanitizeData` +# [5.0.0-pre.18](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.17...v5.0.0-pre.18) (2022-04-11) +### Bug Fixes +- **adapter-tests:** Add tests for pagination in multi updates ([#2472](https://github.com/feathersjs/feathers/issues/2472)) ([98a811a](https://github.com/feathersjs/feathers/commit/98a811ac605575ff812a08d0504729a5efe7a69c)) +- **core:** Ensure that dynamically registered services are always set up ([#2593](https://github.com/feathersjs/feathers/issues/2593)) ([27cc7d0](https://github.com/feathersjs/feathers/commit/27cc7d08321861cd69e6b66e1fdfa43c50664820)) +- **schema:** result resolver correctly resolves paginated find result ([#2594](https://github.com/feathersjs/feathers/issues/2594)) ([6511e45](https://github.com/feathersjs/feathers/commit/6511e45bd0624f1a629530719709f4b27fecbe0b)) +### Features -# [5.0.0-pre.7](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.6...v5.0.0-pre.7) (2021-08-09) +- **authentication:** Add setup method for auth strategies ([#1611](https://github.com/feathersjs/feathers/issues/1611)) ([a3c3581](https://github.com/feathersjs/feathers/commit/a3c35814dccdbbf6de96f04f60b226ce206c6dbe)) +- **configuration:** Allow app configuration to be validated against a schema ([#2590](https://github.com/feathersjs/feathers/issues/2590)) ([a268f86](https://github.com/feathersjs/feathers/commit/a268f86da92a8ada14ed11ab456aac0a4bba5bb0)) +- **core:** Add app.setup and app.teardown hook support ([#2585](https://github.com/feathersjs/feathers/issues/2585)) ([ae4ebee](https://github.com/feathersjs/feathers/commit/ae4ebee5d39957651473007c4d3adb210160e040)) +- **core:** Add app.teardown functionality ([#2570](https://github.com/feathersjs/feathers/issues/2570)) ([fcdf524](https://github.com/feathersjs/feathers/commit/fcdf524ae1995bb59265d39f12e98b7794bed023)) +- **core:** Finalize app.teardown() functionality ([#2584](https://github.com/feathersjs/feathers/issues/2584)) ([1a166f3](https://github.com/feathersjs/feathers/commit/1a166f3ded811ecacf0ae8cb67880bc9fa2eeafa)) +- **transport-commons:** add `context.http.response` ([#2524](https://github.com/feathersjs/feathers/issues/2524)) ([5bc9d44](https://github.com/feathersjs/feathers/commit/5bc9d447043c2e2b742c73ed28ecf3b3264dd9e5)) +# [5.0.0-pre.17](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.16...v5.0.0-pre.17) (2022-02-15) ### Bug Fixes -* **core:** Clean up readme ([eb3b4f2](https://github.com/feathersjs/feathers/commit/eb3b4f248c0816c92a2300cceed18a6f2518508a)) -* **core:** Set version back to development ([b328767](https://github.com/feathersjs/feathers/commit/b3287676cd773e164fd646ba4cffbf81983a9157)) +- **express:** Fix application typings to work with typed configuration ([#2539](https://github.com/feathersjs/feathers/issues/2539)) ([b9dfaee](https://github.com/feathersjs/feathers/commit/b9dfaee834b13864c1ed4f2f6a244eb5bb70395b)) +- **hooks:** Allow all built-in hooks to be used the async and regular way ([#2559](https://github.com/feathersjs/feathers/issues/2559)) ([8f9f631](https://github.com/feathersjs/feathers/commit/8f9f631e0ce89de349207db72def84e7ab496a4a)) +- **queryProperty:** allow compound oneOf ([#2545](https://github.com/feathersjs/feathers/issues/2545)) ([3077d2d](https://github.com/feathersjs/feathers/commit/3077d2d896a38d579ce4d5b530e21ad332bcf221)) +- **schema:** Properly handle resolver errors ([#2540](https://github.com/feathersjs/feathers/issues/2540)) ([31fbdff](https://github.com/feathersjs/feathers/commit/31fbdff8bd848ac7e0eda56e307ac34b1bfcf17f)) +# [5.0.0-pre.16](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.15...v5.0.0-pre.16) (2022-01-12) +### Bug Fixes +- **authentication-oauth:** OAuth redirect lost sometimes due to session store race ([#2514](https://github.com/feathersjs/feathers/issues/2514)) ([#2515](https://github.com/feathersjs/feathers/issues/2515)) ([6109c44](https://github.com/feathersjs/feathers/commit/6109c44428c6b8f6bb4e089be760ea1a4ef3d01e)) +- **schema:** Do not error for schemas without properties ([#2519](https://github.com/feathersjs/feathers/issues/2519)) ([96fdb47](https://github.com/feathersjs/feathers/commit/96fdb47d45fd88a8039aa9cc9ec8aebd98672b95)) +- **schema:** Fix resolver data type and use new validation feature in test fixture ([#2523](https://github.com/feathersjs/feathers/issues/2523)) ([1093f12](https://github.com/feathersjs/feathers/commit/1093f124b60524cbd9050fcf07ddaf1d558973da)) +### Features -# [5.0.0-pre.6](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.5...v5.0.0-pre.6) (2021-08-08) +- **express, koa:** make transports similar ([#2486](https://github.com/feathersjs/feathers/issues/2486)) ([26aa937](https://github.com/feathersjs/feathers/commit/26aa937c114fb8596dfefc599b1f53cead69c159)) +- **schema:** Allow to use custom AJV and test with ajv-formats ([#2513](https://github.com/feathersjs/feathers/issues/2513)) ([ecfa4df](https://github.com/feathersjs/feathers/commit/ecfa4df29f029f6ca8517cacf518c14b46ffeb4e)) +- **schema:** Improve schema typing, validation and extensibility ([#2521](https://github.com/feathersjs/feathers/issues/2521)) ([8c1b350](https://github.com/feathersjs/feathers/commit/8c1b35052792e82d13be03c06583534284fbae82)) +# [5.0.0-pre.15](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.14...v5.0.0-pre.15) (2021-11-27) ### Bug Fixes -* **koa:** Throw a NotFound Feathers error on missing paths ([#2415](https://github.com/feathersjs/feathers/issues/2415)) ([e013f98](https://github.com/feathersjs/feathers/commit/e013f98315d550ced6eacffd615c61bb0912b4ba)) - - - +- **adapter-commons:** clean up in sort.ts and select function ([#2492](https://github.com/feathersjs/feathers/issues/2492)) ([c3ec8a4](https://github.com/feathersjs/feathers/commit/c3ec8a418bdc85506e3c5100015720a45454d8d3)) +- **adapter-commons:** Fix sorting for embedded objects ([#2488](https://github.com/feathersjs/feathers/issues/2488)) ([9c22f70](https://github.com/feathersjs/feathers/commit/9c22f70a838cb6341775d91705a7527c8fc5590e)) +- missing express types for Request, Response ([#2498](https://github.com/feathersjs/feathers/issues/2498)) ([ee67131](https://github.com/feathersjs/feathers/commit/ee67131bbaa24c54d3d781bdf8820015759ac488)) +- **typescript:** Overall typing improvements ([#2478](https://github.com/feathersjs/feathers/issues/2478)) ([b8eb804](https://github.com/feathersjs/feathers/commit/b8eb804158556d9651a8607e3c3fda15e0bfd110)) +### Features -# [5.0.0-pre.5](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.4...v5.0.0-pre.5) (2021-06-23) +- **authentication-oauth:** Allow dynamic oAuth redirect ([#2469](https://github.com/feathersjs/feathers/issues/2469)) ([b7143d4](https://github.com/feathersjs/feathers/commit/b7143d4c0fbe961e714f79512be04449b9bbd7d9)) +- **core:** add `context.http` and move `statusCode` there ([#2496](https://github.com/feathersjs/feathers/issues/2496)) ([b701bf7](https://github.com/feathersjs/feathers/commit/b701bf77fb83048aa1dffa492b3d77dd53f7b72b)) +- **core:** Improve legacy hooks integration ([08c8b40](https://github.com/feathersjs/feathers/commit/08c8b40999bf3889c61a4d4fad97a2c4f78bafc9)) +- **transport-commons:** Ability to register routes with custom params ([#2482](https://github.com/feathersjs/feathers/issues/2482)) ([497990a](https://github.com/feathersjs/feathers/commit/497990ae4a980e5a52a1f0f932db12cd0e6e254a)) +# [5.0.0-pre.14](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.13...v5.0.0-pre.14) (2021-10-13) -### Bug Fixes +**Note:** Version bump only for package feathers -* **authentication-oauth:** Omit query from internal calls ([#2398](https://github.com/feathersjs/feathers/issues/2398)) ([04c7c83](https://github.com/feathersjs/feathers/commit/04c7c83eeaa6a7466c84b958071b468ed42f0b0f)) -* **core:** Add list of protected methods that can not be used for custom methods ([#2390](https://github.com/feathersjs/feathers/issues/2390)) ([6584a21](https://github.com/feathersjs/feathers/commit/6584a216e5a7d5f2a45822be6bfcb91c35cc2252)) -* **hooks:** Migrate built-in hooks and allow backwards compatibility ([#2358](https://github.com/feathersjs/feathers/issues/2358)) ([759c5a1](https://github.com/feathersjs/feathers/commit/759c5a19327a731af965c3604119393b3d09a406)) -* **koa:** Use extended query parser for compatibility ([#2397](https://github.com/feathersjs/feathers/issues/2397)) ([b2944ba](https://github.com/feathersjs/feathers/commit/b2944bac3ec6d5ecc80dc518cd4e58093692db74)) -* Update database adapter common repository urls ([#2380](https://github.com/feathersjs/feathers/issues/2380)) ([3f4db68](https://github.com/feathersjs/feathers/commit/3f4db68d6700c7d9023ecd17d0d39893f75a19fd)) +# [5.0.0-pre.13](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.12...v5.0.0-pre.13) (2021-10-13) +**Note:** Version bump only for package feathers -### Features +# [5.0.0-pre.12](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.11...v5.0.0-pre.12) (2021-10-12) -* **typescript:** Allow to pass generic service options to adapter services ([#2392](https://github.com/feathersjs/feathers/issues/2392)) ([f9431f2](https://github.com/feathersjs/feathers/commit/f9431f242354f804cafb835519f98dd405ac4f0b)) -* Support being a built-in CodeSandbox sandbox ([#2381](https://github.com/feathersjs/feathers/issues/2381)) ([a2ac25a](https://github.com/feathersjs/feathers/commit/a2ac25a26e80530f7c50b88ef15eef46ee2b0634)) -* **adapter-commons:** Add support for params.adapter option and move memory adapter to @feathersjs/memory ([#2367](https://github.com/feathersjs/feathers/issues/2367)) ([a43e7da](https://github.com/feathersjs/feathers/commit/a43e7da22b6b981a96d1321736ea9a0cb924fb4f)) +**Note:** Version bump only for package feathers +# [5.0.0-pre.11](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.10...v5.0.0-pre.11) (2021-10-06) +### Bug Fixes +- **core:** Allow to return a new hook context in basic hooks ([#2462](https://github.com/feathersjs/feathers/issues/2462)) ([422b6fc](https://github.com/feathersjs/feathers/commit/422b6fc11cf9e42f4234f0823a0b06a4df50982d)) +### Features -# [5.0.0-pre.4](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.3...v5.0.0-pre.4) (2021-05-13) +- **schema:** Allow resolvers to validate a schema ([#2465](https://github.com/feathersjs/feathers/issues/2465)) ([7d9590b](https://github.com/feathersjs/feathers/commit/7d9590bbe12b94b8b5a7987684f5d4968e426481)) +# [5.0.0-pre.10](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.9...v5.0.0-pre.10) (2021-09-19) ### Bug Fixes -* **transport-commons:** Fix route placeholder registration and improve radix router performance ([#2336](https://github.com/feathersjs/feathers/issues/2336)) ([4d84dfd](https://github.com/feathersjs/feathers/commit/4d84dfd092ce0510312e975d5cd57e04973fb311)) -* **typescript:** Move Paginated type back for better compatibility ([#2350](https://github.com/feathersjs/feathers/issues/2350)) ([2917d05](https://github.com/feathersjs/feathers/commit/2917d05fffb4716d3c4cdaa5ac6a1aee0972e8a6)) - +- **authentication-local:** adds error handling for undefined/null password field ([#2444](https://github.com/feathersjs/feathers/issues/2444)) ([4323f98](https://github.com/feathersjs/feathers/commit/4323f9859a66a7fe3f7f15d81476bd81b735c226)) ### Features -* **koa:** KoaJS transport adapter ([#2315](https://github.com/feathersjs/feathers/issues/2315)) ([2554b57](https://github.com/feathersjs/feathers/commit/2554b57cf05731df58feeba9c12faab18e442107)) - +- **schema:** Initial version of schema definitions and resolvers ([#2441](https://github.com/feathersjs/feathers/issues/2441)) ([c57a5cd](https://github.com/feathersjs/feathers/commit/c57a5cd56699a121647be4506d8f967e6d72ecae)) +# [5.0.0-pre.9](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.8...v5.0.0-pre.9) (2021-08-09) +**Note:** Version bump only for package feathers +# [5.0.0-pre.8](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.7...v5.0.0-pre.8) (2021-08-09) -# [5.0.0-pre.3](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.2...v5.0.0-pre.3) (2021-04-21) +**Note:** Version bump only for package feathers +# [5.0.0-pre.7](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.6...v5.0.0-pre.7) (2021-08-09) ### Bug Fixes -* **typescript:** Improve TypeScript backwards compatibility ([#2310](https://github.com/feathersjs/feathers/issues/2310)) ([f33be73](https://github.com/feathersjs/feathers/commit/f33be73fc46a533efb15df9aab0658e3240d3897)) +- **core:** Clean up readme ([eb3b4f2](https://github.com/feathersjs/feathers/commit/eb3b4f248c0816c92a2300cceed18a6f2518508a)) +- **core:** Set version back to development ([b328767](https://github.com/feathersjs/feathers/commit/b3287676cd773e164fd646ba4cffbf81983a9157)) +# [5.0.0-pre.6](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.5...v5.0.0-pre.6) (2021-08-08) -### Features - -* **deno:** Feathers core build for Deno ([#2299](https://github.com/feathersjs/feathers/issues/2299)) ([dece8fb](https://github.com/feathersjs/feathers/commit/dece8fbc0e7601f1505ce8bbb1e4e69cc26e8f98)) -* **dependencies:** Remove direct debug dependency ([#2296](https://github.com/feathersjs/feathers/issues/2296)) ([501d416](https://github.com/feathersjs/feathers/commit/501d4164d30c6a126906dc640cdfdc82207ba34a)) +### Bug Fixes +- **koa:** Throw a NotFound Feathers error on missing paths ([#2415](https://github.com/feathersjs/feathers/issues/2415)) ([e013f98](https://github.com/feathersjs/feathers/commit/e013f98315d550ced6eacffd615c61bb0912b4ba)) +# [5.0.0-pre.5](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.4...v5.0.0-pre.5) (2021-06-23) +### Bug Fixes +- **authentication-oauth:** Omit query from internal calls ([#2398](https://github.com/feathersjs/feathers/issues/2398)) ([04c7c83](https://github.com/feathersjs/feathers/commit/04c7c83eeaa6a7466c84b958071b468ed42f0b0f)) +- **core:** Add list of protected methods that can not be used for custom methods ([#2390](https://github.com/feathersjs/feathers/issues/2390)) ([6584a21](https://github.com/feathersjs/feathers/commit/6584a216e5a7d5f2a45822be6bfcb91c35cc2252)) +- **hooks:** Migrate built-in hooks and allow backwards compatibility ([#2358](https://github.com/feathersjs/feathers/issues/2358)) ([759c5a1](https://github.com/feathersjs/feathers/commit/759c5a19327a731af965c3604119393b3d09a406)) +- **koa:** Use extended query parser for compatibility ([#2397](https://github.com/feathersjs/feathers/issues/2397)) ([b2944ba](https://github.com/feathersjs/feathers/commit/b2944bac3ec6d5ecc80dc518cd4e58093692db74)) +- Update database adapter common repository urls ([#2380](https://github.com/feathersjs/feathers/issues/2380)) ([3f4db68](https://github.com/feathersjs/feathers/commit/3f4db68d6700c7d9023ecd17d0d39893f75a19fd)) -# [5.0.0-pre.2](https://github.com/feathersjs/feathers/compare/v5.0.0-beta.1...v5.0.0-pre.2) (2021-04-06) +### Features -**Note:** Version bump only for package feathers +- **typescript:** Allow to pass generic service options to adapter services ([#2392](https://github.com/feathersjs/feathers/issues/2392)) ([f9431f2](https://github.com/feathersjs/feathers/commit/f9431f242354f804cafb835519f98dd405ac4f0b)) +- Support being a built-in CodeSandbox sandbox ([#2381](https://github.com/feathersjs/feathers/issues/2381)) ([a2ac25a](https://github.com/feathersjs/feathers/commit/a2ac25a26e80530f7c50b88ef15eef46ee2b0634)) +- **adapter-commons:** Add support for params.adapter option and move memory adapter to @feathersjs/memory ([#2367](https://github.com/feathersjs/feathers/issues/2367)) ([a43e7da](https://github.com/feathersjs/feathers/commit/a43e7da22b6b981a96d1321736ea9a0cb924fb4f)) +# [5.0.0-pre.4](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.3...v5.0.0-pre.4) (2021-05-13) +### Bug Fixes +- **transport-commons:** Fix route placeholder registration and improve radix router performance ([#2336](https://github.com/feathersjs/feathers/issues/2336)) ([4d84dfd](https://github.com/feathersjs/feathers/commit/4d84dfd092ce0510312e975d5cd57e04973fb311)) +- **typescript:** Move Paginated type back for better compatibility ([#2350](https://github.com/feathersjs/feathers/issues/2350)) ([2917d05](https://github.com/feathersjs/feathers/commit/2917d05fffb4716d3c4cdaa5ac6a1aee0972e8a6)) +### Features -# [5.0.0-beta.1](https://github.com/feathersjs/feathers/compare/v5.0.0-beta.0...v5.0.0-beta.1) (2021-04-03) +- **koa:** KoaJS transport adapter ([#2315](https://github.com/feathersjs/feathers/issues/2315)) ([2554b57](https://github.com/feathersjs/feathers/commit/2554b57cf05731df58feeba9c12faab18e442107)) +# [5.0.0-pre.3](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.2...v5.0.0-pre.3) (2021-04-21) ### Bug Fixes -* **adapter-tests:** Add test that verified paginated total ([#2273](https://github.com/feathersjs/feathers/issues/2273)) ([879bd6b](https://github.com/feathersjs/feathers/commit/879bd6b24f42e04eeeeba110ddddda3e1e1dea34)) -* **dependencies:** Fix transport-commons dependency and update other dependencies ([#2284](https://github.com/feathersjs/feathers/issues/2284)) ([05b03b2](https://github.com/feathersjs/feathers/commit/05b03b27b40604d956047e3021d8053c3a137616)) -* **feathers:** Always enable hooks on default service methods ([#2275](https://github.com/feathersjs/feathers/issues/2275)) ([827cc9b](https://github.com/feathersjs/feathers/commit/827cc9b752eecdaf63605d7dffd86f531b7e4af3)) - +- **typescript:** Improve TypeScript backwards compatibility ([#2310](https://github.com/feathersjs/feathers/issues/2310)) ([f33be73](https://github.com/feathersjs/feathers/commit/f33be73fc46a533efb15df9aab0658e3240d3897)) ### Features -* **adapter-commons:** Added mongoDB like search in embedded objects ([687e3c7](https://github.com/feathersjs/feathers/commit/687e3c7c36904221b2707d0220c0893e3cb1faa9)) - - - +- **deno:** Feathers core build for Deno ([#2299](https://github.com/feathersjs/feathers/issues/2299)) ([dece8fb](https://github.com/feathersjs/feathers/commit/dece8fbc0e7601f1505ce8bbb1e4e69cc26e8f98)) +- **dependencies:** Remove direct debug dependency ([#2296](https://github.com/feathersjs/feathers/issues/2296)) ([501d416](https://github.com/feathersjs/feathers/commit/501d4164d30c6a126906dc640cdfdc82207ba34a)) +# [5.0.0-pre.2](https://github.com/feathersjs/feathers/compare/v5.0.0-beta.1...v5.0.0-pre.2) (2021-04-06) -# [5.0.0-beta.0](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.1...v5.0.0-beta.0) (2021-03-28) +**Note:** Version bump only for package feathers +# [5.0.0-beta.1](https://github.com/feathersjs/feathers/compare/v5.0.0-beta.0...v5.0.0-beta.1) (2021-04-03) ### Bug Fixes -* **adapter-commons:** Always respect paginate.max ([#2267](https://github.com/feathersjs/feathers/issues/2267)) ([f588257](https://github.com/feathersjs/feathers/commit/f5882575536624ed3a32bb6e3ff1919fa17e366d)) -* **transport-commons:** Do not error when adding an undefined connection to a channel ([#2268](https://github.com/feathersjs/feathers/issues/2268)) ([28114c4](https://github.com/feathersjs/feathers/commit/28114c495d6564868bb3ffbf619bf80b774dce4b)) -* Resolve some type problems ([#2260](https://github.com/feathersjs/feathers/issues/2260)) ([a3d75fa](https://github.com/feathersjs/feathers/commit/a3d75fa29490e8a19412a12bc993ee7bb573068f)) -* Update Grant usage and other dependencies ([#2264](https://github.com/feathersjs/feathers/issues/2264)) ([7b0f8fa](https://github.com/feathersjs/feathers/commit/7b0f8fad252419ed0ad0bf259cdf3104d322ab60)) -* **adapter-commons:** Return missing overloads ([#2203](https://github.com/feathersjs/feathers/issues/2203)) ([bbe7e2a](https://github.com/feathersjs/feathers/commit/bbe7e2a131633e9a6e7aac7f7fa02a312bca63c7)) -* **socketio-client:** Fix client transport-commons reference ([#2164](https://github.com/feathersjs/feathers/issues/2164)) ([3a42c54](https://github.com/feathersjs/feathers/commit/3a42c544058456b19c7e21827226541bfa6ad621)) - +- **adapter-tests:** Add test that verified paginated total ([#2273](https://github.com/feathersjs/feathers/issues/2273)) ([879bd6b](https://github.com/feathersjs/feathers/commit/879bd6b24f42e04eeeeba110ddddda3e1e1dea34)) +- **dependencies:** Fix transport-commons dependency and update other dependencies ([#2284](https://github.com/feathersjs/feathers/issues/2284)) ([05b03b2](https://github.com/feathersjs/feathers/commit/05b03b27b40604d956047e3021d8053c3a137616)) +- **feathers:** Always enable hooks on default service methods ([#2275](https://github.com/feathersjs/feathers/issues/2275)) ([827cc9b](https://github.com/feathersjs/feathers/commit/827cc9b752eecdaf63605d7dffd86f531b7e4af3)) ### Features -* **core:** Public custom service methods ([#2270](https://github.com/feathersjs/feathers/issues/2270)) ([e65abfb](https://github.com/feathersjs/feathers/commit/e65abfb5388df6c19a11c565cf1076a29f32668d)) -* Application service types default to any ([#1566](https://github.com/feathersjs/feathers/issues/1566)) ([d93ba9a](https://github.com/feathersjs/feathers/commit/d93ba9a17edd20d3397bb00f4f6e82e804e42ed6)) -* Feathers v5 core refactoring and features ([#2255](https://github.com/feathersjs/feathers/issues/2255)) ([2dafb7c](https://github.com/feathersjs/feathers/commit/2dafb7ce14ba57406aeec13d10ca45b1e709bee9)) -* **authentication-client:** Throw separate OauthError in authentication client ([#2189](https://github.com/feathersjs/feathers/issues/2189)) ([fa45ec5](https://github.com/feathersjs/feathers/commit/fa45ec520b21834e103e6fe4200b06dced56c0e6)) -* **core:** Remove Uberproto ([#2178](https://github.com/feathersjs/feathers/issues/2178)) ([ddf8821](https://github.com/feathersjs/feathers/commit/ddf8821f53317e6a378657f7d66acb03a037ee47)) -* **transport-commons:** New built-in high performance radix router ([#2177](https://github.com/feathersjs/feathers/issues/2177)) ([6d18065](https://github.com/feathersjs/feathers/commit/6d180651b4eb40289ecea3df3575f207aa6c5d1f)) +- **adapter-commons:** Added mongoDB like search in embedded objects ([687e3c7](https://github.com/feathersjs/feathers/commit/687e3c7c36904221b2707d0220c0893e3cb1faa9)) +# [5.0.0-beta.0](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.1...v5.0.0-beta.0) (2021-03-28) -### BREAKING CHANGES +### Bug Fixes -* **core:** Services no longer extend Uberproto objects and -`service.mixin()` is no longer available. +- **adapter-commons:** Always respect paginate.max ([#2267](https://github.com/feathersjs/feathers/issues/2267)) ([f588257](https://github.com/feathersjs/feathers/commit/f5882575536624ed3a32bb6e3ff1919fa17e366d)) +- **transport-commons:** Do not error when adding an undefined connection to a channel ([#2268](https://github.com/feathersjs/feathers/issues/2268)) ([28114c4](https://github.com/feathersjs/feathers/commit/28114c495d6564868bb3ffbf619bf80b774dce4b)) +- Resolve some type problems ([#2260](https://github.com/feathersjs/feathers/issues/2260)) ([a3d75fa](https://github.com/feathersjs/feathers/commit/a3d75fa29490e8a19412a12bc993ee7bb573068f)) +- Update Grant usage and other dependencies ([#2264](https://github.com/feathersjs/feathers/issues/2264)) ([7b0f8fa](https://github.com/feathersjs/feathers/commit/7b0f8fad252419ed0ad0bf259cdf3104d322ab60)) +- **adapter-commons:** Return missing overloads ([#2203](https://github.com/feathersjs/feathers/issues/2203)) ([bbe7e2a](https://github.com/feathersjs/feathers/commit/bbe7e2a131633e9a6e7aac7f7fa02a312bca63c7)) +- **socketio-client:** Fix client transport-commons reference ([#2164](https://github.com/feathersjs/feathers/issues/2164)) ([3a42c54](https://github.com/feathersjs/feathers/commit/3a42c544058456b19c7e21827226541bfa6ad621)) +### Features +- **core:** Public custom service methods ([#2270](https://github.com/feathersjs/feathers/issues/2270)) ([e65abfb](https://github.com/feathersjs/feathers/commit/e65abfb5388df6c19a11c565cf1076a29f32668d)) +- Application service types default to any ([#1566](https://github.com/feathersjs/feathers/issues/1566)) ([d93ba9a](https://github.com/feathersjs/feathers/commit/d93ba9a17edd20d3397bb00f4f6e82e804e42ed6)) +- Feathers v5 core refactoring and features ([#2255](https://github.com/feathersjs/feathers/issues/2255)) ([2dafb7c](https://github.com/feathersjs/feathers/commit/2dafb7ce14ba57406aeec13d10ca45b1e709bee9)) +- **authentication-client:** Throw separate OauthError in authentication client ([#2189](https://github.com/feathersjs/feathers/issues/2189)) ([fa45ec5](https://github.com/feathersjs/feathers/commit/fa45ec520b21834e103e6fe4200b06dced56c0e6)) +- **core:** Remove Uberproto ([#2178](https://github.com/feathersjs/feathers/issues/2178)) ([ddf8821](https://github.com/feathersjs/feathers/commit/ddf8821f53317e6a378657f7d66acb03a037ee47)) +- **transport-commons:** New built-in high performance radix router ([#2177](https://github.com/feathersjs/feathers/issues/2177)) ([6d18065](https://github.com/feathersjs/feathers/commit/6d180651b4eb40289ecea3df3575f207aa6c5d1f)) +### BREAKING CHANGES +- **core:** Services no longer extend Uberproto objects and + `service.mixin()` is no longer available. # [5.0.0-pre.1](https://github.com/feathersjs/feathers/compare/v4.5.11...v5.0.0-pre.1) (2020-12-17) - ### Features -* **memory:** Move feathers-memory into @feathersjs/memory ([#2153](https://github.com/feathersjs/feathers/issues/2153)) ([dd61fe3](https://github.com/feathersjs/feathers/commit/dd61fe371fb0502f78b8ccbe1f45a030e31ecff6)) - - +- **memory:** Move feathers-memory into @feathersjs/memory ([#2153](https://github.com/feathersjs/feathers/issues/2153)) ([dd61fe3](https://github.com/feathersjs/feathers/commit/dd61fe371fb0502f78b8ccbe1f45a030e31ecff6)) # [5.0.0-pre.0](https://github.com/feathersjs/feathers/compare/v4.5.4...v5.0.0-pre.0) (2020-05-19) - ### Bug Fixes -* **errors:** Format package.json with spaces ([cbd31c1](https://github.com/feathersjs/feathers/commit/cbd31c10c2c574de63d6ca5e55dbfb73a5fdd758)) - +- **errors:** Format package.json with spaces ([cbd31c1](https://github.com/feathersjs/feathers/commit/cbd31c10c2c574de63d6ca5e55dbfb73a5fdd758)) ### chore -* **configuration:** Remove environment variable substitution ([#1942](https://github.com/feathersjs/feathers/issues/1942)) ([caaa21f](https://github.com/feathersjs/feathers/commit/caaa21ffdc6a8dcac82fb403c91d9d4b781a6c0a)) -* **package:** Remove @feathersjs/primus packages from core ([#1919](https://github.com/feathersjs/feathers/issues/1919)) ([d20b7d5](https://github.com/feathersjs/feathers/commit/d20b7d5a70f4d3306e294696156e8aa0337c35e9)), closes [#1899](https://github.com/feathersjs/feathers/issues/1899) - +- **configuration:** Remove environment variable substitution ([#1942](https://github.com/feathersjs/feathers/issues/1942)) ([caaa21f](https://github.com/feathersjs/feathers/commit/caaa21ffdc6a8dcac82fb403c91d9d4b781a6c0a)) +- **package:** Remove @feathersjs/primus packages from core ([#1919](https://github.com/feathersjs/feathers/issues/1919)) ([d20b7d5](https://github.com/feathersjs/feathers/commit/d20b7d5a70f4d3306e294696156e8aa0337c35e9)), closes [#1899](https://github.com/feathersjs/feathers/issues/1899) ### Features -* **core:** Migrate @feathersjs/feathers to TypeScript ([#1963](https://github.com/feathersjs/feathers/issues/1963)) ([7812529](https://github.com/feathersjs/feathers/commit/7812529ff0f1008e21211f1d01efbc49795dbe55)) -* **core:** use @feathers/hooks and add async type ([#1929](https://github.com/feathersjs/feathers/issues/1929)) ([a5c4756](https://github.com/feathersjs/feathers/commit/a5c47562eae8410c82fe2f6308f26f8e78b6a3e8)) -* **transport-commons:** Remove legacy message format and unnecessary client timeouts ([#1939](https://github.com/feathersjs/feathers/issues/1939)) ([5538881](https://github.com/feathersjs/feathers/commit/5538881a08bc130de42c5984055729d8336f8615)) - +- **core:** Migrate @feathersjs/feathers to TypeScript ([#1963](https://github.com/feathersjs/feathers/issues/1963)) ([7812529](https://github.com/feathersjs/feathers/commit/7812529ff0f1008e21211f1d01efbc49795dbe55)) +- **core:** use @feathers/hooks and add async type ([#1929](https://github.com/feathersjs/feathers/issues/1929)) ([a5c4756](https://github.com/feathersjs/feathers/commit/a5c47562eae8410c82fe2f6308f26f8e78b6a3e8)) +- **transport-commons:** Remove legacy message format and unnecessary client timeouts ([#1939](https://github.com/feathersjs/feathers/issues/1939)) ([5538881](https://github.com/feathersjs/feathers/commit/5538881a08bc130de42c5984055729d8336f8615)) ### BREAKING CHANGES -* **configuration:** Falls back to node-config instead of adding additional -functionality like path replacements and automatic environment variable insertion. -* **transport-commons:** Removes the old message format and client service timeout -* **package:** Remove primus packages to be moved into the ecosystem. - - - - +- **configuration:** Falls back to node-config instead of adding additional + functionality like path replacements and automatic environment variable insertion. +- **transport-commons:** Removes the old message format and client service timeout +- **package:** Remove primus packages to be moved into the ecosystem. # [5.0.0-pre.0](https://github.com/feathersjs/feathers/compare/v4.5.4...v5.0.0-pre.0) (2020-05-19) ### Bug Fixes -* **authentication-oauth:** Updated typings for projects with strictNullChecks ([#1941](https://github.com/feathersjs/feathers/issues/1941)) ([be91206](https://github.com/feathersjs/feathers/commit/be91206e3dba1e65a81412b7aa636bece3ab4aa2)) -* **errors:** Format package.json with spaces ([cbd31c1](https://github.com/feathersjs/feathers/commit/cbd31c10c2c574de63d6ca5e55dbfb73a5fdd758)) - +- **authentication-oauth:** Updated typings for projects with strictNullChecks ([#1941](https://github.com/feathersjs/feathers/issues/1941)) ([be91206](https://github.com/feathersjs/feathers/commit/be91206e3dba1e65a81412b7aa636bece3ab4aa2)) +- **errors:** Format package.json with spaces ([cbd31c1](https://github.com/feathersjs/feathers/commit/cbd31c10c2c574de63d6ca5e55dbfb73a5fdd758)) ### chore -* **configuration:** Remove environment variable substitution ([#1942](https://github.com/feathersjs/feathers/issues/1942)) ([caaa21f](https://github.com/feathersjs/feathers/commit/caaa21ffdc6a8dcac82fb403c91d9d4b781a6c0a)) -* **package:** Remove @feathersjs/primus packages from core ([#1919](https://github.com/feathersjs/feathers/issues/1919)) ([d20b7d5](https://github.com/feathersjs/feathers/commit/d20b7d5a70f4d3306e294696156e8aa0337c35e9)), closes [#1899](https://github.com/feathersjs/feathers/issues/1899) - +- **configuration:** Remove environment variable substitution ([#1942](https://github.com/feathersjs/feathers/issues/1942)) ([caaa21f](https://github.com/feathersjs/feathers/commit/caaa21ffdc6a8dcac82fb403c91d9d4b781a6c0a)) +- **package:** Remove @feathersjs/primus packages from core ([#1919](https://github.com/feathersjs/feathers/issues/1919)) ([d20b7d5](https://github.com/feathersjs/feathers/commit/d20b7d5a70f4d3306e294696156e8aa0337c35e9)), closes [#1899](https://github.com/feathersjs/feathers/issues/1899) ### Features -* **core:** Migrate @feathersjs/feathers to TypeScript ([#1963](https://github.com/feathersjs/feathers/issues/1963)) ([7812529](https://github.com/feathersjs/feathers/commit/7812529ff0f1008e21211f1d01efbc49795dbe55)) -* **core:** use @feathers/hooks and add async type ([#1929](https://github.com/feathersjs/feathers/issues/1929)) ([a5c4756](https://github.com/feathersjs/feathers/commit/a5c47562eae8410c82fe2f6308f26f8e78b6a3e8)) -* **transport-commons:** Remove legacy message format and unnecessary client timeouts ([#1939](https://github.com/feathersjs/feathers/issues/1939)) ([5538881](https://github.com/feathersjs/feathers/commit/5538881a08bc130de42c5984055729d8336f8615)) - +- **core:** Migrate @feathersjs/feathers to TypeScript ([#1963](https://github.com/feathersjs/feathers/issues/1963)) ([7812529](https://github.com/feathersjs/feathers/commit/7812529ff0f1008e21211f1d01efbc49795dbe55)) +- **core:** use @feathers/hooks and add async type ([#1929](https://github.com/feathersjs/feathers/issues/1929)) ([a5c4756](https://github.com/feathersjs/feathers/commit/a5c47562eae8410c82fe2f6308f26f8e78b6a3e8)) +- **transport-commons:** Remove legacy message format and unnecessary client timeouts ([#1939](https://github.com/feathersjs/feathers/issues/1939)) ([5538881](https://github.com/feathersjs/feathers/commit/5538881a08bc130de42c5984055729d8336f8615)) ### BREAKING CHANGES -* **configuration:** Falls back to node-config instead of adding additional -functionality like path replacements and automatic environment variable insertion. -* **transport-commons:** Removes the old message format and client service timeout -* **package:** Remove primus packages to be moved into the ecosystem. - - +- **configuration:** Falls back to node-config instead of adding additional + functionality like path replacements and automatic environment variable insertion. +- **transport-commons:** Removes the old message format and client service timeout +- **package:** Remove primus packages to be moved into the ecosystem. ## [4.5.11](https://github.com/feathersjs/feathers/compare/v4.5.10...v4.5.11) (2020-12-05) - ### Bug Fixes -* **authentication-client:** Allow reAuthentication using specific strategy ([#2140](https://github.com/feathersjs/feathers/issues/2140)) ([2a2bbf7](https://github.com/feathersjs/feathers/commit/2a2bbf7f8ee6d32b9fac8afab3421286b06e6443)) -* **socketio-client:** Throw an error and show a warning if someone tries to use socket.io-client v3 ([#2135](https://github.com/feathersjs/feathers/issues/2135)) ([cc3521c](https://github.com/feathersjs/feathers/commit/cc3521c935a1cbd690e29b7057998e3898f282db)) -* **typescript:** Fix `data` property definition in @feathersjs/errors ([#2018](https://github.com/feathersjs/feathers/issues/2018)) ([ef1398c](https://github.com/feathersjs/feathers/commit/ef1398cd5b19efa50929e8c9511ca5684a18997f)) - - - - +- **authentication-client:** Allow reAuthentication using specific strategy ([#2140](https://github.com/feathersjs/feathers/issues/2140)) ([2a2bbf7](https://github.com/feathersjs/feathers/commit/2a2bbf7f8ee6d32b9fac8afab3421286b06e6443)) +- **socketio-client:** Throw an error and show a warning if someone tries to use socket.io-client v3 ([#2135](https://github.com/feathersjs/feathers/issues/2135)) ([cc3521c](https://github.com/feathersjs/feathers/commit/cc3521c935a1cbd690e29b7057998e3898f282db)) +- **typescript:** Fix `data` property definition in @feathersjs/errors ([#2018](https://github.com/feathersjs/feathers/issues/2018)) ([ef1398c](https://github.com/feathersjs/feathers/commit/ef1398cd5b19efa50929e8c9511ca5684a18997f)) ## [4.5.10](https://github.com/feathersjs/feathers/compare/v4.5.9...v4.5.10) (2020-11-08) - ### Bug Fixes -* **authentication:** consistent response return between local and jwt strategy ([#2042](https://github.com/feathersjs/feathers/issues/2042)) ([8d25be1](https://github.com/feathersjs/feathers/commit/8d25be101a2593a9e789375c928a07780b9e28cf)) -* **authentication-oauth:** session.destroy is undefined when use cookie-session package ([#2100](https://github.com/feathersjs/feathers/issues/2100)) ([46e84b8](https://github.com/feathersjs/feathers/commit/46e84b83f2acce985380243fc6d08c64e96f0068)) -* **package:** Fix clean script in non Unix environments ([#2110](https://github.com/feathersjs/feathers/issues/2110)) ([09b62c0](https://github.com/feathersjs/feathers/commit/09b62c0c7e636caf620904ba87d61f168a020f05)) -* **typescript:** Add user property to the Params. ([#2090](https://github.com/feathersjs/feathers/issues/2090)) ([1e94265](https://github.com/feathersjs/feathers/commit/1e942651fbaaf07fc66c159225fbc992a0174bf4)) - - - - +- **authentication:** consistent response return between local and jwt strategy ([#2042](https://github.com/feathersjs/feathers/issues/2042)) ([8d25be1](https://github.com/feathersjs/feathers/commit/8d25be101a2593a9e789375c928a07780b9e28cf)) +- **authentication-oauth:** session.destroy is undefined when use cookie-session package ([#2100](https://github.com/feathersjs/feathers/issues/2100)) ([46e84b8](https://github.com/feathersjs/feathers/commit/46e84b83f2acce985380243fc6d08c64e96f0068)) +- **package:** Fix clean script in non Unix environments ([#2110](https://github.com/feathersjs/feathers/issues/2110)) ([09b62c0](https://github.com/feathersjs/feathers/commit/09b62c0c7e636caf620904ba87d61f168a020f05)) +- **typescript:** Add user property to the Params. ([#2090](https://github.com/feathersjs/feathers/issues/2090)) ([1e94265](https://github.com/feathersjs/feathers/commit/1e942651fbaaf07fc66c159225fbc992a0174bf4)) ## [4.5.9](https://github.com/feathersjs/feathers/compare/v4.5.8...v4.5.9) (2020-10-09) - ### Bug Fixes -* **authentication-local:** Keep non-objects in protect hook ([#2085](https://github.com/feathersjs/feathers/issues/2085)) ([5a65e2e](https://github.com/feathersjs/feathers/commit/5a65e2e6cee0a15614f23ee2e0d3c25d3365027d)) -* **authentication-oauth:** Always end session after oAuth flows are finished ([#2087](https://github.com/feathersjs/feathers/issues/2087)) ([d219d0d](https://github.com/feathersjs/feathers/commit/d219d0d89c5e45aa289dd67cb0c8bdc05044c846)) -* **configuration:** Fix handling of config values that start with . or .. but are not actually relative paths; e.g. ".foo" or "..bar" ([#2065](https://github.com/feathersjs/feathers/issues/2065)) ([d07bf59](https://github.com/feathersjs/feathers/commit/d07bf5902e9c8c606f16b9523472972d3d2e9b49)) -* **rest-client:** Handle non-JSON errors with fetch adapter ([#2086](https://github.com/feathersjs/feathers/issues/2086)) ([e24217a](https://github.com/feathersjs/feathers/commit/e24217ad1e784ad71cd9d64fe1727dd02f039991)) - - - - +- **authentication-local:** Keep non-objects in protect hook ([#2085](https://github.com/feathersjs/feathers/issues/2085)) ([5a65e2e](https://github.com/feathersjs/feathers/commit/5a65e2e6cee0a15614f23ee2e0d3c25d3365027d)) +- **authentication-oauth:** Always end session after oAuth flows are finished ([#2087](https://github.com/feathersjs/feathers/issues/2087)) ([d219d0d](https://github.com/feathersjs/feathers/commit/d219d0d89c5e45aa289dd67cb0c8bdc05044c846)) +- **configuration:** Fix handling of config values that start with . or .. but are not actually relative paths; e.g. ".foo" or "..bar" ([#2065](https://github.com/feathersjs/feathers/issues/2065)) ([d07bf59](https://github.com/feathersjs/feathers/commit/d07bf5902e9c8c606f16b9523472972d3d2e9b49)) +- **rest-client:** Handle non-JSON errors with fetch adapter ([#2086](https://github.com/feathersjs/feathers/issues/2086)) ([e24217a](https://github.com/feathersjs/feathers/commit/e24217ad1e784ad71cd9d64fe1727dd02f039991)) ## [4.5.8](https://github.com/feathersjs/feathers/compare/v4.5.7...v4.5.8) (2020-08-12) - -* **authentication-client:** Fix storage type so it works with all supported interfaces ([#2041](https://github.com/feathersjs/feathers/issues/2041)) ([6ee0e78](https://github.com/feathersjs/feathers/commit/6ee0e78d55cf1214f61458f386b94c350eec32af)) - - - - +- **authentication-client:** Fix storage type so it works with all supported interfaces ([#2041](https://github.com/feathersjs/feathers/issues/2041)) ([6ee0e78](https://github.com/feathersjs/feathers/commit/6ee0e78d55cf1214f61458f386b94c350eec32af)) ## [4.5.7](https://github.com/feathersjs/feathers/compare/v4.5.6...v4.5.7) (2020-07-24) - ### Bug Fixes -* **authentication:** Add JWT getEntityQuery ([#2013](https://github.com/feathersjs/feathers/issues/2013)) ([e0e7fb5](https://github.com/feathersjs/feathers/commit/e0e7fb5162940fe776731283b40026c61d9c8a33)) -* **typescript:** Revert add overload types for `find` service methods ([#1972](https://github.com/feathersjs/feathers/issues/1972))" ([#2025](https://github.com/feathersjs/feathers/issues/2025)) ([a9501ac](https://github.com/feathersjs/feathers/commit/a9501acb4d3ef58dfb87d62c57a9bf76569da281)) - - - - +- **authentication:** Add JWT getEntityQuery ([#2013](https://github.com/feathersjs/feathers/issues/2013)) ([e0e7fb5](https://github.com/feathersjs/feathers/commit/e0e7fb5162940fe776731283b40026c61d9c8a33)) +- **typescript:** Revert add overload types for `find` service methods ([#1972](https://github.com/feathersjs/feathers/issues/1972))" ([#2025](https://github.com/feathersjs/feathers/issues/2025)) ([a9501ac](https://github.com/feathersjs/feathers/commit/a9501acb4d3ef58dfb87d62c57a9bf76569da281)) ## [4.5.6](https://github.com/feathersjs/feathers/compare/v4.5.5...v4.5.6) (2020-07-12) - ### Bug Fixes -* **authentication:** Omit query in JWT strategy ([#2011](https://github.com/feathersjs/feathers/issues/2011)) ([04ce7e9](https://github.com/feathersjs/feathers/commit/04ce7e98515fe9d495cd0e83e0da097e9bcd7382)) - - - - +- **authentication:** Omit query in JWT strategy ([#2011](https://github.com/feathersjs/feathers/issues/2011)) ([04ce7e9](https://github.com/feathersjs/feathers/commit/04ce7e98515fe9d495cd0e83e0da097e9bcd7382)) ## [4.5.5](https://github.com/feathersjs/feathers/compare/v4.5.4...v4.5.5) (2020-07-11) - ### Bug Fixes -* **authentication:** Include query params when authenticating via authenticate hook [#2009](https://github.com/feathersjs/feathers/issues/2009) ([4cdb7bf](https://github.com/feathersjs/feathers/commit/4cdb7bf2898385ddac7a1692bc9ac2f6cf5ad446)) -* **authentication-oauth:** Updated typings for projects with strictNullChecks ([#1941](https://github.com/feathersjs/feathers/issues/1941)) ([be91206](https://github.com/feathersjs/feathers/commit/be91206e3dba1e65a81412b7aa636bece3ab4aa2)) -* **typescript:** add overload types for `find` service methods ([#1972](https://github.com/feathersjs/feathers/issues/1972)) ([ef55af0](https://github.com/feathersjs/feathers/commit/ef55af088d05d9d36aba9d9f8d6c2c908a4f20dd)) - - - - +- **authentication:** Include query params when authenticating via authenticate hook [#2009](https://github.com/feathersjs/feathers/issues/2009) ([4cdb7bf](https://github.com/feathersjs/feathers/commit/4cdb7bf2898385ddac7a1692bc9ac2f6cf5ad446)) +- **authentication-oauth:** Updated typings for projects with strictNullChecks ([#1941](https://github.com/feathersjs/feathers/issues/1941)) ([be91206](https://github.com/feathersjs/feathers/commit/be91206e3dba1e65a81412b7aa636bece3ab4aa2)) +- **typescript:** add overload types for `find` service methods ([#1972](https://github.com/feathersjs/feathers/issues/1972)) ([ef55af0](https://github.com/feathersjs/feathers/commit/ef55af088d05d9d36aba9d9f8d6c2c908a4f20dd)) ## [4.5.4](https://github.com/feathersjs/feathers/compare/v4.5.3...v4.5.4) (2020-04-29) - ### Bug Fixes -* **authentication-local:** Allow to hash passwords in array data ([#1936](https://github.com/feathersjs/feathers/issues/1936)) ([64705f5](https://github.com/feathersjs/feathers/commit/64705f5d9d4dc27f799da3a074efaf74379a3398)) -* **authentication-oauth:** Add getEntity method to oAuth authentication and remove provider field for other calls ([#1935](https://github.com/feathersjs/feathers/issues/1935)) ([d925c1b](https://github.com/feathersjs/feathers/commit/d925c1bd193b5c19cb23a246f04fc46d0429fc75)) - - - - +- **authentication-local:** Allow to hash passwords in array data ([#1936](https://github.com/feathersjs/feathers/issues/1936)) ([64705f5](https://github.com/feathersjs/feathers/commit/64705f5d9d4dc27f799da3a074efaf74379a3398)) +- **authentication-oauth:** Add getEntity method to oAuth authentication and remove provider field for other calls ([#1935](https://github.com/feathersjs/feathers/issues/1935)) ([d925c1b](https://github.com/feathersjs/feathers/commit/d925c1bd193b5c19cb23a246f04fc46d0429fc75)) ## [4.5.3](https://github.com/feathersjs/feathers/compare/v4.5.2...v4.5.3) (2020-04-17) - ### Bug Fixes -* **authentication:** Remove entity from connection information on logout ([#1889](https://github.com/feathersjs/feathers/issues/1889)) ([b062753](https://github.com/feathersjs/feathers/commit/b0627530d61babe15dd84369d3093ccae4b780ca)) -* **authentication-oauth:** Allow req.feathers to be used in oAuth authentication requests ([#1886](https://github.com/feathersjs/feathers/issues/1886)) ([854c9ca](https://github.com/feathersjs/feathers/commit/854c9cac9a9a5f8f89054a90feb24ab5c4766f5f)) -* **errors:** Add 410 Gone to errors ([#1849](https://github.com/feathersjs/feathers/issues/1849)) ([6801428](https://github.com/feathersjs/feathers/commit/6801428f8fd17dbfebcdb6f1b0cd01433a4033dc)) -* **typescript:** Add type keys to service pagination options. ([#1888](https://github.com/feathersjs/feathers/issues/1888)) ([859c601](https://github.com/feathersjs/feathers/commit/859c601519c7cb399e8b1667bb50073466812d5c)) -* **typescript:** Use stricter type for HookContext 'method' prop ([#1896](https://github.com/feathersjs/feathers/issues/1896)) ([24a41b7](https://github.com/feathersjs/feathers/commit/24a41b74486ddadccad18f3ae63afdac5bd373c7)) - - - - +- **authentication:** Remove entity from connection information on logout ([#1889](https://github.com/feathersjs/feathers/issues/1889)) ([b062753](https://github.com/feathersjs/feathers/commit/b0627530d61babe15dd84369d3093ccae4b780ca)) +- **authentication-oauth:** Allow req.feathers to be used in oAuth authentication requests ([#1886](https://github.com/feathersjs/feathers/issues/1886)) ([854c9ca](https://github.com/feathersjs/feathers/commit/854c9cac9a9a5f8f89054a90feb24ab5c4766f5f)) +- **errors:** Add 410 Gone to errors ([#1849](https://github.com/feathersjs/feathers/issues/1849)) ([6801428](https://github.com/feathersjs/feathers/commit/6801428f8fd17dbfebcdb6f1b0cd01433a4033dc)) +- **typescript:** Add type keys to service pagination options. ([#1888](https://github.com/feathersjs/feathers/issues/1888)) ([859c601](https://github.com/feathersjs/feathers/commit/859c601519c7cb399e8b1667bb50073466812d5c)) +- **typescript:** Use stricter type for HookContext 'method' prop ([#1896](https://github.com/feathersjs/feathers/issues/1896)) ([24a41b7](https://github.com/feathersjs/feathers/commit/24a41b74486ddadccad18f3ae63afdac5bd373c7)) ## [4.5.2](https://github.com/feathersjs/feathers/compare/v4.5.1...v4.5.2) (2020-03-04) - ### Bug Fixes -* Updated typings for express middleware ([#1839](https://github.com/feathersjs/feathers/issues/1839)) ([6b8e897](https://github.com/feathersjs/feathers/commit/6b8e8971a9dbb08913edd1be48826624645d9dc1)) -* **authentication:** Improve JWT strategy configuration error message ([#1844](https://github.com/feathersjs/feathers/issues/1844)) ([2c771db](https://github.com/feathersjs/feathers/commit/2c771dbb22d53d4f7de3c3f514e57afa1a186322)) -* **package:** update grant-profile to version 0.0.11 ([#1841](https://github.com/feathersjs/feathers/issues/1841)) ([5dcd2aa](https://github.com/feathersjs/feathers/commit/5dcd2aa3483059cc7a2546b145dd72b4705fe2fe)) -* **test:** typo in password ([#1797](https://github.com/feathersjs/feathers/issues/1797)) ([dfba6ec](https://github.com/feathersjs/feathers/commit/dfba6ec2f21adf3aa739218cf870eaaaa5df6e9c)) -* **typescript:** Make HookMap and HookObject generics. ([#1815](https://github.com/feathersjs/feathers/issues/1815)) ([d10145d](https://github.com/feathersjs/feathers/commit/d10145d91a09aef7bce5af80805a3c0fa9d94f26)) - - - - +- Updated typings for express middleware ([#1839](https://github.com/feathersjs/feathers/issues/1839)) ([6b8e897](https://github.com/feathersjs/feathers/commit/6b8e8971a9dbb08913edd1be48826624645d9dc1)) +- **authentication:** Improve JWT strategy configuration error message ([#1844](https://github.com/feathersjs/feathers/issues/1844)) ([2c771db](https://github.com/feathersjs/feathers/commit/2c771dbb22d53d4f7de3c3f514e57afa1a186322)) +- **package:** update grant-profile to version 0.0.11 ([#1841](https://github.com/feathersjs/feathers/issues/1841)) ([5dcd2aa](https://github.com/feathersjs/feathers/commit/5dcd2aa3483059cc7a2546b145dd72b4705fe2fe)) +- **test:** typo in password ([#1797](https://github.com/feathersjs/feathers/issues/1797)) ([dfba6ec](https://github.com/feathersjs/feathers/commit/dfba6ec2f21adf3aa739218cf870eaaaa5df6e9c)) +- **typescript:** Make HookMap and HookObject generics. ([#1815](https://github.com/feathersjs/feathers/issues/1815)) ([d10145d](https://github.com/feathersjs/feathers/commit/d10145d91a09aef7bce5af80805a3c0fa9d94f26)) ## [4.5.1](https://github.com/feathersjs/feathers/compare/v4.5.0...v4.5.1) (2020-01-24) **Note:** Version bump only for package feathers - - - - # [4.5.0](https://github.com/feathersjs/feathers/compare/v4.4.3...v4.5.0) (2020-01-18) - ### Bug Fixes -* Add `params.authentication` type, remove `hook.connection` type ([#1732](https://github.com/feathersjs/feathers/issues/1732)) ([d46b7b2](https://github.com/feathersjs/feathers/commit/d46b7b2abac8862c0e4dbfce20d71b8b8a96692f)) - +- Add `params.authentication` type, remove `hook.connection` type ([#1732](https://github.com/feathersjs/feathers/issues/1732)) ([d46b7b2](https://github.com/feathersjs/feathers/commit/d46b7b2abac8862c0e4dbfce20d71b8b8a96692f)) ### Features -* **authentication-oauth:** Set oAuth redirect URL dynamically and pass query the service ([#1737](https://github.com/feathersjs/feathers/issues/1737)) ([0b05f0b](https://github.com/feathersjs/feathers/commit/0b05f0b58a257820fa61d695a36f36455209f6a1)) -* **rest-client:** Allow for customising rest clients ([#1780](https://github.com/feathersjs/feathers/issues/1780)) ([c5cfec7](https://github.com/feathersjs/feathers/commit/c5cfec7a4aafcaffaab0cdacb9b5d297ff20320f)) - - - - +- **authentication-oauth:** Set oAuth redirect URL dynamically and pass query the service ([#1737](https://github.com/feathersjs/feathers/issues/1737)) ([0b05f0b](https://github.com/feathersjs/feathers/commit/0b05f0b58a257820fa61d695a36f36455209f6a1)) +- **rest-client:** Allow for customising rest clients ([#1780](https://github.com/feathersjs/feathers/issues/1780)) ([c5cfec7](https://github.com/feathersjs/feathers/commit/c5cfec7a4aafcaffaab0cdacb9b5d297ff20320f)) ## [4.4.3](https://github.com/feathersjs/feathers/compare/v4.4.1...v4.4.3) (2019-12-06) - ### Bug Fixes -* **adapter-commons:** Filter arrays in queries ([#1724](https://github.com/feathersjs/feathers/issues/1724)) ([872b669](https://github.com/feathersjs/feathers/commit/872b66906a806ab92ca41b5f6f504ff0af1ce79e)) - - - - +- **adapter-commons:** Filter arrays in queries ([#1724](https://github.com/feathersjs/feathers/issues/1724)) ([872b669](https://github.com/feathersjs/feathers/commit/872b66906a806ab92ca41b5f6f504ff0af1ce79e)) ## [4.4.1](https://github.com/feathersjs/feathers/compare/v4.4.0...v4.4.1) (2019-11-27) - ### Bug Fixes -* Gracefully handle errors in publishers ([#1710](https://github.com/feathersjs/feathers/issues/1710)) ([0616306](https://github.com/feathersjs/feathers/commit/061630696762e9dbf1dc4e738094992ba16989fc)) - - - - +- Gracefully handle errors in publishers ([#1710](https://github.com/feathersjs/feathers/issues/1710)) ([0616306](https://github.com/feathersjs/feathers/commit/061630696762e9dbf1dc4e738094992ba16989fc)) # [4.4.0](https://github.com/feathersjs/feathers/compare/v4.3.11...v4.4.0) (2019-11-27) - ### Bug Fixes -* **authentication-client:** Reset authentication promise on socket disconnect ([#1696](https://github.com/feathersjs/feathers/issues/1696)) ([3951626](https://github.com/feathersjs/feathers/commit/395162633ff22e95833a3c2900cb9464bb5b056f)) -* **core:** Improve hook missing parameter message by adding the service name ([#1703](https://github.com/feathersjs/feathers/issues/1703)) ([2331c2a](https://github.com/feathersjs/feathers/commit/2331c2a3dd70d432db7d62a76ed805d359cbbba5)) -* **rest-client:** Allow to customize getting the query ([#1594](https://github.com/feathersjs/feathers/issues/1594)) ([5f21272](https://github.com/feathersjs/feathers/commit/5f212729849414c4da6f0d51edd1986feca992ee)) -* **transport-commons:** Allow to properly chain SocketIo client.off ([#1706](https://github.com/feathersjs/feathers/issues/1706)) ([a4aecbc](https://github.com/feathersjs/feathers/commit/a4aecbcd3578c1cf4ecffb3a58fb6d26e15ee513)) -* **typescript:** Allow specific service typings for `Hook` and `HookContext` ([#1688](https://github.com/feathersjs/feathers/issues/1688)) ([f5d0ddd](https://github.com/feathersjs/feathers/commit/f5d0ddd9724bf5778355535d2103d59daaad6294)) - +- **authentication-client:** Reset authentication promise on socket disconnect ([#1696](https://github.com/feathersjs/feathers/issues/1696)) ([3951626](https://github.com/feathersjs/feathers/commit/395162633ff22e95833a3c2900cb9464bb5b056f)) +- **core:** Improve hook missing parameter message by adding the service name ([#1703](https://github.com/feathersjs/feathers/issues/1703)) ([2331c2a](https://github.com/feathersjs/feathers/commit/2331c2a3dd70d432db7d62a76ed805d359cbbba5)) +- **rest-client:** Allow to customize getting the query ([#1594](https://github.com/feathersjs/feathers/issues/1594)) ([5f21272](https://github.com/feathersjs/feathers/commit/5f212729849414c4da6f0d51edd1986feca992ee)) +- **transport-commons:** Allow to properly chain SocketIo client.off ([#1706](https://github.com/feathersjs/feathers/issues/1706)) ([a4aecbc](https://github.com/feathersjs/feathers/commit/a4aecbcd3578c1cf4ecffb3a58fb6d26e15ee513)) +- **typescript:** Allow specific service typings for `Hook` and `HookContext` ([#1688](https://github.com/feathersjs/feathers/issues/1688)) ([f5d0ddd](https://github.com/feathersjs/feathers/commit/f5d0ddd9724bf5778355535d2103d59daaad6294)) ### Features -* **authentication:** Add parseStrategies to allow separate strategies for creating JWTs and parsing headers ([#1708](https://github.com/feathersjs/feathers/issues/1708)) ([5e65629](https://github.com/feathersjs/feathers/commit/5e65629b924724c3e81d7c81df047e123d1c8bd7)) -* **authentication-oauth:** Set oAuth redirect URL dynamically ([#1608](https://github.com/feathersjs/feathers/issues/1608)) ([1293e08](https://github.com/feathersjs/feathers/commit/1293e088abbb3d23f4a44680836645a8049ceaae)) - - - - +- **authentication:** Add parseStrategies to allow separate strategies for creating JWTs and parsing headers ([#1708](https://github.com/feathersjs/feathers/issues/1708)) ([5e65629](https://github.com/feathersjs/feathers/commit/5e65629b924724c3e81d7c81df047e123d1c8bd7)) +- **authentication-oauth:** Set oAuth redirect URL dynamically ([#1608](https://github.com/feathersjs/feathers/issues/1608)) ([1293e08](https://github.com/feathersjs/feathers/commit/1293e088abbb3d23f4a44680836645a8049ceaae)) ## [4.3.11](https://github.com/feathersjs/feathers/compare/v4.3.10...v4.3.11) (2019-11-11) - ### Bug Fixes -* **authentication:** Retain object references in authenticate hook ([#1675](https://github.com/feathersjs/feathers/issues/1675)) ([e1939be](https://github.com/feathersjs/feathers/commit/e1939be19d4e79d3f5e2fe69ba894a11c627ae99)) -* **authentication-oauth:** Allow hash based redirects ([#1676](https://github.com/feathersjs/feathers/issues/1676)) ([ffe7cf3](https://github.com/feathersjs/feathers/commit/ffe7cf3fbb4e62d7689065cf7b61f25f602ce8cf)) - - - - +- **authentication:** Retain object references in authenticate hook ([#1675](https://github.com/feathersjs/feathers/issues/1675)) ([e1939be](https://github.com/feathersjs/feathers/commit/e1939be19d4e79d3f5e2fe69ba894a11c627ae99)) +- **authentication-oauth:** Allow hash based redirects ([#1676](https://github.com/feathersjs/feathers/issues/1676)) ([ffe7cf3](https://github.com/feathersjs/feathers/commit/ffe7cf3fbb4e62d7689065cf7b61f25f602ce8cf)) ## [4.3.10](https://github.com/feathersjs/feathers/compare/v4.3.9...v4.3.10) (2019-10-26) **Note:** Version bump only for package feathers - - - - ## [4.3.9](https://github.com/feathersjs/feathers/compare/v4.3.8...v4.3.9) (2019-10-26) - ### Bug Fixes -* Add jsonwebtoken TypeScript type dependency ([317c80a](https://github.com/feathersjs/feathers/commit/317c80a9205e8853bb830a12c3aa1a19e95f9abc)) -* Only initialize default Express session if oAuth is actually used ([#1648](https://github.com/feathersjs/feathers/issues/1648)) ([9b9b43f](https://github.com/feathersjs/feathers/commit/9b9b43ff09af1080e4aaa537064bac37b881c9a2)) -* Small type improvements ([#1624](https://github.com/feathersjs/feathers/issues/1624)) ([50162c6](https://github.com/feathersjs/feathers/commit/50162c6e562f0a47c6a280c4f01fff7c3afee293)) - - - - +- Add jsonwebtoken TypeScript type dependency ([317c80a](https://github.com/feathersjs/feathers/commit/317c80a9205e8853bb830a12c3aa1a19e95f9abc)) +- Only initialize default Express session if oAuth is actually used ([#1648](https://github.com/feathersjs/feathers/issues/1648)) ([9b9b43f](https://github.com/feathersjs/feathers/commit/9b9b43ff09af1080e4aaa537064bac37b881c9a2)) +- Small type improvements ([#1624](https://github.com/feathersjs/feathers/issues/1624)) ([50162c6](https://github.com/feathersjs/feathers/commit/50162c6e562f0a47c6a280c4f01fff7c3afee293)) ## [4.3.8](https://github.com/feathersjs/feathers/compare/v4.3.7...v4.3.8) (2019-10-14) - ### Bug Fixes -* Remove adapter commons type alternatives ([#1620](https://github.com/feathersjs/feathers/issues/1620)) ([c9f3086](https://github.com/feathersjs/feathers/commit/c9f3086344420b57dbce7c4169cf550c97509f0d)) - - - - +- Remove adapter commons type alternatives ([#1620](https://github.com/feathersjs/feathers/issues/1620)) ([c9f3086](https://github.com/feathersjs/feathers/commit/c9f3086344420b57dbce7c4169cf550c97509f0d)) ## [4.3.7](https://github.com/feathersjs/feathers/compare/v4.3.6...v4.3.7) (2019-10-14) - ### Bug Fixes -* Improve authentication client default storage initialization ([#1613](https://github.com/feathersjs/feathers/issues/1613)) ([d7f5107](https://github.com/feathersjs/feathers/commit/d7f5107ef76297b4ca6db580afc5e2b372f5ee4d)) -* improve Service and AdapterService types ([#1567](https://github.com/feathersjs/feathers/issues/1567)) ([baad6a2](https://github.com/feathersjs/feathers/commit/baad6a26f0f543b712ccb40359b3933ad3a21392)) -* make __hooks writable and configurable ([#1520](https://github.com/feathersjs/feathers/issues/1520)) ([1c6c374](https://github.com/feathersjs/feathers/commit/1c6c3742ecf1cb813be56074da89e6736d03ffe8)) -* Typings for express request and response properties ([#1609](https://github.com/feathersjs/feathers/issues/1609)) ([38cf8c9](https://github.com/feathersjs/feathers/commit/38cf8c950c1a4fb4a6d78d68d70e7fdd63b71c3c)) - - - - +- Improve authentication client default storage initialization ([#1613](https://github.com/feathersjs/feathers/issues/1613)) ([d7f5107](https://github.com/feathersjs/feathers/commit/d7f5107ef76297b4ca6db580afc5e2b372f5ee4d)) +- improve Service and AdapterService types ([#1567](https://github.com/feathersjs/feathers/issues/1567)) ([baad6a2](https://github.com/feathersjs/feathers/commit/baad6a26f0f543b712ccb40359b3933ad3a21392)) +- make \_\_hooks writable and configurable ([#1520](https://github.com/feathersjs/feathers/issues/1520)) ([1c6c374](https://github.com/feathersjs/feathers/commit/1c6c3742ecf1cb813be56074da89e6736d03ffe8)) +- Typings for express request and response properties ([#1609](https://github.com/feathersjs/feathers/issues/1609)) ([38cf8c9](https://github.com/feathersjs/feathers/commit/38cf8c950c1a4fb4a6d78d68d70e7fdd63b71c3c)) ## [4.3.6](https://github.com/feathersjs/feathers/compare/v4.3.5...v4.3.6) (2019-10-07) - ### Bug Fixes -* Check query for NaN ([#1607](https://github.com/feathersjs/feathers/issues/1607)) ([f1a781f](https://github.com/feathersjs/feathers/commit/f1a781f)) - - - - +- Check query for NaN ([#1607](https://github.com/feathersjs/feathers/issues/1607)) ([f1a781f](https://github.com/feathersjs/feathers/commit/f1a781f)) ## [4.3.5](https://github.com/feathersjs/feathers/compare/v4.3.4...v4.3.5) (2019-10-07) - ### Bug Fixes -* Authentication type improvements and timeout fix ([#1605](https://github.com/feathersjs/feathers/issues/1605)) ([19854d3](https://github.com/feathersjs/feathers/commit/19854d3)) -* Change this reference in client libraries to explicitly passed app ([#1597](https://github.com/feathersjs/feathers/issues/1597)) ([4e4d10a](https://github.com/feathersjs/feathers/commit/4e4d10a)) -* Improve error message when authentication strategy is not allowed ([#1600](https://github.com/feathersjs/feathers/issues/1600)) ([317a312](https://github.com/feathersjs/feathers/commit/317a312)) - - - - +- Authentication type improvements and timeout fix ([#1605](https://github.com/feathersjs/feathers/issues/1605)) ([19854d3](https://github.com/feathersjs/feathers/commit/19854d3)) +- Change this reference in client libraries to explicitly passed app ([#1597](https://github.com/feathersjs/feathers/issues/1597)) ([4e4d10a](https://github.com/feathersjs/feathers/commit/4e4d10a)) +- Improve error message when authentication strategy is not allowed ([#1600](https://github.com/feathersjs/feathers/issues/1600)) ([317a312](https://github.com/feathersjs/feathers/commit/317a312)) ## [4.3.4](https://github.com/feathersjs/feathers/compare/v4.3.3...v4.3.4) (2019-10-03) - ### Bug Fixes -* Reset version number after every publish ([#1596](https://github.com/feathersjs/feathers/issues/1596)) ([f24f82f](https://github.com/feathersjs/feathers/commit/f24f82f)) -* Typing improvements ([#1580](https://github.com/feathersjs/feathers/issues/1580)) ([7818aec](https://github.com/feathersjs/feathers/commit/7818aec)) - - - - +- Reset version number after every publish ([#1596](https://github.com/feathersjs/feathers/issues/1596)) ([f24f82f](https://github.com/feathersjs/feathers/commit/f24f82f)) +- Typing improvements ([#1580](https://github.com/feathersjs/feathers/issues/1580)) ([7818aec](https://github.com/feathersjs/feathers/commit/7818aec)) ## [4.3.3](https://github.com/feathersjs/feathers/compare/v4.3.2...v4.3.3) (2019-09-21) - ### Bug Fixes -* check for undefined access token ([#1571](https://github.com/feathersjs/feathers/issues/1571)) ([976369d](https://github.com/feathersjs/feathers/commit/976369d)) -* Small improvements in dependencies and code sturcture ([#1562](https://github.com/feathersjs/feathers/issues/1562)) ([42c13e2](https://github.com/feathersjs/feathers/commit/42c13e2)) - - - - +- check for undefined access token ([#1571](https://github.com/feathersjs/feathers/issues/1571)) ([976369d](https://github.com/feathersjs/feathers/commit/976369d)) +- Small improvements in dependencies and code sturcture ([#1562](https://github.com/feathersjs/feathers/issues/1562)) ([42c13e2](https://github.com/feathersjs/feathers/commit/42c13e2)) ## [4.3.2](https://github.com/feathersjs/feathers/compare/v4.3.1...v4.3.2) (2019-09-16) - ### Bug Fixes -* Add info to express error handler logger type ([#1557](https://github.com/feathersjs/feathers/issues/1557)) ([3e1d26c](https://github.com/feathersjs/feathers/commit/3e1d26c)) -* LocalStrategy authenticates without username ([#1560](https://github.com/feathersjs/feathers/issues/1560)) ([2b258fd](https://github.com/feathersjs/feathers/commit/2b258fd)), closes [#1559](https://github.com/feathersjs/feathers/issues/1559) - - - - +- Add info to express error handler logger type ([#1557](https://github.com/feathersjs/feathers/issues/1557)) ([3e1d26c](https://github.com/feathersjs/feathers/commit/3e1d26c)) +- LocalStrategy authenticates without username ([#1560](https://github.com/feathersjs/feathers/issues/1560)) ([2b258fd](https://github.com/feathersjs/feathers/commit/2b258fd)), closes [#1559](https://github.com/feathersjs/feathers/issues/1559) ## [4.3.1](https://github.com/feathersjs/feathers/compare/v4.3.0...v4.3.1) (2019-09-09) - ### Bug Fixes -* Fix regression in transport commons ([#1551](https://github.com/feathersjs/feathers/issues/1551)) ([ed9e934](https://github.com/feathersjs/feathers/commit/ed9e934)) -* Omit standard protocol ports from the default hostname ([#1543](https://github.com/feathersjs/feathers/issues/1543)) ([ef16d29](https://github.com/feathersjs/feathers/commit/ef16d29)) -* Use long-timeout for JWT expiration timers ([#1552](https://github.com/feathersjs/feathers/issues/1552)) ([65637ec](https://github.com/feathersjs/feathers/commit/65637ec)) - - - - +- Fix regression in transport commons ([#1551](https://github.com/feathersjs/feathers/issues/1551)) ([ed9e934](https://github.com/feathersjs/feathers/commit/ed9e934)) +- Omit standard protocol ports from the default hostname ([#1543](https://github.com/feathersjs/feathers/issues/1543)) ([ef16d29](https://github.com/feathersjs/feathers/commit/ef16d29)) +- Use long-timeout for JWT expiration timers ([#1552](https://github.com/feathersjs/feathers/issues/1552)) ([65637ec](https://github.com/feathersjs/feathers/commit/65637ec)) # [4.3.0](https://github.com/feathersjs/feathers/compare/v4.3.0-pre.4...v4.3.0) (2019-08-27) - ### Bug Fixes -* Only remove token on NotAuthenticated error in authentication client and handle error better ([#1525](https://github.com/feathersjs/feathers/issues/1525)) ([13a8758](https://github.com/feathersjs/feathers/commit/13a8758)) - - - - +- Only remove token on NotAuthenticated error in authentication client and handle error better ([#1525](https://github.com/feathersjs/feathers/issues/1525)) ([13a8758](https://github.com/feathersjs/feathers/commit/13a8758)) # [4.3.0-pre.4](https://github.com/feathersjs/feathers/compare/v4.3.0-pre.3...v4.3.0-pre.4) (2019-08-22) - ### Bug Fixes -* Fix auth publisher mistake ([08bad61](https://github.com/feathersjs/feathers/commit/08bad61)) - - - - +- Fix auth publisher mistake ([08bad61](https://github.com/feathersjs/feathers/commit/08bad61)) # [4.3.0-pre.3](https://github.com/feathersjs/feathers/compare/v4.3.0-pre.2...v4.3.0-pre.3) (2019-08-19) - ### Bug Fixes -* Expire and remove authenticated real-time connections ([#1512](https://github.com/feathersjs/feathers/issues/1512)) ([2707c33](https://github.com/feathersjs/feathers/commit/2707c33)) -* Update all dependencies ([7d53a00](https://github.com/feathersjs/feathers/commit/7d53a00)) -* Use WeakMap to connect socket to connection ([#1509](https://github.com/feathersjs/feathers/issues/1509)) ([64807e3](https://github.com/feathersjs/feathers/commit/64807e3)) - +- Expire and remove authenticated real-time connections ([#1512](https://github.com/feathersjs/feathers/issues/1512)) ([2707c33](https://github.com/feathersjs/feathers/commit/2707c33)) +- Update all dependencies ([7d53a00](https://github.com/feathersjs/feathers/commit/7d53a00)) +- Use WeakMap to connect socket to connection ([#1509](https://github.com/feathersjs/feathers/issues/1509)) ([64807e3](https://github.com/feathersjs/feathers/commit/64807e3)) ### Features -* Let strategies handle the connection ([#1510](https://github.com/feathersjs/feathers/issues/1510)) ([4329feb](https://github.com/feathersjs/feathers/commit/4329feb)) - - - - +- Let strategies handle the connection ([#1510](https://github.com/feathersjs/feathers/issues/1510)) ([4329feb](https://github.com/feathersjs/feathers/commit/4329feb)) # [4.3.0-pre.2](https://github.com/feathersjs/feathers/compare/v4.3.0-pre.1...v4.3.0-pre.2) (2019-08-02) - ### Bug Fixes -* @feathersjs/adapter-commons: `update` id is non-nullable ([#1468](https://github.com/feathersjs/feathers/issues/1468)) ([43ec802](https://github.com/feathersjs/feathers/commit/43ec802)) -* Add getEntityId to JWT strategy and fix legacy Socket authentication ([#1488](https://github.com/feathersjs/feathers/issues/1488)) ([9a3b324](https://github.com/feathersjs/feathers/commit/9a3b324)) -* Add method to reliably get default authentication service ([#1470](https://github.com/feathersjs/feathers/issues/1470)) ([e542cb3](https://github.com/feathersjs/feathers/commit/e542cb3)) -* Do not error in authentication client on logout ([#1473](https://github.com/feathersjs/feathers/issues/1473)) ([8211b98](https://github.com/feathersjs/feathers/commit/8211b98)) -* Improve Params typing ([#1474](https://github.com/feathersjs/feathers/issues/1474)) ([54a3aa7](https://github.com/feathersjs/feathers/commit/54a3aa7)) - - - - +- @feathersjs/adapter-commons: `update` id is non-nullable ([#1468](https://github.com/feathersjs/feathers/issues/1468)) ([43ec802](https://github.com/feathersjs/feathers/commit/43ec802)) +- Add getEntityId to JWT strategy and fix legacy Socket authentication ([#1488](https://github.com/feathersjs/feathers/issues/1488)) ([9a3b324](https://github.com/feathersjs/feathers/commit/9a3b324)) +- Add method to reliably get default authentication service ([#1470](https://github.com/feathersjs/feathers/issues/1470)) ([e542cb3](https://github.com/feathersjs/feathers/commit/e542cb3)) +- Do not error in authentication client on logout ([#1473](https://github.com/feathersjs/feathers/issues/1473)) ([8211b98](https://github.com/feathersjs/feathers/commit/8211b98)) +- Improve Params typing ([#1474](https://github.com/feathersjs/feathers/issues/1474)) ([54a3aa7](https://github.com/feathersjs/feathers/commit/54a3aa7)) # [4.3.0-pre.1](https://github.com/feathersjs/feathers/compare/v4.0.0-pre.5...v4.3.0-pre.1) (2019-07-11) **Note:** Version bump only for package feathers - - - - # [4.0.0-pre.5](https://github.com/feathersjs/feathers/compare/v4.0.0-pre.4...v4.0.0-pre.5) (2019-07-10) - ### Bug Fixes -* Fix feathers-memory dependency that did not get updated ([9422b13](https://github.com/feathersjs/feathers/commit/9422b13)) -* Remove unnecessary top level export files in @feathersjs/express ([#1442](https://github.com/feathersjs/feathers/issues/1442)) ([73c3fb2](https://github.com/feathersjs/feathers/commit/73c3fb2)) - +- Fix feathers-memory dependency that did not get updated ([9422b13](https://github.com/feathersjs/feathers/commit/9422b13)) +- Remove unnecessary top level export files in @feathersjs/express ([#1442](https://github.com/feathersjs/feathers/issues/1442)) ([73c3fb2](https://github.com/feathersjs/feathers/commit/73c3fb2)) ### Features -* @feathersjs/express allow to pass an existing Express application instance ([#1446](https://github.com/feathersjs/feathers/issues/1446)) ([853a6b0](https://github.com/feathersjs/feathers/commit/853a6b0)) - - - - +- @feathersjs/express allow to pass an existing Express application instance ([#1446](https://github.com/feathersjs/feathers/issues/1446)) ([853a6b0](https://github.com/feathersjs/feathers/commit/853a6b0)) # [4.0.0-pre.4](https://github.com/feathersjs/feathers/compare/v4.0.0-pre.3...v4.0.0-pre.4) (2019-07-05) - ### Bug Fixes -* @feathersjs/adapter-commons: remove data from `remove` arguments ([#1426](https://github.com/feathersjs/feathers/issues/1426)) ([fd54ae9](https://github.com/feathersjs/feathers/commit/fd54ae9)) -* @feathersjs/express: allow middleware arrays ([#1421](https://github.com/feathersjs/feathers/issues/1421)) ([b605ab8](https://github.com/feathersjs/feathers/commit/b605ab8)) -* @feathersjs/express: replace `reduce` with `map` ([#1429](https://github.com/feathersjs/feathers/issues/1429)) ([44542e9](https://github.com/feathersjs/feathers/commit/44542e9)) -* Clean up hooks code ([#1407](https://github.com/feathersjs/feathers/issues/1407)) ([f25c88b](https://github.com/feathersjs/feathers/commit/f25c88b)) -* Fix @feathersjs/feathers typings http import ([abbc07b](https://github.com/feathersjs/feathers/commit/abbc07b)) -* Fix OpenCollective link ([28888a1](https://github.com/feathersjs/feathers/commit/28888a1)) -* Improve transport-commons types ([#1396](https://github.com/feathersjs/feathers/issues/1396)) ([f9d8536](https://github.com/feathersjs/feathers/commit/f9d8536)) -* Updated typings for ServiceMethods ([#1409](https://github.com/feathersjs/feathers/issues/1409)) ([b5ee7e2](https://github.com/feathersjs/feathers/commit/b5ee7e2)) - +- @feathersjs/adapter-commons: remove data from `remove` arguments ([#1426](https://github.com/feathersjs/feathers/issues/1426)) ([fd54ae9](https://github.com/feathersjs/feathers/commit/fd54ae9)) +- @feathersjs/express: allow middleware arrays ([#1421](https://github.com/feathersjs/feathers/issues/1421)) ([b605ab8](https://github.com/feathersjs/feathers/commit/b605ab8)) +- @feathersjs/express: replace `reduce` with `map` ([#1429](https://github.com/feathersjs/feathers/issues/1429)) ([44542e9](https://github.com/feathersjs/feathers/commit/44542e9)) +- Clean up hooks code ([#1407](https://github.com/feathersjs/feathers/issues/1407)) ([f25c88b](https://github.com/feathersjs/feathers/commit/f25c88b)) +- Fix @feathersjs/feathers typings http import ([abbc07b](https://github.com/feathersjs/feathers/commit/abbc07b)) +- Fix OpenCollective link ([28888a1](https://github.com/feathersjs/feathers/commit/28888a1)) +- Improve transport-commons types ([#1396](https://github.com/feathersjs/feathers/issues/1396)) ([f9d8536](https://github.com/feathersjs/feathers/commit/f9d8536)) +- Updated typings for ServiceMethods ([#1409](https://github.com/feathersjs/feathers/issues/1409)) ([b5ee7e2](https://github.com/feathersjs/feathers/commit/b5ee7e2)) ### Features -* adapter-commons: add `allowsMulti(method)` to AdapterService ([#1431](https://github.com/feathersjs/feathers/issues/1431)) ([e688851](https://github.com/feathersjs/feathers/commit/e688851)) -* Add hook-less methods and service option types to adapter-commons ([#1433](https://github.com/feathersjs/feathers/issues/1433)) ([857f54a](https://github.com/feathersjs/feathers/commit/857f54a)) - - - - +- adapter-commons: add `allowsMulti(method)` to AdapterService ([#1431](https://github.com/feathersjs/feathers/issues/1431)) ([e688851](https://github.com/feathersjs/feathers/commit/e688851)) +- Add hook-less methods and service option types to adapter-commons ([#1433](https://github.com/feathersjs/feathers/issues/1433)) ([857f54a](https://github.com/feathersjs/feathers/commit/857f54a)) # [4.0.0-pre.3](https://github.com/feathersjs/feathers/compare/v4.0.0-pre.2...v4.0.0-pre.3) (2019-06-01) - ### Bug Fixes -* Make oAuth paths more consistent and improve authentication client ([#1377](https://github.com/feathersjs/feathers/issues/1377)) ([adb2543](https://github.com/feathersjs/feathers/commit/adb2543)) -* Set authenticated: true after successful authentication ([#1367](https://github.com/feathersjs/feathers/issues/1367)) ([9918cff](https://github.com/feathersjs/feathers/commit/9918cff)) -* Typings fix and improvements. ([#1364](https://github.com/feathersjs/feathers/issues/1364)) ([515b916](https://github.com/feathersjs/feathers/commit/515b916)) -* Update dependencies and fix tests ([#1373](https://github.com/feathersjs/feathers/issues/1373)) ([d743a7f](https://github.com/feathersjs/feathers/commit/d743a7f)) - - - - +- Make oAuth paths more consistent and improve authentication client ([#1377](https://github.com/feathersjs/feathers/issues/1377)) ([adb2543](https://github.com/feathersjs/feathers/commit/adb2543)) +- Set authenticated: true after successful authentication ([#1367](https://github.com/feathersjs/feathers/issues/1367)) ([9918cff](https://github.com/feathersjs/feathers/commit/9918cff)) +- Typings fix and improvements. ([#1364](https://github.com/feathersjs/feathers/issues/1364)) ([515b916](https://github.com/feathersjs/feathers/commit/515b916)) +- Update dependencies and fix tests ([#1373](https://github.com/feathersjs/feathers/issues/1373)) ([d743a7f](https://github.com/feathersjs/feathers/commit/d743a7f)) # [4.0.0-pre.2](https://github.com/feathersjs/feathers/compare/v4.0.0-pre.1...v4.0.0-pre.2) (2019-05-15) - ### Bug Fixes -* Throw NotAuthenticated on token verification errors ([#1357](https://github.com/feathersjs/feathers/issues/1357)) ([e0120df](https://github.com/feathersjs/feathers/commit/e0120df)) -* **typescript:** finally should be optional ([#1350](https://github.com/feathersjs/feathers/issues/1350)) ([f439a9e](https://github.com/feathersjs/feathers/commit/f439a9e)) -* Add fallback for legacy socket authenticate event ([#1356](https://github.com/feathersjs/feathers/issues/1356)) ([61b1056](https://github.com/feathersjs/feathers/commit/61b1056)) -* Correctly read the oauth strategy config ([#1349](https://github.com/feathersjs/feathers/issues/1349)) ([9abf314](https://github.com/feathersjs/feathers/commit/9abf314)) -* Fix versioning tests. Closes [#1346](https://github.com/feathersjs/feathers/issues/1346) ([dd519f6](https://github.com/feathersjs/feathers/commit/dd519f6)) -* Use `export =` in TypeScript definitions ([#1285](https://github.com/feathersjs/feathers/issues/1285)) ([12d0f4b](https://github.com/feathersjs/feathers/commit/12d0f4b)) - +- Throw NotAuthenticated on token verification errors ([#1357](https://github.com/feathersjs/feathers/issues/1357)) ([e0120df](https://github.com/feathersjs/feathers/commit/e0120df)) +- **typescript:** finally should be optional ([#1350](https://github.com/feathersjs/feathers/issues/1350)) ([f439a9e](https://github.com/feathersjs/feathers/commit/f439a9e)) +- Add fallback for legacy socket authenticate event ([#1356](https://github.com/feathersjs/feathers/issues/1356)) ([61b1056](https://github.com/feathersjs/feathers/commit/61b1056)) +- Correctly read the oauth strategy config ([#1349](https://github.com/feathersjs/feathers/issues/1349)) ([9abf314](https://github.com/feathersjs/feathers/commit/9abf314)) +- Fix versioning tests. Closes [#1346](https://github.com/feathersjs/feathers/issues/1346) ([dd519f6](https://github.com/feathersjs/feathers/commit/dd519f6)) +- Use `export =` in TypeScript definitions ([#1285](https://github.com/feathersjs/feathers/issues/1285)) ([12d0f4b](https://github.com/feathersjs/feathers/commit/12d0f4b)) ### Features -* Add global disconnect event ([#1355](https://github.com/feathersjs/feathers/issues/1355)) ([85afcca](https://github.com/feathersjs/feathers/commit/85afcca)) - - - - +- Add global disconnect event ([#1355](https://github.com/feathersjs/feathers/issues/1355)) ([85afcca](https://github.com/feathersjs/feathers/commit/85afcca)) # [4.0.0-pre.1](https://github.com/feathersjs/feathers/compare/v4.0.0-pre.0...v4.0.0-pre.1) (2019-05-08) - ### Bug Fixes -* Add registerPublisher alias for .publish ([#1302](https://github.com/feathersjs/feathers/issues/1302)) ([98fe8f8](https://github.com/feathersjs/feathers/commit/98fe8f8)) -* Always require strategy parameter in authentication ([#1327](https://github.com/feathersjs/feathers/issues/1327)) ([d4a8021](https://github.com/feathersjs/feathers/commit/d4a8021)) -* Bring back params.authenticated ([#1317](https://github.com/feathersjs/feathers/issues/1317)) ([a0ffd5e](https://github.com/feathersjs/feathers/commit/a0ffd5e)) -* Do not log as errors below a 500 response ([#1256](https://github.com/feathersjs/feathers/issues/1256)) ([33fd0e4](https://github.com/feathersjs/feathers/commit/33fd0e4)) -* Guard against null in client side logout function ([#1319](https://github.com/feathersjs/feathers/issues/1319)) ([fa7f057](https://github.com/feathersjs/feathers/commit/fa7f057)) -* Handle error oAuth redirect in authentication client ([#1307](https://github.com/feathersjs/feathers/issues/1307)) ([12d48ee](https://github.com/feathersjs/feathers/commit/12d48ee)) -* Improve authentication parameter handling ([#1333](https://github.com/feathersjs/feathers/issues/1333)) ([6e77204](https://github.com/feathersjs/feathers/commit/6e77204)) -* Improve oAuth option handling and usability ([#1335](https://github.com/feathersjs/feathers/issues/1335)) ([adb137d](https://github.com/feathersjs/feathers/commit/adb137d)) -* Merge httpStrategies and authStrategies option ([#1308](https://github.com/feathersjs/feathers/issues/1308)) ([afa4d55](https://github.com/feathersjs/feathers/commit/afa4d55)) -* Rename jwtStrategies option to authStrategies ([#1305](https://github.com/feathersjs/feathers/issues/1305)) ([4aee151](https://github.com/feathersjs/feathers/commit/4aee151)) -* Update version number check ([53575c5](https://github.com/feathersjs/feathers/commit/53575c5)) -* Updated HooksObject typings ([#1300](https://github.com/feathersjs/feathers/issues/1300)) ([b28058c](https://github.com/feathersjs/feathers/commit/b28058c)) - +- Add registerPublisher alias for .publish ([#1302](https://github.com/feathersjs/feathers/issues/1302)) ([98fe8f8](https://github.com/feathersjs/feathers/commit/98fe8f8)) +- Always require strategy parameter in authentication ([#1327](https://github.com/feathersjs/feathers/issues/1327)) ([d4a8021](https://github.com/feathersjs/feathers/commit/d4a8021)) +- Bring back params.authenticated ([#1317](https://github.com/feathersjs/feathers/issues/1317)) ([a0ffd5e](https://github.com/feathersjs/feathers/commit/a0ffd5e)) +- Do not log as errors below a 500 response ([#1256](https://github.com/feathersjs/feathers/issues/1256)) ([33fd0e4](https://github.com/feathersjs/feathers/commit/33fd0e4)) +- Guard against null in client side logout function ([#1319](https://github.com/feathersjs/feathers/issues/1319)) ([fa7f057](https://github.com/feathersjs/feathers/commit/fa7f057)) +- Handle error oAuth redirect in authentication client ([#1307](https://github.com/feathersjs/feathers/issues/1307)) ([12d48ee](https://github.com/feathersjs/feathers/commit/12d48ee)) +- Improve authentication parameter handling ([#1333](https://github.com/feathersjs/feathers/issues/1333)) ([6e77204](https://github.com/feathersjs/feathers/commit/6e77204)) +- Improve oAuth option handling and usability ([#1335](https://github.com/feathersjs/feathers/issues/1335)) ([adb137d](https://github.com/feathersjs/feathers/commit/adb137d)) +- Merge httpStrategies and authStrategies option ([#1308](https://github.com/feathersjs/feathers/issues/1308)) ([afa4d55](https://github.com/feathersjs/feathers/commit/afa4d55)) +- Rename jwtStrategies option to authStrategies ([#1305](https://github.com/feathersjs/feathers/issues/1305)) ([4aee151](https://github.com/feathersjs/feathers/commit/4aee151)) +- Update version number check ([53575c5](https://github.com/feathersjs/feathers/commit/53575c5)) +- Updated HooksObject typings ([#1300](https://github.com/feathersjs/feathers/issues/1300)) ([b28058c](https://github.com/feathersjs/feathers/commit/b28058c)) ### Features -* Add params.headers to all transports when available ([#1303](https://github.com/feathersjs/feathers/issues/1303)) ([ebce79b](https://github.com/feathersjs/feathers/commit/ebce79b)) -* Change and *JWT methods to *accessToken ([#1304](https://github.com/feathersjs/feathers/issues/1304)) ([5ac826b](https://github.com/feathersjs/feathers/commit/5ac826b)) -* express use service.methods ([#945](https://github.com/feathersjs/feathers/issues/945)) ([3f0b1c3](https://github.com/feathersjs/feathers/commit/3f0b1c3)) - - - - +- Add params.headers to all transports when available ([#1303](https://github.com/feathersjs/feathers/issues/1303)) ([ebce79b](https://github.com/feathersjs/feathers/commit/ebce79b)) +- Change and *JWT methods to *accessToken ([#1304](https://github.com/feathersjs/feathers/issues/1304)) ([5ac826b](https://github.com/feathersjs/feathers/commit/5ac826b)) +- express use service.methods ([#945](https://github.com/feathersjs/feathers/issues/945)) ([3f0b1c3](https://github.com/feathersjs/feathers/commit/3f0b1c3)) # [4.0.0-pre.0](https://github.com/feathersjs/feathers/compare/v3.2.0-pre.1...v4.0.0-pre.0) (2019-04-21) - ### Bug Fixes -* Add test to make sure different id in adapter query works ([#1165](https://github.com/feathersjs/feathers/issues/1165)) ([0ba4580](https://github.com/feathersjs/feathers/commit/0ba4580)) -* Add whitelist and filter support to common adapter service ([#1132](https://github.com/feathersjs/feathers/issues/1132)) ([df1daaa](https://github.com/feathersjs/feathers/commit/df1daaa)) -* Added path and method in to express request for passport ([#1112](https://github.com/feathersjs/feathers/issues/1112)) ([afa1cb4](https://github.com/feathersjs/feathers/commit/afa1cb4)) -* Authentication core improvements ([#1260](https://github.com/feathersjs/feathers/issues/1260)) ([c5dc7a2](https://github.com/feathersjs/feathers/commit/c5dc7a2)) -* Catch connection initialization errors ([#1043](https://github.com/feathersjs/feathers/issues/1043)) ([4f9acd6](https://github.com/feathersjs/feathers/commit/4f9acd6)) -* Compare socket event data using lodash's isEqual instead of indexOf ([#1061](https://github.com/feathersjs/feathers/issues/1061)) ([f706db3](https://github.com/feathersjs/feathers/commit/f706db3)) -* Do not inherit app object from Object prototype ([#1153](https://github.com/feathersjs/feathers/issues/1153)) ([ed8c2e4](https://github.com/feathersjs/feathers/commit/ed8c2e4)) -* Fix AdapterService multi option when set to true ([#1134](https://github.com/feathersjs/feathers/issues/1134)) ([40402fc](https://github.com/feathersjs/feathers/commit/40402fc)) -* Improve JWT authentication option handling ([#1261](https://github.com/feathersjs/feathers/issues/1261)) ([31b956b](https://github.com/feathersjs/feathers/commit/31b956b)) -* make codeclimate conform to rule of three ([#1076](https://github.com/feathersjs/feathers/issues/1076)) ([0a2ce87](https://github.com/feathersjs/feathers/commit/0a2ce87)) -* Make Mocha a proper devDependency for every repository ([#1053](https://github.com/feathersjs/feathers/issues/1053)) ([9974803](https://github.com/feathersjs/feathers/commit/9974803)) -* More robust parsing of mongodb connection string. Use new url parser. ([#1002](https://github.com/feathersjs/feathers/issues/1002)) ([74b31df](https://github.com/feathersjs/feathers/commit/74b31df)) -* Normalize params to object even when it is falsy ([#1012](https://github.com/feathersjs/feathers/issues/1012)) ([af97818](https://github.com/feathersjs/feathers/commit/af97818)) -* Only merge authenticated property on update ([8a564f7](https://github.com/feathersjs/feathers/commit/8a564f7)) -* reduce authentication connection hook complexity and remove unnecessary checks ([fa94b2f](https://github.com/feathersjs/feathers/commit/fa94b2f)) -* support a secretProvider ([#1063](https://github.com/feathersjs/feathers/issues/1063)) ([9da26ad](https://github.com/feathersjs/feathers/commit/9da26ad)) -* Support Logger swallowing ([#995](https://github.com/feathersjs/feathers/issues/995)) ([5b3b37e](https://github.com/feathersjs/feathers/commit/5b3b37e)), closes [/github.com/feathersjs/generator-feathers/pull/392#issuecomment-420408312](https://github.com//github.com/feathersjs/generator-feathers/pull/392/issues/issuecomment-420408312) -* Throw error in `filterQuery` when query parameter is unknown ([#1131](https://github.com/feathersjs/feathers/issues/1131)) ([cd1a183](https://github.com/feathersjs/feathers/commit/cd1a183)) -* Update 401.html ([#983](https://github.com/feathersjs/feathers/issues/983)) ([cec6bae](https://github.com/feathersjs/feathers/commit/cec6bae)) -* Update 404.html ([#984](https://github.com/feathersjs/feathers/issues/984)) ([72132d1](https://github.com/feathersjs/feathers/commit/72132d1)) -* Update adapter common tests ([#1135](https://github.com/feathersjs/feathers/issues/1135)) ([8166dda](https://github.com/feathersjs/feathers/commit/8166dda)) -* Update adapter common tests to check for falsy ([#1140](https://github.com/feathersjs/feathers/issues/1140)) ([2856722](https://github.com/feathersjs/feathers/commit/2856722)) -* Update adapter tests to not rely on error instance ([#1202](https://github.com/feathersjs/feathers/issues/1202)) ([6885e0e](https://github.com/feathersjs/feathers/commit/6885e0e)) -* Update all dependencies to latest ([#1206](https://github.com/feathersjs/feathers/issues/1206)) ([e51e0f6](https://github.com/feathersjs/feathers/commit/e51e0f6)) -* **adapter-commons:** Keep Symbols when filtering a query ([#1141](https://github.com/feathersjs/feathers/issues/1141)) ([c9f55d8](https://github.com/feathersjs/feathers/commit/c9f55d8)) -* **authentication:** Fall back when req.app is not the application when emitting events ([#1185](https://github.com/feathersjs/feathers/issues/1185)) ([6a534f0](https://github.com/feathersjs/feathers/commit/6a534f0)) -* **chore:** Add .npmignore to adapter-commons ([8e129d8](https://github.com/feathersjs/feathers/commit/8e129d8)) -* **chore:** Properly configure and run code linter ([#1092](https://github.com/feathersjs/feathers/issues/1092)) ([fd3fc34](https://github.com/feathersjs/feathers/commit/fd3fc34)) -* **chore:** Remove CLI and generators that belong in their own repositories ([#1091](https://github.com/feathersjs/feathers/issues/1091)) ([e894ac8](https://github.com/feathersjs/feathers/commit/e894ac8)) -* **compile-task:** on windows machine ([#60](https://github.com/feathersjs/feathers/issues/60)) ([617e0a4](https://github.com/feathersjs/feathers/commit/617e0a4)) -* **docs/new-features:** syntax highlighting ([#347](https://github.com/feathersjs/feathers/issues/347)) ([4ab7c95](https://github.com/feathersjs/feathers/commit/4ab7c95)) -* **knex:** Fix knex + sql server issues when using authentication generator ([#257](https://github.com/feathersjs/feathers/issues/257)) ([8f8f75f](https://github.com/feathersjs/feathers/commit/8f8f75f)) -* **package:** update @feathersjs/commons to version 2.0.0 ([#31](https://github.com/feathersjs/feathers/issues/31)) ([c1ef5b1](https://github.com/feathersjs/feathers/commit/c1ef5b1)) -* **package:** update @feathersjs/commons to version 2.0.0 ([#692](https://github.com/feathersjs/feathers/issues/692)) ([ca665ab](https://github.com/feathersjs/feathers/commit/ca665ab)) -* **package:** update config to version 3.0.0 ([#1100](https://github.com/feathersjs/feathers/issues/1100)) ([c9f4b42](https://github.com/feathersjs/feathers/commit/c9f4b42)) -* use minimal RegExp matching for better performance ([#977](https://github.com/feathersjs/feathers/issues/977)) ([3ca7e97](https://github.com/feathersjs/feathers/commit/3ca7e97)) -* **package:** update @feathersjs/commons to version 2.0.0 ([#45](https://github.com/feathersjs/feathers/issues/45)) ([9e82595](https://github.com/feathersjs/feathers/commit/9e82595)) -* **package:** update @feathersjs/commons to version 2.0.0 ([#84](https://github.com/feathersjs/feathers/issues/84)) ([78ed39c](https://github.com/feathersjs/feathers/commit/78ed39c)) -* **package:** update debug to version 3.0.0 ([#2](https://github.com/feathersjs/feathers/issues/2)) ([7e19603](https://github.com/feathersjs/feathers/commit/7e19603)) -* **package:** update debug to version 3.0.0 ([#22](https://github.com/feathersjs/feathers/issues/22)) ([0b62606](https://github.com/feathersjs/feathers/commit/0b62606)) -* **package:** update debug to version 3.0.0 ([#30](https://github.com/feathersjs/feathers/issues/30)) ([baf7a00](https://github.com/feathersjs/feathers/commit/baf7a00)) -* **package:** update debug to version 3.0.0 ([#31](https://github.com/feathersjs/feathers/issues/31)) ([902ddf5](https://github.com/feathersjs/feathers/commit/902ddf5)) -* **package:** update debug to version 3.0.0 ([#31](https://github.com/feathersjs/feathers/issues/31)) ([f23d617](https://github.com/feathersjs/feathers/commit/f23d617)) -* **package:** update debug to version 3.0.0 ([#45](https://github.com/feathersjs/feathers/issues/45)) ([2391434](https://github.com/feathersjs/feathers/commit/2391434)) -* **package:** update debug to version 3.0.0 ([#45](https://github.com/feathersjs/feathers/issues/45)) ([9b9bde5](https://github.com/feathersjs/feathers/commit/9b9bde5)) -* **package:** update debug to version 3.0.0 ([#555](https://github.com/feathersjs/feathers/issues/555)) ([f788804](https://github.com/feathersjs/feathers/commit/f788804)) -* **package:** update debug to version 3.0.0 ([#59](https://github.com/feathersjs/feathers/issues/59)) ([fedcf06](https://github.com/feathersjs/feathers/commit/fedcf06)) -* **package:** update debug to version 3.0.0 ([#61](https://github.com/feathersjs/feathers/issues/61)) ([6f5009c](https://github.com/feathersjs/feathers/commit/6f5009c)) -* **package:** update debug to version 3.0.0 ([#83](https://github.com/feathersjs/feathers/issues/83)) ([49f1de9](https://github.com/feathersjs/feathers/commit/49f1de9)) -* **package:** update debug to version 3.0.0 ([#86](https://github.com/feathersjs/feathers/issues/86)) ([fd1bb6b](https://github.com/feathersjs/feathers/commit/fd1bb6b)) -* **package:** update debug to version 3.0.1 ([#46](https://github.com/feathersjs/feathers/issues/46)) ([f8ada69](https://github.com/feathersjs/feathers/commit/f8ada69)) -* **package:** update generator-feathers to version 1.0.3 ([#81](https://github.com/feathersjs/feathers/issues/81)) ([0c66bc5](https://github.com/feathersjs/feathers/commit/0c66bc5)) -* **package:** update generator-feathers to version 1.0.5 ([#83](https://github.com/feathersjs/feathers/issues/83)) ([229caba](https://github.com/feathersjs/feathers/commit/229caba)) -* **package:** update generator-feathers to version 1.0.6 ([#86](https://github.com/feathersjs/feathers/issues/86)) ([7ae8e56](https://github.com/feathersjs/feathers/commit/7ae8e56)) -* **package:** update generator-feathers to version 1.1.0 ([#93](https://github.com/feathersjs/feathers/issues/93)) ([f393e4c](https://github.com/feathersjs/feathers/commit/f393e4c)) -* **package:** update generator-feathers to version 1.1.1 ([#95](https://github.com/feathersjs/feathers/issues/95)) ([3279ba9](https://github.com/feathersjs/feathers/commit/3279ba9)) -* **package:** update generator-feathers to version 1.2.0 ([#96](https://github.com/feathersjs/feathers/issues/96)) ([8eb5674](https://github.com/feathersjs/feathers/commit/8eb5674)) -* **package:** update generator-feathers to version 1.2.10 ([#115](https://github.com/feathersjs/feathers/issues/115)) ([c1db2b2](https://github.com/feathersjs/feathers/commit/c1db2b2)) -* **package:** update generator-feathers to version 1.2.11 ([#116](https://github.com/feathersjs/feathers/issues/116)) ([bba6550](https://github.com/feathersjs/feathers/commit/bba6550)) -* **package:** update generator-feathers to version 1.2.12 ([#119](https://github.com/feathersjs/feathers/issues/119)) ([e5c737d](https://github.com/feathersjs/feathers/commit/e5c737d)) -* **package:** update generator-feathers to version 1.2.2 ([#98](https://github.com/feathersjs/feathers/issues/98)) ([ee629e3](https://github.com/feathersjs/feathers/commit/ee629e3)), closes [#97](https://github.com/feathersjs/feathers/issues/97) -* **package:** update generator-feathers to version 1.2.3 ([#99](https://github.com/feathersjs/feathers/issues/99)) ([b6cf361](https://github.com/feathersjs/feathers/commit/b6cf361)) -* **package:** update generator-feathers to version 1.2.4 ([#101](https://github.com/feathersjs/feathers/issues/101)) ([2182fef](https://github.com/feathersjs/feathers/commit/2182fef)) -* **package:** update generator-feathers to version 1.2.5 ([#104](https://github.com/feathersjs/feathers/issues/104)) ([295f6aa](https://github.com/feathersjs/feathers/commit/295f6aa)) -* **package:** update generator-feathers to version 1.2.6 ([#106](https://github.com/feathersjs/feathers/issues/106)) ([66125dc](https://github.com/feathersjs/feathers/commit/66125dc)) -* **package:** update generator-feathers to version 1.2.9 ([#110](https://github.com/feathersjs/feathers/issues/110)) ([17e55dc](https://github.com/feathersjs/feathers/commit/17e55dc)) -* **package:** update generator-feathers to version 2.0.0 ([#126](https://github.com/feathersjs/feathers/issues/126)) ([eff6627](https://github.com/feathersjs/feathers/commit/eff6627)) -* **package:** update generator-feathers to version 2.1.0 ([#128](https://github.com/feathersjs/feathers/issues/128)) ([b712355](https://github.com/feathersjs/feathers/commit/b712355)) -* **package:** update generator-feathers to version 2.1.1 ([#129](https://github.com/feathersjs/feathers/issues/129)) ([1f91c0b](https://github.com/feathersjs/feathers/commit/1f91c0b)) -* **package:** update generator-feathers to version 2.2.0 ([#130](https://github.com/feathersjs/feathers/issues/130)) ([308ad0b](https://github.com/feathersjs/feathers/commit/308ad0b)) -* **package:** update generator-feathers to version 2.3.0 ([#131](https://github.com/feathersjs/feathers/issues/131)) ([7894807](https://github.com/feathersjs/feathers/commit/7894807)) -* **package:** update generator-feathers to version 2.3.1 ([#132](https://github.com/feathersjs/feathers/issues/132)) ([c3e3187](https://github.com/feathersjs/feathers/commit/c3e3187)) -* **package:** update generator-feathers to version 2.4.0 ([#137](https://github.com/feathersjs/feathers/issues/137)) ([1645d2e](https://github.com/feathersjs/feathers/commit/1645d2e)) -* **package:** update generator-feathers to version 2.4.1 ([#140](https://github.com/feathersjs/feathers/issues/140)) ([e5a5f7c](https://github.com/feathersjs/feathers/commit/e5a5f7c)) -* **package:** update generator-feathers to version 2.4.4 ([#151](https://github.com/feathersjs/feathers/issues/151)) ([3dcd480](https://github.com/feathersjs/feathers/commit/3dcd480)) -* **package:** update generator-feathers to version 2.5.2 ([#155](https://github.com/feathersjs/feathers/issues/155)) ([493ca4b](https://github.com/feathersjs/feathers/commit/493ca4b)) -* **package:** update generator-feathers to version 2.5.3 ([#156](https://github.com/feathersjs/feathers/issues/156)) ([ef570a8](https://github.com/feathersjs/feathers/commit/ef570a8)) -* **package:** update generator-feathers to version 2.5.4 ([#158](https://github.com/feathersjs/feathers/issues/158)) ([787f30c](https://github.com/feathersjs/feathers/commit/787f30c)) -* **package:** update generator-feathers to version 2.5.5 ([#159](https://github.com/feathersjs/feathers/issues/159)) ([bbd1b29](https://github.com/feathersjs/feathers/commit/bbd1b29)) -* **package:** update generator-feathers to version 2.5.6 ([#161](https://github.com/feathersjs/feathers/issues/161)) ([cb72a5c](https://github.com/feathersjs/feathers/commit/cb72a5c)) -* **package:** update generator-feathers to version 2.6.0 ([#164](https://github.com/feathersjs/feathers/issues/164)) ([6212ec9](https://github.com/feathersjs/feathers/commit/6212ec9)) -* **package:** update generator-feathers-plugin to version 0.11.0 ([#105](https://github.com/feathersjs/feathers/issues/105)) ([d40bb75](https://github.com/feathersjs/feathers/commit/d40bb75)) -* **package:** update generator-feathers-plugin to version 0.12.1 ([#112](https://github.com/feathersjs/feathers/issues/112)) ([f374e01](https://github.com/feathersjs/feathers/commit/f374e01)) -* **package:** update generator-feathers-plugin to version 1.0.0 ([#134](https://github.com/feathersjs/feathers/issues/134)) ([ee905b0](https://github.com/feathersjs/feathers/commit/ee905b0)) -* **package:** update jsonwebtoken to version 8.0.0 ([#567](https://github.com/feathersjs/feathers/issues/567)) ([6811626](https://github.com/feathersjs/feathers/commit/6811626)) -* **package:** update ms to version 2.0.0 ([#509](https://github.com/feathersjs/feathers/issues/509)) ([7e4b0b6](https://github.com/feathersjs/feathers/commit/7e4b0b6)) -* **package:** update passport to version 0.4.0 ([#558](https://github.com/feathersjs/feathers/issues/558)) ([dcb14a5](https://github.com/feathersjs/feathers/commit/dcb14a5)) -* **package:** update passport-jwt to version 4.0.0 ([#58](https://github.com/feathersjs/feathers/issues/58)) ([77a3800](https://github.com/feathersjs/feathers/commit/77a3800)) -* **package:** update socket.io to version 2.0.0 ([#75](https://github.com/feathersjs/feathers/issues/75)) ([d4a4b71](https://github.com/feathersjs/feathers/commit/d4a4b71)) -* **package:** update yeoman-environment to version 2.0.0 ([#89](https://github.com/feathersjs/feathers/issues/89)) ([2355652](https://github.com/feathersjs/feathers/commit/2355652)) -* **package:** update yeoman-generator to version 2.0.0 ([#279](https://github.com/feathersjs/feathers/issues/279)) ([4f38e8b](https://github.com/feathersjs/feathers/commit/4f38e8b)) -* **package:** update yeoman-generator to version 2.0.0 ([#46](https://github.com/feathersjs/feathers/issues/46)) ([7071095](https://github.com/feathersjs/feathers/commit/7071095)) -* **package:** update yeoman-generator to version 3.0.0 ([#374](https://github.com/feathersjs/feathers/issues/374)) ([acdbbca](https://github.com/feathersjs/feathers/commit/acdbbca)) - +- Add test to make sure different id in adapter query works ([#1165](https://github.com/feathersjs/feathers/issues/1165)) ([0ba4580](https://github.com/feathersjs/feathers/commit/0ba4580)) +- Add whitelist and filter support to common adapter service ([#1132](https://github.com/feathersjs/feathers/issues/1132)) ([df1daaa](https://github.com/feathersjs/feathers/commit/df1daaa)) +- Added path and method in to express request for passport ([#1112](https://github.com/feathersjs/feathers/issues/1112)) ([afa1cb4](https://github.com/feathersjs/feathers/commit/afa1cb4)) +- Authentication core improvements ([#1260](https://github.com/feathersjs/feathers/issues/1260)) ([c5dc7a2](https://github.com/feathersjs/feathers/commit/c5dc7a2)) +- Catch connection initialization errors ([#1043](https://github.com/feathersjs/feathers/issues/1043)) ([4f9acd6](https://github.com/feathersjs/feathers/commit/4f9acd6)) +- Compare socket event data using lodash's isEqual instead of indexOf ([#1061](https://github.com/feathersjs/feathers/issues/1061)) ([f706db3](https://github.com/feathersjs/feathers/commit/f706db3)) +- Do not inherit app object from Object prototype ([#1153](https://github.com/feathersjs/feathers/issues/1153)) ([ed8c2e4](https://github.com/feathersjs/feathers/commit/ed8c2e4)) +- Fix AdapterService multi option when set to true ([#1134](https://github.com/feathersjs/feathers/issues/1134)) ([40402fc](https://github.com/feathersjs/feathers/commit/40402fc)) +- Improve JWT authentication option handling ([#1261](https://github.com/feathersjs/feathers/issues/1261)) ([31b956b](https://github.com/feathersjs/feathers/commit/31b956b)) +- make codeclimate conform to rule of three ([#1076](https://github.com/feathersjs/feathers/issues/1076)) ([0a2ce87](https://github.com/feathersjs/feathers/commit/0a2ce87)) +- Make Mocha a proper devDependency for every repository ([#1053](https://github.com/feathersjs/feathers/issues/1053)) ([9974803](https://github.com/feathersjs/feathers/commit/9974803)) +- More robust parsing of mongodb connection string. Use new url parser. ([#1002](https://github.com/feathersjs/feathers/issues/1002)) ([74b31df](https://github.com/feathersjs/feathers/commit/74b31df)) +- Normalize params to object even when it is falsy ([#1012](https://github.com/feathersjs/feathers/issues/1012)) ([af97818](https://github.com/feathersjs/feathers/commit/af97818)) +- Only merge authenticated property on update ([8a564f7](https://github.com/feathersjs/feathers/commit/8a564f7)) +- reduce authentication connection hook complexity and remove unnecessary checks ([fa94b2f](https://github.com/feathersjs/feathers/commit/fa94b2f)) +- support a secretProvider ([#1063](https://github.com/feathersjs/feathers/issues/1063)) ([9da26ad](https://github.com/feathersjs/feathers/commit/9da26ad)) +- Support Logger swallowing ([#995](https://github.com/feathersjs/feathers/issues/995)) ([5b3b37e](https://github.com/feathersjs/feathers/commit/5b3b37e)), closes [/github.com/feathersjs/generator-feathers/pull/392#issuecomment-420408312](https://github.com//github.com/feathersjs/generator-feathers/pull/392/issues/issuecomment-420408312) +- Throw error in `filterQuery` when query parameter is unknown ([#1131](https://github.com/feathersjs/feathers/issues/1131)) ([cd1a183](https://github.com/feathersjs/feathers/commit/cd1a183)) +- Update 401.html ([#983](https://github.com/feathersjs/feathers/issues/983)) ([cec6bae](https://github.com/feathersjs/feathers/commit/cec6bae)) +- Update 404.html ([#984](https://github.com/feathersjs/feathers/issues/984)) ([72132d1](https://github.com/feathersjs/feathers/commit/72132d1)) +- Update adapter common tests ([#1135](https://github.com/feathersjs/feathers/issues/1135)) ([8166dda](https://github.com/feathersjs/feathers/commit/8166dda)) +- Update adapter common tests to check for falsy ([#1140](https://github.com/feathersjs/feathers/issues/1140)) ([2856722](https://github.com/feathersjs/feathers/commit/2856722)) +- Update adapter tests to not rely on error instance ([#1202](https://github.com/feathersjs/feathers/issues/1202)) ([6885e0e](https://github.com/feathersjs/feathers/commit/6885e0e)) +- Update all dependencies to latest ([#1206](https://github.com/feathersjs/feathers/issues/1206)) ([e51e0f6](https://github.com/feathersjs/feathers/commit/e51e0f6)) +- **adapter-commons:** Keep Symbols when filtering a query ([#1141](https://github.com/feathersjs/feathers/issues/1141)) ([c9f55d8](https://github.com/feathersjs/feathers/commit/c9f55d8)) +- **authentication:** Fall back when req.app is not the application when emitting events ([#1185](https://github.com/feathersjs/feathers/issues/1185)) ([6a534f0](https://github.com/feathersjs/feathers/commit/6a534f0)) +- **chore:** Add .npmignore to adapter-commons ([8e129d8](https://github.com/feathersjs/feathers/commit/8e129d8)) +- **chore:** Properly configure and run code linter ([#1092](https://github.com/feathersjs/feathers/issues/1092)) ([fd3fc34](https://github.com/feathersjs/feathers/commit/fd3fc34)) +- **chore:** Remove CLI and generators that belong in their own repositories ([#1091](https://github.com/feathersjs/feathers/issues/1091)) ([e894ac8](https://github.com/feathersjs/feathers/commit/e894ac8)) +- **compile-task:** on windows machine ([#60](https://github.com/feathersjs/feathers/issues/60)) ([617e0a4](https://github.com/feathersjs/feathers/commit/617e0a4)) +- **docs/new-features:** syntax highlighting ([#347](https://github.com/feathersjs/feathers/issues/347)) ([4ab7c95](https://github.com/feathersjs/feathers/commit/4ab7c95)) +- **knex:** Fix knex + sql server issues when using authentication generator ([#257](https://github.com/feathersjs/feathers/issues/257)) ([8f8f75f](https://github.com/feathersjs/feathers/commit/8f8f75f)) +- **package:** update @feathersjs/commons to version 2.0.0 ([#31](https://github.com/feathersjs/feathers/issues/31)) ([c1ef5b1](https://github.com/feathersjs/feathers/commit/c1ef5b1)) +- **package:** update @feathersjs/commons to version 2.0.0 ([#692](https://github.com/feathersjs/feathers/issues/692)) ([ca665ab](https://github.com/feathersjs/feathers/commit/ca665ab)) +- **package:** update config to version 3.0.0 ([#1100](https://github.com/feathersjs/feathers/issues/1100)) ([c9f4b42](https://github.com/feathersjs/feathers/commit/c9f4b42)) +- use minimal RegExp matching for better performance ([#977](https://github.com/feathersjs/feathers/issues/977)) ([3ca7e97](https://github.com/feathersjs/feathers/commit/3ca7e97)) +- **package:** update @feathersjs/commons to version 2.0.0 ([#45](https://github.com/feathersjs/feathers/issues/45)) ([9e82595](https://github.com/feathersjs/feathers/commit/9e82595)) +- **package:** update @feathersjs/commons to version 2.0.0 ([#84](https://github.com/feathersjs/feathers/issues/84)) ([78ed39c](https://github.com/feathersjs/feathers/commit/78ed39c)) +- **package:** update debug to version 3.0.0 ([#2](https://github.com/feathersjs/feathers/issues/2)) ([7e19603](https://github.com/feathersjs/feathers/commit/7e19603)) +- **package:** update debug to version 3.0.0 ([#22](https://github.com/feathersjs/feathers/issues/22)) ([0b62606](https://github.com/feathersjs/feathers/commit/0b62606)) +- **package:** update debug to version 3.0.0 ([#30](https://github.com/feathersjs/feathers/issues/30)) ([baf7a00](https://github.com/feathersjs/feathers/commit/baf7a00)) +- **package:** update debug to version 3.0.0 ([#31](https://github.com/feathersjs/feathers/issues/31)) ([902ddf5](https://github.com/feathersjs/feathers/commit/902ddf5)) +- **package:** update debug to version 3.0.0 ([#31](https://github.com/feathersjs/feathers/issues/31)) ([f23d617](https://github.com/feathersjs/feathers/commit/f23d617)) +- **package:** update debug to version 3.0.0 ([#45](https://github.com/feathersjs/feathers/issues/45)) ([2391434](https://github.com/feathersjs/feathers/commit/2391434)) +- **package:** update debug to version 3.0.0 ([#45](https://github.com/feathersjs/feathers/issues/45)) ([9b9bde5](https://github.com/feathersjs/feathers/commit/9b9bde5)) +- **package:** update debug to version 3.0.0 ([#555](https://github.com/feathersjs/feathers/issues/555)) ([f788804](https://github.com/feathersjs/feathers/commit/f788804)) +- **package:** update debug to version 3.0.0 ([#59](https://github.com/feathersjs/feathers/issues/59)) ([fedcf06](https://github.com/feathersjs/feathers/commit/fedcf06)) +- **package:** update debug to version 3.0.0 ([#61](https://github.com/feathersjs/feathers/issues/61)) ([6f5009c](https://github.com/feathersjs/feathers/commit/6f5009c)) +- **package:** update debug to version 3.0.0 ([#83](https://github.com/feathersjs/feathers/issues/83)) ([49f1de9](https://github.com/feathersjs/feathers/commit/49f1de9)) +- **package:** update debug to version 3.0.0 ([#86](https://github.com/feathersjs/feathers/issues/86)) ([fd1bb6b](https://github.com/feathersjs/feathers/commit/fd1bb6b)) +- **package:** update debug to version 3.0.1 ([#46](https://github.com/feathersjs/feathers/issues/46)) ([f8ada69](https://github.com/feathersjs/feathers/commit/f8ada69)) +- **package:** update generator-feathers to version 1.0.3 ([#81](https://github.com/feathersjs/feathers/issues/81)) ([0c66bc5](https://github.com/feathersjs/feathers/commit/0c66bc5)) +- **package:** update generator-feathers to version 1.0.5 ([#83](https://github.com/feathersjs/feathers/issues/83)) ([229caba](https://github.com/feathersjs/feathers/commit/229caba)) +- **package:** update generator-feathers to version 1.0.6 ([#86](https://github.com/feathersjs/feathers/issues/86)) ([7ae8e56](https://github.com/feathersjs/feathers/commit/7ae8e56)) +- **package:** update generator-feathers to version 1.1.0 ([#93](https://github.com/feathersjs/feathers/issues/93)) ([f393e4c](https://github.com/feathersjs/feathers/commit/f393e4c)) +- **package:** update generator-feathers to version 1.1.1 ([#95](https://github.com/feathersjs/feathers/issues/95)) ([3279ba9](https://github.com/feathersjs/feathers/commit/3279ba9)) +- **package:** update generator-feathers to version 1.2.0 ([#96](https://github.com/feathersjs/feathers/issues/96)) ([8eb5674](https://github.com/feathersjs/feathers/commit/8eb5674)) +- **package:** update generator-feathers to version 1.2.10 ([#115](https://github.com/feathersjs/feathers/issues/115)) ([c1db2b2](https://github.com/feathersjs/feathers/commit/c1db2b2)) +- **package:** update generator-feathers to version 1.2.11 ([#116](https://github.com/feathersjs/feathers/issues/116)) ([bba6550](https://github.com/feathersjs/feathers/commit/bba6550)) +- **package:** update generator-feathers to version 1.2.12 ([#119](https://github.com/feathersjs/feathers/issues/119)) ([e5c737d](https://github.com/feathersjs/feathers/commit/e5c737d)) +- **package:** update generator-feathers to version 1.2.2 ([#98](https://github.com/feathersjs/feathers/issues/98)) ([ee629e3](https://github.com/feathersjs/feathers/commit/ee629e3)), closes [#97](https://github.com/feathersjs/feathers/issues/97) +- **package:** update generator-feathers to version 1.2.3 ([#99](https://github.com/feathersjs/feathers/issues/99)) ([b6cf361](https://github.com/feathersjs/feathers/commit/b6cf361)) +- **package:** update generator-feathers to version 1.2.4 ([#101](https://github.com/feathersjs/feathers/issues/101)) ([2182fef](https://github.com/feathersjs/feathers/commit/2182fef)) +- **package:** update generator-feathers to version 1.2.5 ([#104](https://github.com/feathersjs/feathers/issues/104)) ([295f6aa](https://github.com/feathersjs/feathers/commit/295f6aa)) +- **package:** update generator-feathers to version 1.2.6 ([#106](https://github.com/feathersjs/feathers/issues/106)) ([66125dc](https://github.com/feathersjs/feathers/commit/66125dc)) +- **package:** update generator-feathers to version 1.2.9 ([#110](https://github.com/feathersjs/feathers/issues/110)) ([17e55dc](https://github.com/feathersjs/feathers/commit/17e55dc)) +- **package:** update generator-feathers to version 2.0.0 ([#126](https://github.com/feathersjs/feathers/issues/126)) ([eff6627](https://github.com/feathersjs/feathers/commit/eff6627)) +- **package:** update generator-feathers to version 2.1.0 ([#128](https://github.com/feathersjs/feathers/issues/128)) ([b712355](https://github.com/feathersjs/feathers/commit/b712355)) +- **package:** update generator-feathers to version 2.1.1 ([#129](https://github.com/feathersjs/feathers/issues/129)) ([1f91c0b](https://github.com/feathersjs/feathers/commit/1f91c0b)) +- **package:** update generator-feathers to version 2.2.0 ([#130](https://github.com/feathersjs/feathers/issues/130)) ([308ad0b](https://github.com/feathersjs/feathers/commit/308ad0b)) +- **package:** update generator-feathers to version 2.3.0 ([#131](https://github.com/feathersjs/feathers/issues/131)) ([7894807](https://github.com/feathersjs/feathers/commit/7894807)) +- **package:** update generator-feathers to version 2.3.1 ([#132](https://github.com/feathersjs/feathers/issues/132)) ([c3e3187](https://github.com/feathersjs/feathers/commit/c3e3187)) +- **package:** update generator-feathers to version 2.4.0 ([#137](https://github.com/feathersjs/feathers/issues/137)) ([1645d2e](https://github.com/feathersjs/feathers/commit/1645d2e)) +- **package:** update generator-feathers to version 2.4.1 ([#140](https://github.com/feathersjs/feathers/issues/140)) ([e5a5f7c](https://github.com/feathersjs/feathers/commit/e5a5f7c)) +- **package:** update generator-feathers to version 2.4.4 ([#151](https://github.com/feathersjs/feathers/issues/151)) ([3dcd480](https://github.com/feathersjs/feathers/commit/3dcd480)) +- **package:** update generator-feathers to version 2.5.2 ([#155](https://github.com/feathersjs/feathers/issues/155)) ([493ca4b](https://github.com/feathersjs/feathers/commit/493ca4b)) +- **package:** update generator-feathers to version 2.5.3 ([#156](https://github.com/feathersjs/feathers/issues/156)) ([ef570a8](https://github.com/feathersjs/feathers/commit/ef570a8)) +- **package:** update generator-feathers to version 2.5.4 ([#158](https://github.com/feathersjs/feathers/issues/158)) ([787f30c](https://github.com/feathersjs/feathers/commit/787f30c)) +- **package:** update generator-feathers to version 2.5.5 ([#159](https://github.com/feathersjs/feathers/issues/159)) ([bbd1b29](https://github.com/feathersjs/feathers/commit/bbd1b29)) +- **package:** update generator-feathers to version 2.5.6 ([#161](https://github.com/feathersjs/feathers/issues/161)) ([cb72a5c](https://github.com/feathersjs/feathers/commit/cb72a5c)) +- **package:** update generator-feathers to version 2.6.0 ([#164](https://github.com/feathersjs/feathers/issues/164)) ([6212ec9](https://github.com/feathersjs/feathers/commit/6212ec9)) +- **package:** update generator-feathers-plugin to version 0.11.0 ([#105](https://github.com/feathersjs/feathers/issues/105)) ([d40bb75](https://github.com/feathersjs/feathers/commit/d40bb75)) +- **package:** update generator-feathers-plugin to version 0.12.1 ([#112](https://github.com/feathersjs/feathers/issues/112)) ([f374e01](https://github.com/feathersjs/feathers/commit/f374e01)) +- **package:** update generator-feathers-plugin to version 1.0.0 ([#134](https://github.com/feathersjs/feathers/issues/134)) ([ee905b0](https://github.com/feathersjs/feathers/commit/ee905b0)) +- **package:** update jsonwebtoken to version 8.0.0 ([#567](https://github.com/feathersjs/feathers/issues/567)) ([6811626](https://github.com/feathersjs/feathers/commit/6811626)) +- **package:** update ms to version 2.0.0 ([#509](https://github.com/feathersjs/feathers/issues/509)) ([7e4b0b6](https://github.com/feathersjs/feathers/commit/7e4b0b6)) +- **package:** update passport to version 0.4.0 ([#558](https://github.com/feathersjs/feathers/issues/558)) ([dcb14a5](https://github.com/feathersjs/feathers/commit/dcb14a5)) +- **package:** update passport-jwt to version 4.0.0 ([#58](https://github.com/feathersjs/feathers/issues/58)) ([77a3800](https://github.com/feathersjs/feathers/commit/77a3800)) +- **package:** update socket.io to version 2.0.0 ([#75](https://github.com/feathersjs/feathers/issues/75)) ([d4a4b71](https://github.com/feathersjs/feathers/commit/d4a4b71)) +- **package:** update yeoman-environment to version 2.0.0 ([#89](https://github.com/feathersjs/feathers/issues/89)) ([2355652](https://github.com/feathersjs/feathers/commit/2355652)) +- **package:** update yeoman-generator to version 2.0.0 ([#279](https://github.com/feathersjs/feathers/issues/279)) ([4f38e8b](https://github.com/feathersjs/feathers/commit/4f38e8b)) +- **package:** update yeoman-generator to version 2.0.0 ([#46](https://github.com/feathersjs/feathers/issues/46)) ([7071095](https://github.com/feathersjs/feathers/commit/7071095)) +- **package:** update yeoman-generator to version 3.0.0 ([#374](https://github.com/feathersjs/feathers/issues/374)) ([acdbbca](https://github.com/feathersjs/feathers/commit/acdbbca)) ### chore -* **package:** Move adapter tests into their own module ([#1164](https://github.com/feathersjs/feathers/issues/1164)) ([dcc1e6b](https://github.com/feathersjs/feathers/commit/dcc1e6b)) -* drop support for Node.js 0.10 ([#48](https://github.com/feathersjs/feathers/issues/48)) ([3f7555a](https://github.com/feathersjs/feathers/commit/3f7555a)) - +- **package:** Move adapter tests into their own module ([#1164](https://github.com/feathersjs/feathers/issues/1164)) ([dcc1e6b](https://github.com/feathersjs/feathers/commit/dcc1e6b)) +- drop support for Node.js 0.10 ([#48](https://github.com/feathersjs/feathers/issues/48)) ([3f7555a](https://github.com/feathersjs/feathers/commit/3f7555a)) ### Features -* @feathers/cli: introduce option to choose jest for tests instead of mocha ([#1057](https://github.com/feathersjs/feathers/issues/1057)) ([1356a1c](https://github.com/feathersjs/feathers/commit/1356a1c)) -* @feathersjs/authentication-oauth ([#1299](https://github.com/feathersjs/feathers/issues/1299)) ([656bae7](https://github.com/feathersjs/feathers/commit/656bae7)) -* Add authentication through oAuth redirect to authentication client ([#1301](https://github.com/feathersjs/feathers/issues/1301)) ([35d8043](https://github.com/feathersjs/feathers/commit/35d8043)) -* Add AuthenticationBaseStrategy and make authentication option handling more explicit ([#1284](https://github.com/feathersjs/feathers/issues/1284)) ([2667d92](https://github.com/feathersjs/feathers/commit/2667d92)) -* Add TypeScript definitions ([#1275](https://github.com/feathersjs/feathers/issues/1275)) ([9dd6713](https://github.com/feathersjs/feathers/commit/9dd6713)) -* Added generators for feathers-objection & feathers-cassandra ([#1010](https://github.com/feathersjs/feathers/issues/1010)) ([c8b27d0](https://github.com/feathersjs/feathers/commit/c8b27d0)) -* Allow registering a service at the root level ([#1115](https://github.com/feathersjs/feathers/issues/1115)) ([c73d322](https://github.com/feathersjs/feathers/commit/c73d322)) -* Allow to skip sending service events ([#1270](https://github.com/feathersjs/feathers/issues/1270)) ([b487bbd](https://github.com/feathersjs/feathers/commit/b487bbd)) -* Authentication v3 client ([#1240](https://github.com/feathersjs/feathers/issues/1240)) ([65b43bd](https://github.com/feathersjs/feathers/commit/65b43bd)) -* Authentication v3 core server implementation ([#1205](https://github.com/feathersjs/feathers/issues/1205)) ([1bd7591](https://github.com/feathersjs/feathers/commit/1bd7591)) -* Authentication v3 Express integration ([#1218](https://github.com/feathersjs/feathers/issues/1218)) ([82bcfbe](https://github.com/feathersjs/feathers/commit/82bcfbe)) -* Authentication v3 local authentication ([#1211](https://github.com/feathersjs/feathers/issues/1211)) ([0fa5f7c](https://github.com/feathersjs/feathers/commit/0fa5f7c)) -* Common database adapter utilities and test suite ([#1130](https://github.com/feathersjs/feathers/issues/1130)) ([17b3dc8](https://github.com/feathersjs/feathers/commit/17b3dc8)) -* Make custom query for oAuth authentication ([#1124](https://github.com/feathersjs/feathers/issues/1124)) ([5d43e3c](https://github.com/feathersjs/feathers/commit/5d43e3c)) -* Remove (hook, next) signature and SKIP support ([#1269](https://github.com/feathersjs/feathers/issues/1269)) ([211c0f8](https://github.com/feathersjs/feathers/commit/211c0f8)) -* Support params symbol to skip authenticate hook ([#1296](https://github.com/feathersjs/feathers/issues/1296)) ([d16cf4d](https://github.com/feathersjs/feathers/commit/d16cf4d)) - +- @feathers/cli: introduce option to choose jest for tests instead of mocha ([#1057](https://github.com/feathersjs/feathers/issues/1057)) ([1356a1c](https://github.com/feathersjs/feathers/commit/1356a1c)) +- @feathersjs/authentication-oauth ([#1299](https://github.com/feathersjs/feathers/issues/1299)) ([656bae7](https://github.com/feathersjs/feathers/commit/656bae7)) +- Add authentication through oAuth redirect to authentication client ([#1301](https://github.com/feathersjs/feathers/issues/1301)) ([35d8043](https://github.com/feathersjs/feathers/commit/35d8043)) +- Add AuthenticationBaseStrategy and make authentication option handling more explicit ([#1284](https://github.com/feathersjs/feathers/issues/1284)) ([2667d92](https://github.com/feathersjs/feathers/commit/2667d92)) +- Add TypeScript definitions ([#1275](https://github.com/feathersjs/feathers/issues/1275)) ([9dd6713](https://github.com/feathersjs/feathers/commit/9dd6713)) +- Added generators for feathers-objection & feathers-cassandra ([#1010](https://github.com/feathersjs/feathers/issues/1010)) ([c8b27d0](https://github.com/feathersjs/feathers/commit/c8b27d0)) +- Allow registering a service at the root level ([#1115](https://github.com/feathersjs/feathers/issues/1115)) ([c73d322](https://github.com/feathersjs/feathers/commit/c73d322)) +- Allow to skip sending service events ([#1270](https://github.com/feathersjs/feathers/issues/1270)) ([b487bbd](https://github.com/feathersjs/feathers/commit/b487bbd)) +- Authentication v3 client ([#1240](https://github.com/feathersjs/feathers/issues/1240)) ([65b43bd](https://github.com/feathersjs/feathers/commit/65b43bd)) +- Authentication v3 core server implementation ([#1205](https://github.com/feathersjs/feathers/issues/1205)) ([1bd7591](https://github.com/feathersjs/feathers/commit/1bd7591)) +- Authentication v3 Express integration ([#1218](https://github.com/feathersjs/feathers/issues/1218)) ([82bcfbe](https://github.com/feathersjs/feathers/commit/82bcfbe)) +- Authentication v3 local authentication ([#1211](https://github.com/feathersjs/feathers/issues/1211)) ([0fa5f7c](https://github.com/feathersjs/feathers/commit/0fa5f7c)) +- Common database adapter utilities and test suite ([#1130](https://github.com/feathersjs/feathers/issues/1130)) ([17b3dc8](https://github.com/feathersjs/feathers/commit/17b3dc8)) +- Make custom query for oAuth authentication ([#1124](https://github.com/feathersjs/feathers/issues/1124)) ([5d43e3c](https://github.com/feathersjs/feathers/commit/5d43e3c)) +- Remove (hook, next) signature and SKIP support ([#1269](https://github.com/feathersjs/feathers/issues/1269)) ([211c0f8](https://github.com/feathersjs/feathers/commit/211c0f8)) +- Support params symbol to skip authenticate hook ([#1296](https://github.com/feathersjs/feathers/issues/1296)) ([d16cf4d](https://github.com/feathersjs/feathers/commit/d16cf4d)) ### BREAKING CHANGES -* Rewrite for authentication v3 -* Update authentication strategies for @feathersjs/authentication v3 -* **package:** Removes adapter tests from @feathersjs/adapter-commons -* Move database adapter utilities from @feathersjs/commons into its own module -* This module no longer supports Node.js 0.10 +- Rewrite for authentication v3 +- Update authentication strategies for @feathersjs/authentication v3 +- **package:** Removes adapter tests from @feathersjs/adapter-commons +- Move database adapter utilities from @feathersjs/commons into its own module +- This module no longer supports Node.js 0.10 diff --git a/LICENSE b/LICENSE index 3f395cc665..59604f46f3 100644 --- a/LICENSE +++ b/LICENSE @@ -1,6 +1,6 @@ The MIT License (MIT) -Copyright (c) 2021 Feathers +Copyright (c) 2022 Feathers Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated documentation files (the "Software"), to deal diff --git a/packages/feathers/readme.md b/README.md similarity index 91% rename from packages/feathers/readme.md rename to README.md index 46eba676a6..01be1db801 100644 --- a/packages/feathers/readme.md +++ b/README.md @@ -6,6 +6,7 @@ [![Maintainability](https://api.codeclimate.com/v1/badges/cb5ec42a2d0cc1a47a02/maintainability)](https://codeclimate.com/github/feathersjs/feathers/maintainability) [![Test Coverage](https://api.codeclimate.com/v1/badges/cb5ec42a2d0cc1a47a02/test_coverage)](https://codeclimate.com/github/feathersjs/feathers/test_coverage) [![Download Status](https://img.shields.io/npm/dm/@feathersjs/feathers.svg?style=flat-square)](https://www.npmjs.com/package/@feathersjs/feathers) +[![Discord](https://badgen.net/badge/icon/discord?icon=discord&label)](https://discord.gg/qa8kez8QBx) Feathers is a lightweight web-framework for creating real-time applications and REST APIs using JavaScript or TypeScript. @@ -31,6 +32,6 @@ The [Feathers docs](http://docs.feathersjs.com) are loaded with awesome stuff an ## License -Copyright (c) 2021 [Feathers contributors](https://github.com/feathersjs/feathers/graphs/contributors) +Copyright (c) 2022 [Feathers contributors](https://github.com/feathersjs/feathers/graphs/contributors) Licensed under the [MIT license](LICENSE). diff --git a/_templates/package/new/index.test.ts.t b/_templates/package/new/index.test.ts.t deleted file mode 100644 index 053c5be400..0000000000 --- a/_templates/package/new/index.test.ts.t +++ /dev/null @@ -1,12 +0,0 @@ ---- -to: packages/<%= name %>/test/index.test.ts ---- - -import assert from 'assert'; -import { hello } from '../src'; - -describe('@feathersjs/<%= name %>', () => { - it('initializes', async () => { - assert.strictEqual(hello(), 'Hello'); - }); -}); diff --git a/_templates/package/new/index.ts.t b/_templates/package/new/index.ts.t deleted file mode 100644 index b0120efce8..0000000000 --- a/_templates/package/new/index.ts.t +++ /dev/null @@ -1,7 +0,0 @@ ---- -to: packages/<%= name %>/src/index.ts ---- - -export function hello () { - return 'Hello'; -} diff --git a/deno/LICENSE b/deno/LICENSE index 3f395cc665..59604f46f3 100644 --- a/deno/LICENSE +++ b/deno/LICENSE @@ -1,6 +1,6 @@ The MIT License (MIT) -Copyright (c) 2021 Feathers +Copyright (c) 2022 Feathers Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated documentation files (the "Software"), to deal diff --git a/deno/readme.md b/deno/README.md similarity index 94% rename from deno/readme.md rename to deno/README.md index 6b8ef62fc5..63d9d4ecd4 100644 --- a/deno/readme.md +++ b/deno/README.md @@ -10,7 +10,7 @@ This folder contains the Deno build of Feathers. // app.ts import { feathers } from 'https://deno.land/x/feathers@v5.0.0-pre.3/mod.ts'; -type Message { +type Message = { message: string; } @@ -20,7 +20,7 @@ class MyService { } } -type ServiceTypes { +type ServiceTypes = { myservice: MyService } diff --git a/lerna.json b/lerna.json index 3908b2f63f..a6b6a52736 100644 --- a/lerna.json +++ b/lerna.json @@ -1,18 +1,13 @@ { "ci": false, - "packages": [ - "packages/*" - ], - "version": "5.0.0-pre.16", + "packages": ["packages/*"], + "version": "5.0.0-pre.31", "command": { "bootstrap": { "hoist": true }, "publish": { - "allowBranch": [ - "crow", - "dove" - ], + "allowBranch": ["crow", "dove"], "message": "chore(release): publish %s", "conventionalCommits": true, "createRelease": "github" diff --git a/main/adapter-commons/LICENSE b/main/adapter-commons/LICENSE index 3f395cc665..59604f46f3 100644 --- a/main/adapter-commons/LICENSE +++ b/main/adapter-commons/LICENSE @@ -1,6 +1,6 @@ The MIT License (MIT) -Copyright (c) 2021 Feathers +Copyright (c) 2022 Feathers Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated documentation files (the "Software"), to deal diff --git a/main/adapter-commons/mod.ts b/main/adapter-commons/mod.ts new file mode 100644 index 0000000000..3b3419b271 --- /dev/null +++ b/main/adapter-commons/mod.ts @@ -0,0 +1 @@ +export * from "./src/index.ts"; diff --git a/main/adapter-commons/src/declarations.ts b/main/adapter-commons/src/declarations.ts new file mode 100644 index 0000000000..3d9543f40f --- /dev/null +++ b/main/adapter-commons/src/declarations.ts @@ -0,0 +1,166 @@ +import { + Query, + Params, + Paginated, + Id, + NullableId, +} from "../../feathers/mod.ts"; + +export type FilterQueryOptions = { + filters?: FilterSettings; + operators?: string[]; + paginate?: PaginationParams; +}; + +export type QueryFilter = (value: any, options: FilterQueryOptions) => any; + +export type FilterSettings = { + [key: string]: QueryFilter | true; +}; + +export interface PaginationOptions { + default?: number; + max?: number; +} + +export type PaginationParams = false | PaginationOptions; + +export interface AdapterServiceOptions { + /** + * Whether to allow multiple updates for everything (`true`) or specific methods (e.g. `['create', 'remove']`) + */ + multi?: boolean | string[]; + /** + * The name of the id property + */ + id?: string; + /** + * Pagination settings for this service + */ + paginate?: PaginationParams; + /** + * A list of additional property query operators to allow in a query + */ + operators?: string[]; + /** + * An object of additional top level query filters, e.g. `{ $populate: true }` + * Can also be a converter function like `{ $ignoreCase: (value) => value === 'true' ? true : false }` + */ + filters?: FilterSettings; + /** + * @deprecated Use service `events` option when registering the service with `app.use`. + */ + events?: string[]; + /** + * @deprecated renamed to `operators`. + */ + whitelist?: string[]; +} + +export interface AdapterQuery extends Query { + $limit?: number; + $skip?: number; + $select?: string[]; + $sort?: { [key: string]: 1 | -1 }; +} +/** + * Additional `params` that can be passed to an adapter service method call. + */ +export interface AdapterParams< + Q = AdapterQuery, + A extends Partial = Partial +> extends Params { + adapter?: A; + paginate?: PaginationParams; +} + +/** + * Hook-less (internal) service methods. Directly call database adapter service methods + * without running any service-level hooks or sanitization. This can be useful if you need the raw data + * from the service and don't want to trigger any of its hooks. + * + * Important: These methods are only available internally on the server, not on the client + * side and only for the Feathers database adapters. + * + * These methods do not trigger events. + * + * @see {@link https://docs.feathersjs.com/guides/migrating.html#hook-less-service-methods} + */ +export interface InternalServiceMethods< + T = any, + D = Partial, + P extends AdapterParams = AdapterParams +> { + /** + * Retrieve all resources from this service. + * Does not sanitize the query and should only be used on the server. + * + * @param _params - Service call parameters {@link Params} + */ + $find(_params?: P & { paginate?: PaginationOptions }): Promise>; + $find(_params?: P & { paginate: false }): Promise; + $find(params?: P): Promise>; + + /** + * Retrieve a single resource matching the given ID, skipping any service-level hooks. + * Does not sanitize the query and should only be used on the server. + * + * @param id - ID of the resource to locate + * @param params - Service call parameters {@link Params} + * @see {@link HookLessServiceMethods} + * @see {@link https://docs.feathersjs.com/api/services.html#get-id-params|Feathers API Documentation: .get(id, params)} + */ + $get(id: Id, params?: P): Promise; + + /** + * Create a new resource for this service, skipping any service-level hooks. + * Does not sanitize data or checks if multiple updates are allowed and should only be used on the server. + * + * @param data - Data to insert into this service. + * @param params - Service call parameters {@link Params} + * @see {@link HookLessServiceMethods} + * @see {@link https://docs.feathersjs.com/api/services.html#create-data-params|Feathers API Documentation: .create(data, params)} + */ + $create(data: Partial, params?: P): Promise; + $create(data: Partial[], params?: P): Promise; + $create(data: Partial | Partial[], params?: P): Promise; + + /** + * Completely replace the resource identified by id, skipping any service-level hooks. + * Does not sanitize data or query and should only be used on the server. + * + * @param id - ID of the resource to be updated + * @param data - Data to be put in place of the current resource. + * @param params - Service call parameters {@link Params} + * @see {@link HookLessServiceMethods} + * @see {@link https://docs.feathersjs.com/api/services.html#update-id-data-params|Feathers API Documentation: .update(id, data, params)} + */ + $update(id: Id, data: D, params?: P): Promise; + + /** + * Merge any resources matching the given ID with the given data, skipping any service-level hooks. + * Does not sanitize the data or query and should only be used on the server. + * + * @param id - ID of the resource to be patched + * @param data - Data to merge with the current resource. + * @param params - Service call parameters {@link Params} + * @see {@link HookLessServiceMethods} + * @see {@link https://docs.feathersjs.com/api/services.html#patch-id-data-params|Feathers API Documentation: .patch(id, data, params)} + */ + $patch(id: null, data: Partial, params?: P): Promise; + $patch(id: Id, data: Partial, params?: P): Promise; + $patch(id: NullableId, data: Partial, params?: P): Promise; + + /** + * Remove resources matching the given ID from the this service, skipping any service-level hooks. + * Does not sanitize query and should only be used on the server. + * + * @param id - ID of the resource to be removed + * @param params - Service call parameters {@link Params} + * @see {@link HookLessServiceMethods} + * @see {@link https://docs.feathersjs.com/api/services.html#remove-id-params|Feathers API Documentation: .remove(id, params)} + */ + $remove(id: null, params?: P): Promise; + $remove(id: Id, params?: P): Promise; + $remove(id: NullableId, params?: P): Promise; +} diff --git a/main/adapter-commons/src/filter-query.ts b/main/adapter-commons/src/filter-query.ts deleted file mode 100644 index 76d1067159..0000000000 --- a/main/adapter-commons/src/filter-query.ts +++ /dev/null @@ -1,116 +0,0 @@ -import { _ } from '../../commons/src/index.ts'; -import { BadRequest } from '../../errors/src/index.ts'; - -function parse (number: any) { - if (typeof number !== 'undefined') { - return Math.abs(parseInt(number, 10)); - } - - return undefined; -} - -// Returns the pagination limit and will take into account the -// default and max pagination settings -function getLimit (limit: any, paginate: any) { - if (paginate && (paginate.default || paginate.max)) { - const base = paginate.default || 0; - const lower = typeof limit === 'number' && !isNaN(limit) ? limit : base; - const upper = typeof paginate.max === 'number' ? paginate.max : Number.MAX_VALUE; - - return Math.min(lower, upper); - } - - return limit; -} - -// Makes sure that $sort order is always converted to an actual number -function convertSort (sort: any) { - if (typeof sort !== 'object' || Array.isArray(sort)) { - return sort; - } - - return Object.keys(sort).reduce((result, key) => { - result[key] = typeof sort[key] === 'object' - ? sort[key] : parseInt(sort[key], 10); - - return result; - }, {} as { [key: string]: number }); -} - -function cleanQuery (query: any, operators: any, filters: any): any { - if (Array.isArray(query)) { - return query.map(value => cleanQuery(value, operators, filters)); - } else if (_.isObject(query) && query.constructor === {}.constructor) { - const result: { [key: string]: any } = {}; - - _.each(query, (value, key) => { - if (key[0] === '$') { - if (filters[key] !== undefined) { - return; - } - - if (!operators.includes(key)) { - throw new BadRequest(`Invalid query parameter ${key}`, query); - } - } - - result[key] = cleanQuery(value, operators, filters); - }); - - Object.getOwnPropertySymbols(query).forEach(symbol => { - // @ts-ignore - result[symbol] = query[symbol]; - }); - - return result; - } - - return query; -} - -function assignFilters (object: any, query: any, filters: any, options: any) { - if (Array.isArray(filters)) { - _.each(filters, (key) => { - if (query[key] !== undefined) { - object[key] = query[key]; - } - }); - } else { - _.each(filters, (converter, key) => { - const converted = converter(query[key], options); - - if (converted !== undefined) { - object[key] = converted; - } - }); - } - - return object; -} - -export const FILTERS = { - $sort: (value: any) => convertSort(value), - $limit: (value: any, options: any) => getLimit(parse(value), options.paginate), - $skip: (value: any) => parse(value), - $select: (value: any) => value -}; - -export const OPERATORS = ['$in', '$nin', '$lt', '$lte', '$gt', '$gte', '$ne', '$or']; - -// Converts Feathers special query parameters and pagination settings -// and returns them separately a `filters` and the rest of the query -// as `query` -export function filterQuery (query: any, options: any = {}) { - const { - filters: additionalFilters = {}, - operators: additionalOperators = [] - } = options; - const result: { [key: string]: any } = {}; - - result.filters = assignFilters({}, query, FILTERS, options); - result.filters = assignFilters(result.filters, query, additionalFilters, options); - - result.query = cleanQuery(query, OPERATORS.concat(additionalOperators), result.filters); - - return result; -} diff --git a/main/adapter-commons/src/index.ts b/main/adapter-commons/src/index.ts index 1fae5a0ba3..81a47945f7 100644 --- a/main/adapter-commons/src/index.ts +++ b/main/adapter-commons/src/index.ts @@ -1,27 +1,23 @@ -import { _ } from '../../commons/src/index.ts'; +import { _ } from "../../commons/mod.ts"; +import { Params } from "../../feathers/mod.ts"; -export { AdapterService } from './service.ts'; -export type { InternalServiceMethods, ServiceOptions, AdapterParams } from './service.ts'; -export { filterQuery, FILTERS, OPERATORS } from './filter-query.ts'; -export * from './sort.ts'; +export * from "./declarations.ts"; +export * from "./service.ts"; +export { filterQuery, FILTERS, OPERATORS } from "./query.ts"; +export * from "./sort.ts"; // Return a function that filters a result object or array // and picks only the fields passed as `params.query.$select` // and additional `otherFields` -export function select (params: any, ...otherFields: any[]) { - const fields = params && params.query && params.query.$select; +export function select(params: Params, ...otherFields: string[]) { + const queryFields: string[] | undefined = params?.query?.$select; - if (Array.isArray(fields) && otherFields.length) { - fields.push(...otherFields); + if (!queryFields) { + return (result: any) => result; } - const convert = (result: any) => { - if (!Array.isArray(fields)) { - return result; - } - - return _.pick(result, ...fields); - }; + const resultFields = queryFields.concat(otherFields); + const convert = (result: any) => _.pick(result, ...resultFields); return (result: any) => { if (Array.isArray(result)) { diff --git a/main/adapter-commons/src/query.ts b/main/adapter-commons/src/query.ts new file mode 100644 index 0000000000..1a1df8e31a --- /dev/null +++ b/main/adapter-commons/src/query.ts @@ -0,0 +1,156 @@ +import { _ } from "../../commons/mod.ts"; +import { BadRequest } from "../../errors/mod.ts"; +import { Query } from "../../feathers/mod.ts"; +import { FilterQueryOptions, FilterSettings } from "./declarations.ts"; + +const parse = (value: any) => + typeof value !== "undefined" ? parseInt(value, 10) : value; + +const isPlainObject = (value: any) => + _.isObject(value) && value.constructor === {}.constructor; + +const validateQueryProperty = (query: any, operators: string[] = []): Query => { + if (!isPlainObject(query)) { + return query; + } + + for (const key of Object.keys(query)) { + if (key.startsWith("$") && !operators.includes(key)) { + throw new BadRequest(`Invalid query parameter ${key}`, query); + } + + const value = query[key]; + + if (isPlainObject(value)) { + query[key] = validateQueryProperty(value, operators); + } + } + + return { + ...query, + }; +}; + +const getFilters = (query: Query, settings: FilterQueryOptions) => { + const filterNames = Object.keys(settings.filters as object); + + return filterNames.reduce((current, key) => { + const queryValue = query[key]; + const filter = settings.filters?.[key]; + + if (filter) { + const value = + typeof filter === "function" + ? filter(queryValue, settings) + : queryValue; + + if (value !== undefined) { + current[key] = value; + } + } + + return current; + }, {} as { [key: string]: any }); +}; + +const getQuery = (query: Query, settings: FilterQueryOptions) => { + const keys = Object.keys(query).concat( + Object.getOwnPropertySymbols(query) as any as string[] + ); + + return keys.reduce((result, key) => { + if (typeof key === "string" && key.startsWith("$")) { + if (settings.filters?.[key] === undefined) { + throw new BadRequest(`Invalid filter value ${key}`); + } + } else { + result[key] = validateQueryProperty(query[key], settings.operators); + } + + return result; + }, {} as Query); +}; + +export const OPERATORS = [ + "$in", + "$nin", + "$lt", + "$lte", + "$gt", + "$gte", + "$ne", + "$or", +]; + +export const FILTERS: FilterSettings = { + $skip: (value: any) => parse(value), + $sort: (sort: any): { [key: string]: number } => { + if (typeof sort !== "object" || Array.isArray(sort)) { + return sort; + } + + return Object.keys(sort).reduce((result, key) => { + result[key] = + typeof sort[key] === "object" ? sort[key] : parse(sort[key]); + + return result; + }, {} as { [key: string]: number }); + }, + $limit: (_limit: any, { paginate }: FilterQueryOptions) => { + const limit = parse(_limit); + + if (paginate && (paginate.default || paginate.max)) { + const base = paginate.default || 0; + const lower = + typeof limit === "number" && !isNaN(limit) && limit >= 0 ? limit : base; + const upper = + typeof paginate.max === "number" ? paginate.max : Number.MAX_VALUE; + + return Math.min(lower, upper); + } + + return limit; + }, + $select: (select: any) => { + if (Array.isArray(select)) { + return select.map((current) => `${current}`); + } + + return select; + }, + $or: (or: any, { operators }: FilterQueryOptions) => { + if (Array.isArray(or)) { + return or.map((current) => validateQueryProperty(current, operators)); + } + + return or; + }, +}; + +/** + * Converts Feathers special query parameters and pagination settings + * and returns them separately as `filters` and the rest of the query + * as `query`. `options` also gets passed the pagination settings and + * a list of additional `operators` to allow when querying properties. + * + * @param query The initial query + * @param options Options for filtering the query + * @returns An object with `query` which contains the query without `filters` + * and `filters` which contains the converted values for each filter. + */ +export function filterQuery(_query: Query, options: FilterQueryOptions = {}) { + const query = _query || {}; + const settings = { + ...options, + filters: { + ...FILTERS, + ...options.filters, + }, + operators: OPERATORS.concat(options.operators || []), + }; + + return { + filters: getFilters(query, settings), + query: getQuery(query, settings), + }; +} diff --git a/main/adapter-commons/src/service.ts b/main/adapter-commons/src/service.ts index 53dd94e73d..cfece51427 100644 --- a/main/adapter-commons/src/service.ts +++ b/main/adapter-commons/src/service.ts @@ -1,84 +1,205 @@ -import { NotImplemented, BadRequest, MethodNotAllowed } from '../../errors/src/index.ts'; -import type { ServiceMethods, Params, Id, NullableId, Paginated } from '../../feathers/src/declarations.ts'; -import { filterQuery } from './filter-query.ts'; - -const callMethod = (self: any, name: any, ...args: any[]) => { - if (typeof self[name] !== 'function') { - return Promise.reject(new NotImplemented(`Method ${name} not available`)); - } - - return self[name](...args); -}; +// deno-lint-ignore-file require-await +import { BadRequest, MethodNotAllowed } from "../../errors/mod.ts"; +import { Id, NullableId, Paginated, Query } from "../../feathers/mod.ts"; +import { + AdapterParams, + AdapterServiceOptions, + InternalServiceMethods, + PaginationOptions, +} from "./declarations.ts"; +import { filterQuery } from "./query.ts"; const alwaysMulti: { [key: string]: boolean } = { find: true, get: false, - update: false + update: false, }; -export interface ServiceOptions { - events?: string[]; - multi: boolean|string[]; - id: string; - paginate: { - default?: number; - max?: number; +/** + * An abstract base class that a database adapter can extend from to implement the + * `__find`, `__get`, `__update`, `__patch` and `__remove` methods. + */ +export abstract class AdapterBase< + T = any, + D = Partial, + P extends AdapterParams = AdapterParams, + O extends AdapterServiceOptions = AdapterServiceOptions +> implements InternalServiceMethods +{ + options: O; + + constructor(options: O) { + this.options = { + id: "id", + events: [], + paginate: false, + multi: false, + filters: {}, + operators: [], + ...options, + }; } - whitelist?: string[]; - allow: string[]; - filters: string[]; -} -export interface AdapterOptions extends Pick { - Model?: M; -} + get id() { + return this.options.id; + } -export interface AdapterParams extends Params { - adapter?: Partial>; -} + get events() { + return this.options.events; + } -/** - * Hook-less (internal) service methods. Directly call database adapter service methods - * without running any service-level hooks. This can be useful if you need the raw data - * from the service and don't want to trigger any of its hooks. - * - * Important: These methods are only available internally on the server, not on the client - * side and only for the Feathers database adapters. - * - * These methods do not trigger events. - * - * @see {@link https://docs.feathersjs.com/guides/migrating.html#hook-less-service-methods} - */ -export interface InternalServiceMethods> { + /** + * Check if this adapter allows multiple updates for a method. + * @param method The method name to check. + * @param params The service call params. + * @returns Wether or not multiple updates are allowed. + */ + allowsMulti(method: string, params: P = {} as P) { + const always = alwaysMulti[method]; + + if (typeof always !== "undefined") { + return always; + } + + const { multi } = this.getOptions(params); + + if (multi === true || multi === false) { + return multi; + } + + return multi?.includes(method); + } /** - * Retrieve all resources from this service, skipping any service-level hooks. + * Returns the combined options for a service call. Options will be merged + * with `this.options` and `params.adapter` for dynamic overrides. + * + * @param params The parameters for the service method call + * @returns The actual options for this call + */ + getOptions(params: P): O { + const paginate = + params.paginate !== undefined ? params.paginate : this.options.paginate; + + return { + ...this.options, + paginate, + ...params.adapter, + }; + } + + /** + * Sanitize the incoming data, e.g. removing invalid keywords etc. + * + * @param data The data to sanitize + * @param _params Service call parameters + * @returns The sanitized data + */ + async sanitizeData>(data: X, _params?: P) { + return data; + } + + /** + * Returns a sanitized version of `params.query`, converting filter values + * (like $limit and $skip) into the expected type. Will throw an error if + * a `$` prefixed filter or operator value that is not allowed in `filters` + * or `operators` is encountered. + * + * @param params The service call parameter. + * @returns A new object containing the sanitized query. + */ + async sanitizeQuery(params: P = {} as P): Promise { + const options = this.getOptions(params); + const { query, filters } = filterQuery(params.query!, options); + + return { + ...filters, + ...query, + }; + } + + abstract $find( + _params?: P & { paginate?: PaginationOptions } + ): Promise>; + abstract $find(_params?: P & { paginate: false }): Promise; + abstract $find(params?: P): Promise>; + + /** + * Retrieve all resources from this service, skipping any service-level hooks but sanitize the query + * with allowed filters and properties by calling `sanitizeQuery`. * * @param params - Service call parameters {@link Params} * @see {@link HookLessServiceMethods} * @see {@link https://docs.feathersjs.com/api/services.html#find-params|Feathers API Documentation: .find(params)} */ - _find (params?: AdapterParams): Promise>; + async _find( + _params?: P & { paginate?: PaginationOptions } + ): Promise>; + async _find(_params?: P & { paginate: false }): Promise; + async _find(params?: P): Promise>; + async _find(params?: P): Promise> { + const query = await this.sanitizeQuery(params); + + return this.$find({ + ...params, + query, + } as P & { paginate?: PaginationOptions | false }); + } + + abstract $get(id: Id, params?: P): Promise; /** - * Retrieve a single resource matching the given ID, skipping any service-level hooks. + * Retrieve a single resource matching the given ID, skipping any service-level hooks but sanitize the query + * with allowed filters and properties by calling `sanitizeQuery`. * * @param id - ID of the resource to locate * @param params - Service call parameters {@link Params} * @see {@link HookLessServiceMethods} * @see {@link https://docs.feathersjs.com/api/services.html#get-id-params|Feathers API Documentation: .get(id, params)} */ - _get (id: Id, params?: AdapterParams): Promise; + async _get(id: Id, params?: P): Promise { + const query = await this.sanitizeQuery(params); + + return this.$get(id, { + ...params, + query, + } as P); + } + + abstract $create(data: Partial, params?: P): Promise; + abstract $create(data: Partial[], params?: P): Promise; + abstract $create( + data: Partial | Partial[], + params?: P + ): Promise; /** - * Create a new resource for this service, skipping any service-level hooks. + * Create a new resource for this service, skipping any service-level hooks, sanitize the data + * and check if multiple updates are allowed. * * @param data - Data to insert into this service. * @param params - Service call parameters {@link Params} * @see {@link HookLessServiceMethods} * @see {@link https://docs.feathersjs.com/api/services.html#create-data-params|Feathers API Documentation: .create(data, params)} */ - _create (data: D | D[], params?: AdapterParams): Promise; + async _create(data: Partial, params?: P): Promise; + async _create(data: Partial[], params?: P): Promise; + async _create(data: Partial | Partial[], params?: P): Promise; + async _create(data: Partial | Partial[], params?: P): Promise { + if (Array.isArray(data) && !this.allowsMulti("create", params)) { + throw new MethodNotAllowed("Can not create multiple entries"); + } + + const payload = Array.isArray(data) + ? await Promise.all( + data.map((current) => this.sanitizeData(current, params)) + ) + : await this.sanitizeData(data, params); + + return this.$create(payload, params); + } + + abstract $update(id: Id, data: D, params?: P): Promise; /** * Replace any resources matching the given ID with the given data, skipping any service-level hooks. @@ -89,10 +210,33 @@ export interface InternalServiceMethods> { * @see {@link HookLessServiceMethods} * @see {@link https://docs.feathersjs.com/api/services.html#update-id-data-params|Feathers API Documentation: .update(id, data, params)} */ - _update (id: Id, data: D, params?: AdapterParams): Promise; + async _update(id: Id, data: D, params?: P): Promise { + if (id === null || Array.isArray(data)) { + throw new BadRequest( + "You can not replace multiple instances. Did you mean 'patch'?" + ); + } + + const payload = await this.sanitizeData(data, params); + const query = await this.sanitizeQuery(params); + + return this.$update(id, payload, { + ...params, + query, + } as P); + } + + abstract $patch(id: null, data: Partial, params?: P): Promise; + abstract $patch(id: Id, data: Partial, params?: P): Promise; + abstract $patch( + id: NullableId, + data: Partial, + params?: P + ): Promise; /** * Merge any resources matching the given ID with the given data, skipping any service-level hooks. + * Sanitizes the query and data and checks it multiple updates are allowed. * * @param id - ID of the resource to be patched * @param data - Data to merge with the current resource. @@ -100,132 +244,49 @@ export interface InternalServiceMethods> { * @see {@link HookLessServiceMethods} * @see {@link https://docs.feathersjs.com/api/services.html#patch-id-data-params|Feathers API Documentation: .patch(id, data, params)} */ - _patch (id: NullableId, data: D, params?: AdapterParams): Promise; + async _patch(id: null, data: Partial, params?: P): Promise; + async _patch(id: Id, data: Partial, params?: P): Promise; + async _patch(id: NullableId, data: Partial, params?: P): Promise; + async _patch(id: NullableId, data: Partial, params?: P): Promise { + if (id === null && !this.allowsMulti("patch", params)) { + throw new MethodNotAllowed("Can not patch multiple entries"); + } + + const { $limit, ...query } = await this.sanitizeQuery(params); + const payload = await this.sanitizeData(data, params); + + return this.$patch(id, payload, { + ...params, + query, + } as P); + } + + abstract $remove(id: null, params?: P): Promise; + abstract $remove(id: Id, params?: P): Promise; + abstract $remove(id: NullableId, params?: P): Promise; /** * Remove resources matching the given ID from the this service, skipping any service-level hooks. + * Sanitized the query and verifies that multiple updates are allowed. * * @param id - ID of the resource to be removed * @param params - Service call parameters {@link Params} * @see {@link HookLessServiceMethods} * @see {@link https://docs.feathersjs.com/api/services.html#remove-id-params|Feathers API Documentation: .remove(id, params)} */ - _remove (id: NullableId, params?: AdapterParams): Promise; -} - -export class AdapterService< - T = any, - D = Partial, - O extends Partial = Partial -> implements ServiceMethods, D> { - options: ServiceOptions & O; - - constructor (options: O) { - this.options = Object.assign({ - id: 'id', - events: [], - paginate: {}, - multi: false, - filters: [], - allow: [] - }, options); - } - - get id () { - return this.options.id; - } - - get events () { - return this.options.events; - } - - filterQuery (params: AdapterParams = {}, opts: any = {}) { - const paginate = typeof params.paginate !== 'undefined' - ? params.paginate - : this.getOptions(params).paginate; - const { query = {} } = params; - const options = Object.assign({ - operators: this.options.whitelist || this.options.allow || [], - filters: this.options.filters, - paginate - }, opts); - const result = filterQuery(query, options); - - return Object.assign(result, { paginate }); - } - - allowsMulti (method: string, params: AdapterParams = {}) { - const always = alwaysMulti[method]; - - if (typeof always !== 'undefined') { - return always; - } - - const { multi: option } = this.getOptions(params); - - if (option === true || option === false) { - return option; - } - - return option.includes(method); - } - - getOptions (params: AdapterParams): ServiceOptions & { model?: any } { - return { - ...this.options, - ...params.adapter - } - } - - find (params?: AdapterParams): Promise> { - return callMethod(this, '_find', params); - } - - get (id: Id, params?: AdapterParams): Promise { - return callMethod(this, '_get', id, params); - } - - create (data: Partial, params?: AdapterParams): Promise; - create (data: Partial[], params?: AdapterParams): Promise; - create (data: Partial | Partial[], params?: AdapterParams): Promise { - if (Array.isArray(data) && !this.allowsMulti('create', params)) { - return Promise.reject(new MethodNotAllowed('Can not create multiple entries')); + async _remove(id: null, params?: P): Promise; + async _remove(id: Id, params?: P): Promise; + async _remove(id: NullableId, params?: P): Promise; + async _remove(id: NullableId, params?: P): Promise { + if (id === null && !this.allowsMulti("remove", params)) { + throw new MethodNotAllowed("Can not remove multiple entries"); } - return callMethod(this, '_create', data, params); - } - - update (id: Id, data: D, params?: AdapterParams): Promise { - if (id === null || Array.isArray(data)) { - return Promise.reject(new BadRequest( - 'You can not replace multiple instances. Did you mean \'patch\'?' - )); - } + const { $limit, ...query } = await this.sanitizeQuery(params); - return callMethod(this, '_update', id, data, params); + return this.$remove(id, { + ...params, + query, + } as P); } - - patch (id: Id, data: Partial, params?: AdapterParams): Promise; - patch (id: null, data: Partial, params?: AdapterParams): Promise; - patch (id: NullableId, data: Partial, params?: AdapterParams): Promise; - patch (id: NullableId, data: Partial, params?: AdapterParams): Promise { - if (id === null && !this.allowsMulti('patch', params)) { - return Promise.reject(new MethodNotAllowed('Can not patch multiple entries')); - } - - return callMethod(this, '_patch', id, data, params); - } - - remove (id: Id, params?: AdapterParams): Promise; - remove (id: null, params?: AdapterParams): Promise; - remove (id: NullableId, params?: AdapterParams): Promise; - remove (id: NullableId, params?: AdapterParams): Promise { - if (id === null && !this.allowsMulti('remove', params)) { - return Promise.reject(new MethodNotAllowed('Can not remove multiple entries')); - } - - return callMethod(this, '_remove', id, params); - } - - async setup () {} } diff --git a/main/adapter-commons/src/sort.ts b/main/adapter-commons/src/sort.ts index 0781c61d8d..281c197397 100644 --- a/main/adapter-commons/src/sort.ts +++ b/main/adapter-commons/src/sort.ts @@ -1,64 +1,104 @@ // Sorting algorithm taken from NeDB (https://github.com/louischatriot/nedb) // See https://github.com/louischatriot/nedb/blob/e3f0078499aa1005a59d0c2372e425ab789145c1/lib/model.js#L189 -function compareNSB (a: any, b: any): 0 | 1 | -1 { - if (a < b) { return -1; } - if (a > b) { return 1; } +export function compareNSB(a: any, b: any) { + if (a < b) { + return -1; + } + if (a > b) { + return 1; + } return 0; } -function compareArrays (a: any, b: any) { - let i; - let comp; +export function compareArrays(a: any[], b: any[]) { + for (let i = 0, l = Math.min(a.length, b.length); i < l; i++) { + const comparison = compare(a[i], b[i]); - for (i = 0; i < Math.min(a.length, b.length); i += 1) { - comp = compare(a[i], b[i]); - - if (comp !== 0) { return comp; } + if (comparison !== 0) { + return comparison; + } } // Common section was identical, longest one wins return compareNSB(a.length, b.length); } -function compare (a: any, b: any, compareStrings: any = compareNSB): any { +export function compare( + a: any, + b: any, + compareStrings: any = compareNSB +): 0 | 1 | -1 { + if (a === b) { + return 0; + } + // undefined - if (a === undefined) { return b === undefined ? 0 : -1; } - if (b === undefined) { return a === undefined ? 0 : 1; } + if (a === undefined) { + return -1; + } + if (b === undefined) { + return 1; + } // null - if (a === null) { return b === null ? 0 : -1; } - if (b === null) { return a === null ? 0 : 1; } + if (a === null) { + return -1; + } + if (b === null) { + return 1; + } // Numbers - if (typeof a === 'number') { return typeof b === 'number' ? compareNSB(a, b) : -1; } - if (typeof b === 'number') { return typeof a === 'number' ? compareNSB(a, b) : 1; } + if (typeof a === "number") { + return typeof b === "number" ? compareNSB(a, b) : -1; + } + if (typeof b === "number") { + return 1; + } // Strings - if (typeof a === 'string') { return typeof b === 'string' ? compareStrings(a, b) : -1; } - if (typeof b === 'string') { return typeof a === 'string' ? compareStrings(a, b) : 1; } + if (typeof a === "string") { + return typeof b === "string" ? compareStrings(a, b) : -1; + } + if (typeof b === "string") { + return 1; + } // Booleans - if (typeof a === 'boolean') { return typeof b === 'boolean' ? compareNSB(a, b) : -1; } - if (typeof b === 'boolean') { return typeof a === 'boolean' ? compareNSB(a, b) : 1; } + if (typeof a === "boolean") { + return typeof b === "boolean" ? compareNSB(a, b) : -1; + } + if (typeof b === "boolean") { + return 1; + } // Dates - if (a instanceof Date) { return b instanceof Date ? compareNSB(a.getTime(), b.getTime()) : -1; } - if (b instanceof Date) { return a instanceof Date ? compareNSB(a.getTime(), b.getTime()) : 1; } + if (a instanceof Date) { + return b instanceof Date ? compareNSB(a.getTime(), b.getTime()) : -1; + } + if (b instanceof Date) { + return 1; + } // Arrays (first element is most significant and so on) - if (Array.isArray(a)) { return Array.isArray(b) ? compareArrays(a, b) : -1; } - if (Array.isArray(b)) { return Array.isArray(a) ? compareArrays(a, b) : 1; } + if (Array.isArray(a)) { + return Array.isArray(b) ? compareArrays(a, b) : -1; + } + if (Array.isArray(b)) { + return 1; + } // Objects const aKeys = Object.keys(a).sort(); const bKeys = Object.keys(b).sort(); - let comp = 0; - for (let i = 0; i < Math.min(aKeys.length, bKeys.length); i += 1) { - comp = compare(a[aKeys[i]], b[bKeys[i]]); + for (let i = 0, l = Math.min(aKeys.length, bKeys.length); i < l; i++) { + const comparison = compare(a[aKeys[i]], b[bKeys[i]]); - if (comp !== 0) { return comp; } + if (comparison !== 0) { + return comparison; + } } return compareNSB(aKeys.length, bKeys.length); @@ -66,45 +106,31 @@ function compare (a: any, b: any, compareStrings: any = compareNSB): any { // An in-memory sorting function according to the // $sort special query parameter -export function sorter ($sort: any) { - let sortLevels = 0; // > 0 if $sort has tags with '.' i.e. '{a: 1, b: -1, "c.x.z": 1}' - - const getVal = (a: any, sortKeys: any[]) => { - const keys = sortKeys.map(key => key); - let val = a; - do { - const key = keys.shift(); - val = val[key]; - } while (keys.length); - - return val; - }; +export function sorter($sort: { [key: string]: -1 | 1 }) { + const get = (value: any, path: string[]) => + path.reduce((value, key) => value[key], value); - const criteria = Object.keys($sort).map(key => { + const compares = Object.keys($sort).map((key) => { const direction = $sort[key]; - const keys = key.split('.'); - sortLevels += (keys.length > 1) ? 1 : 0; + const path = key.split("."); - return { keys, direction }; + if (path.length === 1) { + return (a: any, b: any) => direction * compare(a[key], b[key]); + } else { + return (a: any, b: any) => + direction * compare(get(a, path), get(b, path)); + } }); return function (a: any, b: any) { - let compared; + for (const compare of compares) { + const comparasion = compare(a, b); - for (const criterion of criteria) { - if (sortLevels) { - compared = criterion.direction * compare(getVal(a, criterion.keys), getVal(b, criterion.keys)); - } else { - compared = criterion.direction * compare(a[criterion.keys[0]], b[criterion.keys[0]]); - } - - if (compared !== 0) { - return compared; + if (comparasion !== 0) { + return comparasion; } } return 0; }; } - -export { compareNSB, compareArrays, compare } \ No newline at end of file diff --git a/main/adapter-commons/test/commons.test.ts b/main/adapter-commons/test/commons.test.ts index 5ecc9a6b7f..353eafdb43 100644 --- a/main/adapter-commons/test/commons.test.ts +++ b/main/adapter-commons/test/commons.test.ts @@ -1,67 +1,96 @@ -import { it, assertEquals } from '../../commons/src/index.ts' -import { select } from '../src/index.ts'; +import { + describe, + it, + assertStrictEquals, + assertEquals, +} from "../../commons/mod.ts"; +import { select } from "../mod.ts"; -it('adapter-commons: select', () => { - const selector = select({ - query: { $select: ['name', 'age'] } - }); +describe("@feathersjs/adapter-commons", () => { + describe("select", () => { + it("select", () => { + const selector = select({ + query: { $select: ["name", "age"] }, + }); - return Promise.resolve({ - name: 'David', - age: 3, - test: 'me' - }).then(selector).then(result => assertEquals(result, { - name: 'David', - age: 3 - })); -}); + return Promise.resolve({ + name: "David", + age: 3, + test: "me", + }) + .then(selector) + .then((result) => + assertEquals(result, { + name: "David", + age: 3, + }) + ); + }); -it('adapter-commons: select with arrays', () => { - const selector = select({ - query: { $select: ['name', 'age'] } - }); + it("select with arrays", () => { + const selector = select({ + query: { $select: ["name", "age"] }, + }); - return Promise.resolve([{ - name: 'David', - age: 3, - test: 'me' - }, { - name: 'D', - age: 4, - test: 'you' - }]).then(selector).then(result => assertEquals(result, [{ - name: 'David', - age: 3 - }, { - name: 'D', - age: 4 - }])); -}); + return Promise.resolve([ + { + name: "David", + age: 3, + test: "me", + }, + { + name: "D", + age: 4, + test: "you", + }, + ]) + .then(selector) + .then((result) => + assertEquals(result, [ + { + name: "David", + age: 3, + }, + { + name: "D", + age: 4, + }, + ]) + ); + }); -it('adapter-commons: select with no query', () => { - const selector = select({}); - const data = { - name: 'David' - }; + it("select with no query", () => { + const selector = select({}); + const data = { + name: "David", + }; - return Promise.resolve(data).then(selector).then(result => - assertEquals(result, data) - ); -}); + return Promise.resolve(data) + .then(selector) + .then((result) => assertStrictEquals(result, data)); + }); -it('adapter-commons: select with other fields', () => { - const selector = select({ - query: { $select: [ 'name' ] } - }, 'id'); - const data = { - id: 'me', - name: 'David', - age: 10 - }; + it("select with other fields", () => { + const selector = select( + { + query: { $select: ["name"] }, + }, + "id" + ); + const data = { + id: "me", + name: "David", + age: 10, + }; - return Promise.resolve(data) - .then(selector) - .then(result => { - assertEquals(result, { id: 'me', name: 'David' }) + return Promise.resolve(data) + .then(selector) + .then((result) => + assertEquals(result, { + id: "me", + name: "David", + }) + ); }); + }); }); diff --git a/main/adapter-commons/test/filter-query.test.ts b/main/adapter-commons/test/filter-query.test.ts deleted file mode 100644 index c9a971da21..0000000000 --- a/main/adapter-commons/test/filter-query.test.ts +++ /dev/null @@ -1,256 +0,0 @@ -import { it, assert, assertEquals, assertStrictEquals, assertThrows } from '../../commons/src/testing.ts' -import { errors } from '../../errors/src/index.ts' -import { objectId } from 'https://deno.land/x/objectid@0.2.0/mod.ts'; - -import { filterQuery } from '../src/filter-query.ts'; - -// const { ObjectId } = Bson -const makeLimitQuery = () => ({ $limit: 1 }) -const makeSkipQuery = () => ({ $skip: 1 }) -const makeSelectQuery = () => ({ $select: 1 }) - -// describe('@feathersjs/adapter-commons/filterQuery', () => { -// describe('$sort', () => { -it('returns $sort when present in query', () => { - const originalQuery = { $sort: { name: 1 } }; - const { filters, query } = filterQuery(originalQuery); - - assertStrictEquals(filters.$sort.name, 1); - assertEquals(query, {}); - assertEquals(originalQuery, { - $sort: { name: 1 } - }, 'does not modify original query'); -}); - -it('returns $sort when present in query as an object', () => { - const { filters, query } = filterQuery({ $sort: { name: { something: 10 } } }); - - assertStrictEquals(filters.$sort.name.something, 10); - assertEquals(query, {}); -}); - -it('converts strings in $sort', () => { - const { filters, query } = filterQuery({ $sort: { test: '-1' } }); - - assertStrictEquals(filters.$sort.test, -1); - assertEquals(query, {}); -}); - -it('does not convert $sort arrays', () => { - const $sort = [ [ 'test', '-1' ], [ 'a', '1' ] ]; - const { filters, query } = filterQuery({ $sort }); - - assertEquals(filters.$sort, $sort); - assertEquals(query, {}); -}); - -it('throws an error when special parameter is not known', () => { - try { - const query = { $foo: 1 }; - filterQuery(query); - assert(false, 'Should never get here'); - } catch (error: any) { - assertStrictEquals(error.name, 'BadRequest'); - assertStrictEquals(error.message, 'Invalid query parameter $foo'); - } -}); - -it('returns undefined when not present in query', () => { - const query = { foo: 1 }; - const { filters } = filterQuery(query); - - assertStrictEquals(filters.$sort, undefined); -}); - -it('returns $limit when present in query', () => { - const limitQuery = makeLimitQuery() - const { filters, query } = filterQuery(limitQuery); - - assertStrictEquals(filters.$limit, 1); - assertEquals(query, {}); -}); - -it('returns undefined when not present in query', () => { - const query = { foo: 1 }; - const { filters } = filterQuery(query); - - assertStrictEquals(filters.$limit, undefined); -}); - -it('removes $limit from query when present', () => { - const limitQuery = makeLimitQuery() - assertEquals(filterQuery(limitQuery).query, {}); -}); - -it('parses $limit strings into integers (#4)', () => { - const { filters } = filterQuery({ $limit: '2' }); - - assertStrictEquals(filters.$limit, 2); -}); - -it('allows $limit 0', () => { - const { filters } = filterQuery({ $limit: 0 }, { default: 10 }); - - assertStrictEquals(filters.$limit, 0); -}); - -// describe('pagination', () => { -it('limits with default pagination', () => { - const { filters } = filterQuery({}, { paginate: { default: 10 } }); - - assertStrictEquals(filters.$limit, 10); -}); - -it('limits with max pagination', () => { - const { filters } = filterQuery({ $limit: 20 }, { paginate: { default: 5, max: 10 } }); - const { filters: filtersNeg } = filterQuery({ $limit: -20 }, { paginate: { default: 5, max: 10 } }); - - assertStrictEquals(filters.$limit, 10); - assertStrictEquals(filtersNeg.$limit, 10); -}); - -it('limits with default pagination when not a number', () => { - const { filters } = filterQuery({ $limit: 'something' }, { paginate: { default: 5, max: 10 } }); - - assertStrictEquals(filters.$limit, 5); -}); - -it('limits to 0 when no paginate.default and not a number', () => { - const { filters } = filterQuery({ $limit: 'something' }, { paginate: { max: 10 } }); - - assertStrictEquals(filters.$limit, 0); -}); - -it('still uses paginate.max when there is no paginate.default (#2104)', () => { - const { filters } = filterQuery({ $limit: 100 }, { paginate: { max: 10 } }); - - assertStrictEquals(filters.$limit, 10); -}); - -// describe('$skip', () => { -it('returns $skip when present in query', () => { - const skipQuery = makeSkipQuery() - const { filters } = filterQuery(skipQuery); - - assertStrictEquals(filters.$skip, 1); -}); - -it('removes $skip from query when present', () => { - const skipQuery = makeSkipQuery() - assertEquals(filterQuery(skipQuery).query, {}); -}); - -it('returns undefined when not present in query', () => { - const query = { foo: 1 }; - const { filters } = filterQuery(query); - - assertStrictEquals(filters.$skip, undefined); -}); - -it('parses $skip strings into integers (#4)', () => { - const { filters } = filterQuery({ $skip: '33' }); - - assertStrictEquals(filters.$skip, 33); -}); - -// describe('$select', () => { -it('returns $select when present in query', () => { - const selectQuery = makeSelectQuery() - const { filters } = filterQuery(selectQuery); - - assertStrictEquals(filters.$select, 1); -}); - -it('removes $select from query when present', () => { - const selectQuery = makeSelectQuery() - assertEquals(filterQuery(selectQuery).query, {}); -}); - -it('returns undefined when not present in query', () => { - const query = { foo: 1 }; - const { filters } = filterQuery(query); - - assertStrictEquals(filters.$select, undefined); -}); - -it('includes Symbols', () => { - const TEST = Symbol('testing'); - const original = { - [TEST]: 'message', - other: true, - sub: { [TEST]: 'othermessage' } - }; - - const { query } = filterQuery(original); - - assertEquals(query, { - [TEST]: 'message', - other: true, - sub: { [TEST]: 'othermessage' } - }); -}); - -it('only converts plain objects', () => { - const userId = objectId().toString(); - const original = { - userId - }; - - const { query } = filterQuery(original); - - assertEquals(query, original); -}); - -// describe('arrays', () => { -it('validates queries in arrays', () => { - assertThrows( - () => { - filterQuery({ - $or: [{ $exists: false }] - }); - }, - errors.BadRequest, - 'Invalid query parameter $exists' - ); -}); - -// describe('additional filters', () => { -it('throw error when not set as additionals', () => { - try { - filterQuery({ $select: 1, $known: 1 }); - assert(false, 'Should never get here'); - } catch (error: any) { - assertStrictEquals(error.message, 'Invalid query parameter $known'); - } -}); - -it('returns default and known additional filters (array)', () => { - const query = { $select: ['a', 'b'], $known: 1, $unknown: 1 }; - const { filters } = filterQuery(query, { filters: [ '$known', '$unknown' ] }); - - assertStrictEquals(filters.$unknown, 1); - assertStrictEquals(filters.$known, 1); - assertEquals(filters.$select, [ 'a', 'b' ]); -}); - -it('returns default and known additional filters (object)', () => { - const { filters } = filterQuery({ - $known: 1, - $select: 1 - }, { filters: { $known: (value: any) => value.toString() } }); - - assertStrictEquals(filters.$unknown, undefined); - assertStrictEquals(filters.$known, '1'); - assertStrictEquals(filters.$select, 1); -}); - -// describe('additional operators', () => { -it('returns query with default and known additional operators', () => { - const { query } = filterQuery({ - $ne: 1, $known: 1 - }, { operators: [ '$known' ] }); - - assertStrictEquals(query.$ne, 1); - assertStrictEquals(query.$known, 1); - assertStrictEquals(query.$unknown, undefined); -}); diff --git a/main/adapter-commons/test/fixture.ts b/main/adapter-commons/test/fixture.ts new file mode 100644 index 0000000000..08f3442493 --- /dev/null +++ b/main/adapter-commons/test/fixture.ts @@ -0,0 +1,129 @@ +// deno-lint-ignore-file require-await +import { + AdapterBase, + AdapterParams, + InternalServiceMethods, + PaginationOptions, +} from "../mod.ts"; +import { Id, NullableId, Paginated } from "../../feathers/mod.ts"; + +export type Data = { + id: Id; +}; + +export class MethodBase + extends AdapterBase, AdapterParams> + implements InternalServiceMethods +{ + async $find( + _params?: AdapterParams & { paginate?: PaginationOptions } + ): Promise>; + async $find(_params?: AdapterParams & { paginate: false }): Promise; + async $find(params?: AdapterParams): Promise>; + async $find( + params?: AdapterParams + ): Promise> { + if (params && params.paginate === false) { + return { + total: 0, + limit: 10, + skip: 0, + data: [], + }; + } + + return []; + } + + async $get(id: Id, _params?: AdapterParams): Promise { + return { id }; + } + + async $create( + data: Partial[], + _params?: AdapterParams + ): Promise; + async $create(data: Partial, _params?: AdapterParams): Promise; + async $create( + data: Partial | Partial[], + _params?: AdapterParams + ): Promise { + if (Array.isArray(data)) { + return [ + { + id: "something", + }, + ]; + } + + return { + id: "something", + ...data, + }; + } + + async create( + data: Partial | Partial[], + params?: AdapterParams + ): Promise { + return this._create(data, params); + } + + async $update(id: NullableId, _data: Data, _params?: AdapterParams) { + return Promise.resolve({ id } as Data); + } + + async $patch( + id: null, + _data: Partial, + _params?: AdapterParams + ): Promise; + async $patch( + id: Id, + _data: Partial, + _params?: AdapterParams + ): Promise; + async $patch( + id: NullableId, + _data: Partial, + _params?: AdapterParams + ): Promise { + if (id === null) { + return []; + } + + return { id }; + } + + async $remove(id: null, _params?: AdapterParams): Promise; + async $remove(id: Id, _params?: AdapterParams): Promise; + async $remove(id: NullableId, _params?: AdapterParams) { + if (id === null) { + return [] as Data[]; + } + + return { id }; + } +} + +export class MethodService extends MethodBase { + find(params?: AdapterParams): Promise> { + return this._find(params); + } + + get(id: Id, params?: AdapterParams): Promise { + return this._get(id, params); + } + + async update(id: Id, data: Data, params?: AdapterParams) { + return this._update(id, data, params); + } + + async patch(id: NullableId, data: Partial, params?: AdapterParams) { + return this._patch(id, data, params); + } + + async remove(id: NullableId, params?: AdapterParams) { + return this._remove(id, params); + } +} diff --git a/main/adapter-commons/test/query.test.ts b/main/adapter-commons/test/query.test.ts new file mode 100644 index 0000000000..af255cbed9 --- /dev/null +++ b/main/adapter-commons/test/query.test.ts @@ -0,0 +1,336 @@ +import { + describe, + it, + assertStrictEquals, + unreachable, + beforeEach, + assertThrows, + assertEquals, +} from "../../commons/mod.ts"; +import { ObjectId } from "https://deno.land/x/mongo@v0.31.1/mod.ts"; +import { filterQuery } from "../mod.ts"; +import { BadRequest } from "../../errors/mod.ts"; + +describe("@feathersjs/adapter-commons/filterQuery", () => { + describe("$sort", () => { + it("returns $sort when present in query", () => { + const originalQuery = { $sort: { name: 1 } }; + const { filters, query } = filterQuery(originalQuery); + + assertStrictEquals(filters.$sort.name, 1); + assertEquals(query, {}); + assertEquals( + originalQuery, + { + $sort: { name: 1 }, + }, + "does not modify original query" + ); + }); + + it("returns $sort when present in query as an object", () => { + const { filters, query } = filterQuery({ + $sort: { name: { something: 10 } }, + }); + + assertStrictEquals(filters.$sort.name.something, 10); + assertEquals(query, {}); + }); + + it("converts strings in $sort", () => { + const { filters, query } = filterQuery({ $sort: { test: "-1" } }); + + assertStrictEquals(filters.$sort.test, -1); + assertEquals(query, {}); + }); + + it("does not convert $sort arrays", () => { + const $sort = [ + ["test", "-1"], + ["a", "1"], + ]; + const { filters, query } = filterQuery({ $sort }); + + assertStrictEquals(filters.$sort, $sort); + assertEquals(query, {}); + }); + + it("throws an error when special parameter is not known", () => { + try { + const query = { $foo: 1 }; + filterQuery(query); + unreachable(); + } catch (error: any) { + assertStrictEquals(error.name, "BadRequest"); + assertStrictEquals(error.message, "Invalid filter value $foo"); + } + }); + + it("returns undefined when not present in query", () => { + const query = { foo: 1 }; + const { filters } = filterQuery(query); + + assertStrictEquals(filters.$sort, undefined); + }); + }); + + describe("$limit", () => { + let testQuery: any; + + beforeEach(() => { + testQuery = { $limit: 1 }; + }); + + it("returns $limit when present in query", () => { + const { filters, query } = filterQuery(testQuery); + + assertStrictEquals(filters.$limit, 1); + assertEquals(query, {}); + }); + + it("returns undefined when not present in query", () => { + const query = { foo: 1 }; + const { filters } = filterQuery(query); + + assertStrictEquals(filters.$limit, undefined); + }); + + it("removes $limit from query when present", () => { + assertEquals(filterQuery(testQuery).query, {}); + }); + + it("parses $limit strings into integers (#4)", () => { + const { filters } = filterQuery({ $limit: "2" }); + + assertStrictEquals(filters.$limit, 2); + }); + + it("allows $limit 0", () => { + const { filters } = filterQuery( + { $limit: 0 }, + { paginate: { default: 10 } } + ); + + assertStrictEquals(filters.$limit, 0); + }); + + describe("pagination", () => { + it("limits with default pagination", () => { + const { filters } = filterQuery({}, { paginate: { default: 10 } }); + const { filters: filtersNeg } = filterQuery( + { $limit: -20 }, + { paginate: { default: 5, max: 10 } } + ); + + assertStrictEquals(filters.$limit, 10); + assertStrictEquals(filtersNeg.$limit, 5); + }); + + it("limits with max pagination", () => { + const { filters } = filterQuery( + { $limit: 20 }, + { paginate: { default: 5, max: 10 } } + ); + + assertStrictEquals(filters.$limit, 10); + }); + + it("limits with default pagination when not a number", () => { + const { filters } = filterQuery( + { $limit: "something" }, + { paginate: { default: 5, max: 10 } } + ); + + assertStrictEquals(filters.$limit, 5); + }); + + it("limits to 0 when no paginate.default and not a number", () => { + const { filters } = filterQuery( + { $limit: "something" }, + { paginate: { max: 10 } } + ); + + assertStrictEquals(filters.$limit, 0); + }); + + it("still uses paginate.max when there is no paginate.default (#2104)", () => { + const { filters } = filterQuery( + { $limit: 100 }, + { paginate: { max: 10 } } + ); + + assertStrictEquals(filters.$limit, 10); + }); + }); + }); + + describe("$skip", () => { + let testQuery: any; + + beforeEach(() => { + testQuery = { $skip: 1 }; + }); + + it("returns $skip when present in query", () => { + const { filters } = filterQuery(testQuery); + + assertStrictEquals(filters.$skip, 1); + }); + + it("removes $skip from query when present", () => { + assertEquals(filterQuery(testQuery).query, {}); + }); + + it("returns undefined when not present in query", () => { + const query = { foo: 1 }; + const { filters } = filterQuery(query); + + assertStrictEquals(filters.$skip, undefined); + }); + + it("parses $skip strings into integers (#4)", () => { + const { filters } = filterQuery({ $skip: "33" }); + + assertStrictEquals(filters.$skip, 33); + }); + }); + + describe("$select", () => { + let testQuery: any; + + beforeEach(() => { + testQuery = { $select: 1 }; + }); + + it("returns $select when present in query", () => { + const { filters } = filterQuery(testQuery); + + assertStrictEquals(filters.$select, 1); + }); + + it("removes $select from query when present", () => { + assertEquals(filterQuery(testQuery).query, {}); + }); + + it("returns undefined when not present in query", () => { + const query = { foo: 1 }; + const { filters } = filterQuery(query); + + assertStrictEquals(filters.$select, undefined); + }); + + it("includes Symbols", () => { + const TEST = Symbol("testing"); + const original = { + [TEST]: "message", + other: true, + sub: { [TEST]: "othermessage" }, + }; + + const { query } = filterQuery(original); + + assertEquals(query, { + [TEST]: "message", + other: true, + sub: { [TEST]: "othermessage" }, + }); + }); + + it("only converts plain objects", () => { + const userId = new ObjectId(); + const original = { + userId, + }; + + const { query } = filterQuery(original); + + assertEquals(query, original); + }); + }); + + describe("arrays", () => { + it("validates queries in arrays", () => { + assertThrows( + () => { + filterQuery({ + $or: [{ $exists: false }], + }); + }, + BadRequest, + "Invalid query parameter $exists" + ); + }); + + it("allows default operators in $or", () => { + const { filters } = filterQuery({ + $or: [{ value: { $gte: 10 } }], + }); + + assertEquals(filters, { + $or: [{ value: { $gte: 10 } }], + }); + }); + }); + + describe("additional filters", () => { + it("throw error when not set as additionals", () => { + try { + filterQuery({ $select: 1, $known: 1 }); + unreachable(); + } catch (error: any) { + assertStrictEquals(error.message, "Invalid filter value $known"); + } + }); + + it("returns default and known additional filters (array)", () => { + const query = { $select: ["a", "b"], $known: 1, $unknown: 1 }; + const { filters } = filterQuery(query, { + filters: { + $known: true, + $unknown: true, + }, + }); + + assertStrictEquals(filters.$unknown, 1); + assertStrictEquals(filters.$known, 1); + assertEquals(filters.$select, ["a", "b"]); + }); + + it("returns default and known additional filters (object)", () => { + const { filters } = filterQuery( + { + $known: 1, + $select: 1, + }, + { filters: { $known: (value: any) => value.toString() } } + ); + + assertStrictEquals(filters.$unknown, undefined); + assertStrictEquals(filters.$known, "1"); + assertStrictEquals(filters.$select, 1); + }); + }); + + describe("additional operators", () => { + it("returns query with default and known additional operators", () => { + const { query } = filterQuery( + { + prop: { $ne: 1, $known: 1 }, + }, + { operators: ["$known"] } + ); + + assertEquals(query, { prop: { $ne: 1, $known: 1 } }); + }); + + it("throws an error with unknown query operator", () => { + assertThrows( + () => + filterQuery({ + prop: { $unknown: "something" }, + }), + "Invalid query parameter $unknown" + ); + }); + }); +}); diff --git a/main/adapter-commons/test/service.test.ts b/main/adapter-commons/test/service.test.ts index 4e3a106cd2..303e20dcfb 100644 --- a/main/adapter-commons/test/service.test.ts +++ b/main/adapter-commons/test/service.test.ts @@ -1,216 +1,224 @@ -/* eslint-disable @typescript-eslint/no-unused-vars */ -import { it, assert, assertEquals, assertStrictEquals } from '../../commons/src/index.ts' -import { NotImplemented } from '../../errors/src/index.ts'; -import { AdapterService, InternalServiceMethods } from '../src/index.ts'; -import { Params, Id, NullableId } from '../../feathers/src/declarations.ts'; - -const METHODS = [ 'find', 'get', 'create', 'update', 'patch', 'remove' ]; - -// describe('@feathersjs/adapter-commons/service', () => { -class CustomService extends AdapterService { -} - -// describe('errors when method does not exit', () => { -METHODS.forEach(method => { - it(`Undeclared Extended Methods: ${method}`, () => { - const service = new CustomService({}); - - // @ts-ignore suppress - return service[method]() - .then(() => { - throw new Error('Should never get here'); - }).catch((error: Error) => { - assert(error instanceof NotImplemented); - assertStrictEquals(error.message, `Method _${method} not available`); +/* eslint-disable @typescript-eslint/no-unused-vars, @typescript-eslint/ban-ts-comment */ +import { + describe, + it, + assertRejects, + assertStrictEquals, + assertEquals, +} from "../../commons/mod.ts"; +import { MethodNotAllowed } from "../../errors/mod.ts"; +import { createContext } from "../../feathers/mod.ts"; +import { MethodService } from "./fixture.ts"; + +const METHODS: ["find", "get", "create", "update", "patch", "remove"] = [ + "find", + "get", + "create", + "update", + "patch", + "remove", +]; + +describe("@feathersjs/adapter-commons/service", () => { + describe("works when methods exist", () => { + METHODS.forEach((method) => { + it(`${method}`, () => { + const service = new MethodService({}); + const args = []; + + if (method !== "find") { + args.push("test"); + } + + if (method === "update" || method === "patch") { + args.push({}); + } + + // @ts-ignore + service[method](...args); }); - }); -}); - -// // describe('works when methods exist', () => { -class MethodService extends AdapterService implements InternalServiceMethods { - _find (_params?: Params) { - return Promise.resolve([]); - } - - _get (id: Id, _params?: Params) { - return Promise.resolve({ id }); - } - - _create (data: Partial | Partial[], _params?: Params) { - return Promise.resolve(data); - } - - _update (id: NullableId, _data: any, _params?: Params) { - return Promise.resolve({ id }); - } - - _patch (id: NullableId, _data: any, _params?: Params) { - return Promise.resolve({ id }); - } - - _remove (id: NullableId, _params?: Params) { - return Promise.resolve({ id }); - } -} - -METHODS.forEach(method => { - it(`Internal Methods: ${method}`, () => { - const service = new MethodService({}); - const args = []; - - if (method !== 'find') { - args.push('test'); - } - - if (method === 'update' || method === 'patch') { - args.push({}); - } - - // @ts-ignore suppress - return service[method](...args); - }); -}); - -it('does not allow multi patch', () => { - const service = new MethodService({}); - - return service.patch(null, {}) - .then(() => assert(false)) - .catch(error => { - assertStrictEquals(error.name, 'MethodNotAllowed'); - assertStrictEquals(error.message, 'Can not patch multiple entries'); }); -}); -it('does not allow multi remove', () => { - const service = new MethodService({}); + it("does not allow multi patch", async () => { + const service = new MethodService({}); - return service.remove(null, {}) - .then(() => assert(false)) - .catch(error => { - assertStrictEquals(error.name, 'MethodNotAllowed'); - assertStrictEquals(error.message, 'Can not remove multiple entries'); + await assertRejects( + () => service.patch(null, {}), + MethodNotAllowed, + "Can not patch multiple entries" + ); }); -}); -it('does not allow multi create', () => { - const service = new MethodService({}); + it("does not allow multi remove", async () => { + const service = new MethodService({}); - return service.create([]) - .then(() => assert(false)) - .catch(error => { - assertStrictEquals(error.name, 'MethodNotAllowed'); - assertStrictEquals(error.message, 'Can not create multiple entries'); + await assertRejects( + () => service.remove(null, {}), + MethodNotAllowed, + "Can not remove multiple entries" + ); }); -}); -it('multi can be set to true', () => { - const service = new MethodService({}); + it("does not allow multi create", async () => { + const service = new MethodService({}); - service.options.multi = true; + await assertRejects( + () => service.create([], {}), + MethodNotAllowed, + "Can not create multiple entries" + ); + }); - return service.create([]) - .then(() => assert(true)); -}); + it("multi can be set to true", async () => { + const service = new MethodService({}); -it('filterQuery', () => { - const service = new CustomService({ - whitelist: [ '$something' ] - }); - const filtered = service.filterQuery({ - query: { $limit: 10, test: 'me' } - }); + service.options.multi = true; - assertEquals(filtered, { - paginate: {}, - filters: { $limit: 10 }, - query: { test: 'me' } + await service.create([]); + }); }); - const withWhitelisted = service.filterQuery({ - query: { $limit: 10, $something: 'else' } - }); + it("sanitizeQuery", async () => { + const service = new MethodService({ + filters: { + $something: true, + }, + operators: ["$test"], + }); - assertEquals(withWhitelisted, { - paginate: {}, - filters: { $limit: 10 }, - query: { $something: 'else' } + assertEquals( + await service.sanitizeQuery({ + // @ts-ignore + query: { $limit: "10", test: "me" }, + }), + { $limit: 10, test: "me" } + ); + + assertEquals( + await service.sanitizeQuery({ + adapter: { + paginate: { max: 2 }, + }, + query: { $limit: "10", test: "me" } as any, + }), + { $limit: 2, test: "me" } + ); + + await assertRejects( + () => + service.sanitizeQuery({ + query: { name: { $bla: "me" } }, + }), + "Invalid query parameter $bla" + ); + + assertEquals( + await service.sanitizeQuery({ + adapter: { + operators: ["$bla"], + }, + query: { name: { $bla: "Dave" } }, + }), + { name: { $bla: "Dave" } } + ); }); -}); -it('getOptions', () => { - const service = new AdapterService({ - multi: true - }); - const opts = service.getOptions({ - adapter: { - multi: [ 'create' ], + it("getOptions", () => { + const service = new MethodService({ + multi: true, paginate: { - default: 10, - max: 100 - } - } - }); + default: 1, + max: 10, + }, + }); + const opts = service.getOptions({ + adapter: { + multi: ["create"], + paginate: { + default: 10, + max: 100, + }, + }, + }); - assertEquals(opts, { - id: 'id', - events: [], - paginate: { default: 10, max: 100 }, - multi: [ 'create' ], - filters: [], - allow: [] + assertEquals(opts, { + id: "id", + events: [], + paginate: { default: 10, max: 100 }, + multi: ["create"], + filters: {}, + operators: [], + }); + + const notPaginated = service.getOptions({ + paginate: false, + }); + + assertEquals(notPaginated, { + id: "id", + events: [], + paginate: false, + multi: true, + filters: {}, + operators: [], + }); }); -}); -// 'allowsMulti with true' -const allowsMultiWithTrueService = new AdapterService({multi: true}); + describe("allowsMulti", () => { + describe("with true", () => { + const service = new MethodService({ multi: true }); -it('allowsMulti with true: returns true for multiple methods', () => { - assertStrictEquals(allowsMultiWithTrueService.allowsMulti('patch'), true); -}); + it("does return true for multiple methodes", () => { + assertEquals(service.allowsMulti("patch"), true); + }); -it('allowsMulti with true: returns false for always non-multiple methods', () => { - assertStrictEquals(allowsMultiWithTrueService.allowsMulti('update'), false); -}); + it("does return false for always non-multiple methodes", () => { + assertEquals(service.allowsMulti("update"), false); + }); -it('allowsMulti with true: returns true for unknown methods', () => { - assertStrictEquals(allowsMultiWithTrueService.allowsMulti('other'), true); -}); + it("does return true for unknown methods", () => { + assertEquals(service.allowsMulti("other"), true); + }); + }); -// 'allowsMulti with false' -const multiWithFalseService = new AdapterService({multi: false}); + describe("with false", () => { + const service = new MethodService({ multi: false }); -it('allowsMulti with false: returns false for multiple methods', () => { - assertStrictEquals(multiWithFalseService.allowsMulti('remove'), false); -}); + it("does return false for multiple methodes", () => { + assertEquals(service.allowsMulti("remove"), false); + }); -it('allowsMulti with false: returns true for always multiple methods', () => { - assertStrictEquals(multiWithFalseService.allowsMulti('find'), true); -}); + it("does return true for always multiple methodes", () => { + assertEquals(service.allowsMulti("find"), true); + }); -it('allowsMulti with false: returns false for unknown methods', () => { - assertStrictEquals(multiWithFalseService.allowsMulti('other'), false); -}); + it("does return false for unknown methods", () => { + assertEquals(service.allowsMulti("other"), false); + }); + }); -// 'allowsMulti with array' -const multiArrayService = new AdapterService({multi: ['create', 'get', 'other']}); + describe("with array", () => { + const service = new MethodService({ multi: ["create", "get", "other"] }); -it('allowsMulti with array: returns true for specified multiple methods', () => { - assertStrictEquals(multiArrayService.allowsMulti('create'), true); -}); + it("does return true for specified multiple methodes", () => { + assertEquals(service.allowsMulti("create"), true); + }); -it('allowsMulti with array: returns false for non-specified multiple methods', () => { - assertStrictEquals(multiArrayService.allowsMulti('patch'), false); -}); + it("does return false for non-specified multiple methodes", () => { + assertEquals(service.allowsMulti("patch"), false); + }); -it('allowsMulti with array: returns false for specified always multiple methods', () => { - assertStrictEquals(multiArrayService.allowsMulti('get'), false); -}); + it("does return false for specified always multiple methodes", () => { + assertEquals(service.allowsMulti("get"), false); + }); -it('allowsMulti with array: returns true for specified unknown methods', () => { - assertStrictEquals(multiArrayService.allowsMulti('other'), true); -}); + it("does return true for specified unknown methodes", () => { + assertEquals(service.allowsMulti("other"), true); + }); -it('allowsMulti with array: returns false for non-specified unknown methods', () => { - assertStrictEquals(multiArrayService.allowsMulti('another'), false); + it("does return false for non-specified unknown methodes", () => { + assertEquals(service.allowsMulti("another"), false); + }); + }); + }); }); diff --git a/main/adapter-commons/test/sort.test.ts b/main/adapter-commons/test/sort.test.ts index ad40afd6d9..5c768ecf58 100644 --- a/main/adapter-commons/test/sort.test.ts +++ b/main/adapter-commons/test/sort.test.ts @@ -1,289 +1,390 @@ -import { it, assertEquals, assert } from '../../commons/src/testing.ts' -import { sorter } from '../src/index.ts'; - -// describe('sorter', () => { -it('simple sorter', () => { - const array = [{ - name: 'David' - }, { - name: 'Eric' - }]; - - const sort = sorter({ - name: -1 - }); +import { + describe, + it, + assertStrictEquals, + beforeEach, + assertEquals, +} from "../../commons/mod.ts"; +import { sorter } from "../mod.ts"; - assertEquals(array.sort(sort), [{ - name: 'Eric' - }, { - name: 'David' - }]); -}); +describe("@feathersjs/adapter-commons", () => { + describe("sorter", () => { + it("simple sorter", () => { + const array = [ + { + name: "David", + }, + { + name: "Eric", + }, + ]; -it('simple sorter with arrays', () => { - const array = [{ - names: [ 'a', 'b' ] - }, { - names: [ 'c', 'd' ] - }]; + const sort = sorter({ + name: -1, + }); - const sort = sorter({ - names: -1 - }); + assertEquals(array.sort(sort), [ + { + name: "Eric", + }, + { + name: "David", + }, + ]); + }); - assertEquals(array.sort(sort), [{ - names: [ 'c', 'd' ] - }, { - names: [ 'a', 'b' ] - }]); -}); + it("simple sorter with arrays", () => { + const array = [ + { + names: ["a", "b"], + }, + { + names: ["c", "d"], + }, + ]; -it('simple sorter with objects', () => { - const array = [{ - names: { - first: 'Dave', - last: 'L' - } - }, { - names: { - first: 'A', - last: 'B' - } - }]; - - const sort = sorter({ - names: 1 - }); + const sort = sorter({ + names: -1, + }); - assertEquals(array.sort(sort), [{ - names: { - first: 'A', - last: 'B' - } - }, { - names: { - first: 'Dave', - last: 'L' - } - }]); -}); + assertEquals(array.sort(sort), [ + { + names: ["c", "d"], + }, + { + names: ["a", "b"], + }, + ]); + }); -it('two property sorter', () => { - const array = [{ - name: 'David', - counter: 0 - }, { - name: 'Eric', - counter: 1 - }, { - name: 'David', - counter: 1 - }, { - name: 'Eric', - counter: 0 - }]; - - const sort = sorter({ - name: -1, - counter: 1 - }); + it("simple sorter with objects", () => { + const array = [ + { + names: { + first: "Dave", + last: "L", + }, + }, + { + names: { + first: "A", + last: "B", + }, + }, + ]; - assertEquals(array.sort(sort), [ - { name: 'Eric', counter: 0 }, - { name: 'Eric', counter: 1 }, - { name: 'David', counter: 0 }, - { name: 'David', counter: 1 } - ]); -}); + const sort = sorter({ + names: 1, + }); -it('two property sorter with names', () => { - const array = [{ - name: 'David', - counter: 0 - }, { - name: 'Eric', - counter: 1 - }, { - name: 'Andrew', - counter: 1 - }, { - name: 'David', - counter: 1 - }, { - name: 'Andrew', - counter: 0 - }, { - name: 'Eric', - counter: 0 - }]; - - const sort = sorter({ - name: -1, - counter: 1 - }); + assertEquals(array.sort(sort), [ + { + names: { + first: "A", + last: "B", + }, + }, + { + names: { + first: "Dave", + last: "L", + }, + }, + ]); + }); - assertEquals(array.sort(sort), [ - { name: 'Eric', counter: 0 }, - { name: 'Eric', counter: 1 }, - { name: 'David', counter: 0 }, - { name: 'David', counter: 1 }, - { name: 'Andrew', counter: 0 }, - { name: 'Andrew', counter: 1 } - ]); -}); + it("two property sorter", () => { + const array = [ + { + name: "David", + counter: 0, + }, + { + name: "Eric", + counter: 1, + }, + { + name: "David", + counter: 1, + }, + { + name: "Eric", + counter: 0, + }, + ]; -it('three property sorter with names', () => { - const array = [{ - name: 'David', - counter: 0, - age: 2 - }, { - name: 'Eric', - counter: 1, - age: 2 - }, { - name: 'David', - counter: 1, - age: 1 - }, { - name: 'Eric', - counter: 0, - age: 1 - }, { - name: 'Andrew', - counter: 0, - age: 2 - }, { - name: 'Andrew', - counter: 0, - age: 1 - }]; - - const sort = sorter({ - name: -1, - counter: 1, - age: -1 - }); + const sort = sorter({ + name: -1, + counter: 1, + }); - assertEquals(array.sort(sort), [ - { name: 'Eric', counter: 0, age: 1 }, - { name: 'Eric', counter: 1, age: 2 }, - { name: 'David', counter: 0, age: 2 }, - { name: 'David', counter: 1, age: 1 }, - { name: 'Andrew', counter: 0, age: 2 }, - { name: 'Andrew', counter: 0, age: 1 } - ]); -}); + assertEquals(array.sort(sort), [ + { name: "Eric", counter: 0 }, + { name: "Eric", counter: 1 }, + { name: "David", counter: 0 }, + { name: "David", counter: 1 }, + ]); + }); -// describe('sorter mongoDB-like sorting on embedded objects', () => { -const makeData = () => ([ -{ _id: 1, item: { category: 'cake', type: 'chiffon' }, amount: 10 }, -{ _id: 2, item: { category: 'cookies', type: 'chocolate chip' }, amount: 50 }, -{ _id: 3, item: { category: 'cookies', type: 'chocolate chip' }, amount: 15 }, -{ _id: 4, item: { category: 'cake', type: 'lemon' }, amount: 30 }, -{ _id: 5, item: { category: 'cake', type: 'carrot' }, amount: 20 }, -{ _id: 6, item: { category: 'brownies', type: 'blondie' }, amount: 10 } -]) - -it('straight test', () => { - const data = makeData() - const sort = sorter({ - amount: -1 - }); + it("two property sorter with names", () => { + const array = [ + { + name: "David", + counter: 0, + }, + { + name: "Eric", + counter: 1, + }, + { + name: "Andrew", + counter: 1, + }, + { + name: "David", + counter: 1, + }, + { + name: "Andrew", + counter: 0, + }, + { + name: "Eric", + counter: 0, + }, + ]; - assertEquals(data.sort(sort), [ - { _id: 2, item: { category: 'cookies', type: 'chocolate chip' }, amount: 50 }, - { _id: 4, item: { category: 'cake', type: 'lemon' }, amount: 30 }, - { _id: 5, item: { category: 'cake', type: 'carrot' }, amount: 20 }, - { _id: 3, item: { category: 'cookies', type: 'chocolate chip' }, amount: 15 }, - { _id: 1, item: { category: 'cake', type: 'chiffon' }, amount: 10 }, - { _id: 6, item: { category: 'brownies', type: 'blondie' }, amount: 10 } - ]); -}); + const sort = sorter({ + name: -1, + counter: 1, + }); -it('embedded sort 1', () => { - const data = makeData() - const sort = sorter({ - 'item.category': 1, - 'item.type': 1 - }); + assertEquals(array.sort(sort), [ + { name: "Eric", counter: 0 }, + { name: "Eric", counter: 1 }, + { name: "David", counter: 0 }, + { name: "David", counter: 1 }, + { name: "Andrew", counter: 0 }, + { name: "Andrew", counter: 1 }, + ]); + }); - assertEquals(data.sort(sort), [ - { _id: 6, item: { category: 'brownies', type: 'blondie' }, amount: 10 }, - { _id: 5, item: { category: 'cake', type: 'carrot' }, amount: 20 }, - { _id: 1, item: { category: 'cake', type: 'chiffon' }, amount: 10 }, - { _id: 4, item: { category: 'cake', type: 'lemon' }, amount: 30 }, - { _id: 2, item: { category: 'cookies', type: 'chocolate chip' }, amount: 50 }, - { _id: 3, item: { category: 'cookies', type: 'chocolate chip' }, amount: 15 } - ]); -}); + it("three property sorter with names", () => { + const array = [ + { + name: "David", + counter: 0, + age: 2, + }, + { + name: "Eric", + counter: 1, + age: 2, + }, + { + name: "David", + counter: 1, + age: 1, + }, + { + name: "Eric", + counter: 0, + age: 1, + }, + { + name: "Andrew", + counter: 0, + age: 2, + }, + { + name: "Andrew", + counter: 0, + age: 1, + }, + ]; -it('embedded sort 2', () => { - const data = makeData() - const sort = sorter({ - 'item.category': 1, - 'item.type': 1, - amount: 1 + const sort = sorter({ + name: -1, + counter: 1, + age: -1, + }); + + assertEquals(array.sort(sort), [ + { name: "Eric", counter: 0, age: 1 }, + { name: "Eric", counter: 1, age: 2 }, + { name: "David", counter: 0, age: 2 }, + { name: "David", counter: 1, age: 1 }, + { name: "Andrew", counter: 0, age: 2 }, + { name: "Andrew", counter: 0, age: 1 }, + ]); + }); }); - assertEquals(data.sort(sort), [ - { _id: 6, item: { category: 'brownies', type: 'blondie' }, amount: 10 }, - { _id: 5, item: { category: 'cake', type: 'carrot' }, amount: 20 }, - { _id: 1, item: { category: 'cake', type: 'chiffon' }, amount: 10 }, - { _id: 4, item: { category: 'cake', type: 'lemon' }, amount: 30 }, - { _id: 3, item: { category: 'cookies', type: 'chocolate chip' }, amount: 15 }, - { _id: 2, item: { category: 'cookies', type: 'chocolate chip' }, amount: 50 } - ]); -}); + describe("sorter mongoDB-like sorting on embedded objects", () => { + let data: any[] = []; -it('embedded sort 3', () => { - const data = makeData() - const sort = sorter({ - 'item.category': 1, - 'item.type': 1, - amount: -1 - }); + beforeEach(() => { + data = [ + { _id: 1, item: { category: "cake", type: "chiffon" }, amount: 10 }, + { + _id: 2, + item: { category: "cookies", type: "chocolate chip" }, + amount: 50, + }, + { + _id: 3, + item: { category: "cookies", type: "chocolate chip" }, + amount: 15, + }, + { _id: 4, item: { category: "cake", type: "lemon" }, amount: 30 }, + { _id: 5, item: { category: "cake", type: "carrot" }, amount: 20 }, + { _id: 6, item: { category: "brownies", type: "blondie" }, amount: 10 }, + ]; + }); - assert.deepStrictEqual(data.sort(sort), [ - { _id: 6, item: { category: 'brownies', type: 'blondie' }, amount: 10 }, - { _id: 5, item: { category: 'cake', type: 'carrot' }, amount: 20 }, - { _id: 1, item: { category: 'cake', type: 'chiffon' }, amount: 10 }, - { _id: 4, item: { category: 'cake', type: 'lemon' }, amount: 30 }, - { _id: 2, item: { category: 'cookies', type: 'chocolate chip' }, amount: 50 }, - { _id: 3, item: { category: 'cookies', type: 'chocolate chip' }, amount: 15 } - ]); -}); + it("straight test", () => { + const sort = sorter({ + amount: -1, + }); -it('embedded sort 4', () => { - const data = makeData() - const sort = sorter({ - amount: -1, - 'item.category': 1 - }); + assertEquals(data.sort(sort), [ + { + _id: 2, + item: { category: "cookies", type: "chocolate chip" }, + amount: 50, + }, + { _id: 4, item: { category: "cake", type: "lemon" }, amount: 30 }, + { _id: 5, item: { category: "cake", type: "carrot" }, amount: 20 }, + { + _id: 3, + item: { category: "cookies", type: "chocolate chip" }, + amount: 15, + }, + { _id: 1, item: { category: "cake", type: "chiffon" }, amount: 10 }, + { _id: 6, item: { category: "brownies", type: "blondie" }, amount: 10 }, + ]); + }); - assert.deepStrictEqual(data.sort(sort), [ - { _id: 2, item: { category: 'cookies', type: 'chocolate chip' }, amount: 50 }, - { _id: 4, item: { category: 'cake', type: 'lemon' }, amount: 30 }, - { _id: 5, item: { category: 'cake', type: 'carrot' }, amount: 20 }, - { _id: 3, item: { category: 'cookies', type: 'chocolate chip' }, amount: 15 }, - { _id: 6, item: { category: 'brownies', type: 'blondie' }, amount: 10 }, - { _id: 1, item: { category: 'cake', type: 'chiffon' }, amount: 10 } - ]); -}); + it("embedded sort 1", () => { + const sort = sorter({ + "item.category": 1, + "item.type": 1, + }); -it('embedded sort 5', () => { - const data = makeData() - const sort = sorter({ - 'item.category': 1, - amount: 1 - }); + assertEquals(data.sort(sort), [ + { _id: 6, item: { category: "brownies", type: "blondie" }, amount: 10 }, + { _id: 5, item: { category: "cake", type: "carrot" }, amount: 20 }, + { _id: 1, item: { category: "cake", type: "chiffon" }, amount: 10 }, + { _id: 4, item: { category: "cake", type: "lemon" }, amount: 30 }, + { + _id: 2, + item: { category: "cookies", type: "chocolate chip" }, + amount: 50, + }, + { + _id: 3, + item: { category: "cookies", type: "chocolate chip" }, + amount: 15, + }, + ]); + }); + + it("embedded sort 2", () => { + const sort = sorter({ + "item.category": 1, + "item.type": 1, + amount: 1, + }); - assert.deepStrictEqual(data.sort(sort), [ - { _id: 6, item: { category: 'brownies', type: 'blondie' }, amount: 10 }, - { _id: 1, item: { category: 'cake', type: 'chiffon' }, amount: 10 }, - { _id: 5, item: { category: 'cake', type: 'carrot' }, amount: 20 }, - { _id: 4, item: { category: 'cake', type: 'lemon' }, amount: 30 }, - { _id: 3, item: { category: 'cookies', type: 'chocolate chip' }, amount: 15 }, - { _id: 2, item: { category: 'cookies', type: 'chocolate chip' }, amount: 50 } - ]); + assertEquals(data.sort(sort), [ + { _id: 6, item: { category: "brownies", type: "blondie" }, amount: 10 }, + { _id: 5, item: { category: "cake", type: "carrot" }, amount: 20 }, + { _id: 1, item: { category: "cake", type: "chiffon" }, amount: 10 }, + { _id: 4, item: { category: "cake", type: "lemon" }, amount: 30 }, + { + _id: 3, + item: { category: "cookies", type: "chocolate chip" }, + amount: 15, + }, + { + _id: 2, + item: { category: "cookies", type: "chocolate chip" }, + amount: 50, + }, + ]); + }); + + it("embedded sort 3", () => { + const sort = sorter({ + "item.category": 1, + "item.type": 1, + amount: -1, + }); + + assertEquals(data.sort(sort), [ + { _id: 6, item: { category: "brownies", type: "blondie" }, amount: 10 }, + { _id: 5, item: { category: "cake", type: "carrot" }, amount: 20 }, + { _id: 1, item: { category: "cake", type: "chiffon" }, amount: 10 }, + { _id: 4, item: { category: "cake", type: "lemon" }, amount: 30 }, + { + _id: 2, + item: { category: "cookies", type: "chocolate chip" }, + amount: 50, + }, + { + _id: 3, + item: { category: "cookies", type: "chocolate chip" }, + amount: 15, + }, + ]); + }); + + it("embedded sort 4", () => { + const sort = sorter({ + amount: -1, + "item.category": 1, + }); + + assertEquals(data.sort(sort), [ + { + _id: 2, + item: { category: "cookies", type: "chocolate chip" }, + amount: 50, + }, + { _id: 4, item: { category: "cake", type: "lemon" }, amount: 30 }, + { _id: 5, item: { category: "cake", type: "carrot" }, amount: 20 }, + { + _id: 3, + item: { category: "cookies", type: "chocolate chip" }, + amount: 15, + }, + { _id: 6, item: { category: "brownies", type: "blondie" }, amount: 10 }, + { _id: 1, item: { category: "cake", type: "chiffon" }, amount: 10 }, + ]); + }); + + it("embedded sort 5", () => { + const sort = sorter({ + "item.category": 1, + amount: 1, + }); + + assertEquals(data.sort(sort), [ + { _id: 6, item: { category: "brownies", type: "blondie" }, amount: 10 }, + { _id: 1, item: { category: "cake", type: "chiffon" }, amount: 10 }, + { _id: 5, item: { category: "cake", type: "carrot" }, amount: 20 }, + { _id: 4, item: { category: "cake", type: "lemon" }, amount: 30 }, + { + _id: 3, + item: { category: "cookies", type: "chocolate chip" }, + amount: 15, + }, + { + _id: 2, + item: { category: "cookies", type: "chocolate chip" }, + amount: 50, + }, + ]); + }); + }); }); diff --git a/main/adapter-tests/LICENSE b/main/adapter-tests/LICENSE new file mode 100644 index 0000000000..59604f46f3 --- /dev/null +++ b/main/adapter-tests/LICENSE @@ -0,0 +1,22 @@ +The MIT License (MIT) + +Copyright (c) 2022 Feathers + +Permission is hereby granted, free of charge, to any person obtaining a copy +of this software and associated documentation files (the "Software"), to deal +in the Software without restriction, including without limitation the rights +to use, copy, modify, merge, publish, distribute, sublicense, and/or sell +copies of the Software, and to permit persons to whom the Software is +furnished to do so, subject to the following conditions: + +The above copyright notice and this permission notice shall be included in all +copies or substantial portions of the Software. + +THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE +AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, +OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE +SOFTWARE. + diff --git a/main/adapter-tests/README.md b/main/adapter-tests/README.md new file mode 100644 index 0000000000..9d54b46a4c --- /dev/null +++ b/main/adapter-tests/README.md @@ -0,0 +1,25 @@ +# Feathers Adapter Tests + +[![CI](https://github.com/feathersjs/feathers/workflows/Node.js%20CI/badge.svg)](https://github.com/feathersjs/feathers/actions?query=workflow%3A%22Node.js+CI%22) +[![Download Status](https://img.shields.io/npm/dm/@feathersjs/adapter-commons.svg?style=flat-square)](https://www.npmjs.com/package/@feathersjs/adapter-commons) +[![Discord](https://badgen.net/badge/icon/discord?icon=discord&label)](https://discord.gg/qa8kez8QBx) + +> Feathers shared database adapter test suite + +## About + +This is a repository that contains the test suite for the common database +adapter syntax. See the +[API documentation](https://docs.feathersjs.com/api/databases/common.html) for +more information. + +## Authors + +[Feathers contributors](https://github.com/feathersjs/adapter-tests/graphs/contributors) + +## License + +Copyright (c) 2022 +[Feathers contributors](https://github.com/feathersjs/feathers/graphs/contributors) + +Licensed under the [MIT license](LICENSE). diff --git a/main/adapter-tests/mod.ts b/main/adapter-tests/mod.ts new file mode 100644 index 0000000000..b0dd28d7cc --- /dev/null +++ b/main/adapter-tests/mod.ts @@ -0,0 +1,2 @@ +export * from "./src/index.ts"; +export { default } from "./src/index.ts"; \ No newline at end of file diff --git a/main/adapter-tests/src/basic.ts b/main/adapter-tests/src/basic.ts new file mode 100644 index 0000000000..fa6c3a7795 --- /dev/null +++ b/main/adapter-tests/src/basic.ts @@ -0,0 +1,87 @@ +import {assert, assertStrictEquals, beforeEach, describe, it} from "../../commons/mod.ts"; +import { AdapterBasicTest } from "./declarations.ts"; + +export default ( + test: AdapterBasicTest, + app: any, + _errors: any, + serviceName: string, + idProp: string, +) => { + describe("Basic Functionality", () => { + let service: any; + + beforeEach(() => { + service = app.service(serviceName); + }); + + it(".id", () => { + assertStrictEquals( + service.id, + idProp, + "id property is set to expected name", + ); + }); + + test(".options", () => { + assert(service.options, "Options are available in service.options"); + }); + + test(".events", () => { + assert( + service.events.includes("testing"), + 'service.events is set and includes "testing"', + ); + }); + + describe("Raw Methods", () => { + test("._get", () => { + assertStrictEquals(typeof service._get, "function"); + }); + + test("._find", () => { + assertStrictEquals(typeof service._find, "function"); + }); + + test("._create", () => { + assertStrictEquals(typeof service._create, "function"); + }); + + test("._update", () => { + assertStrictEquals(typeof service._update, "function"); + }); + + test("._patch", () => { + assertStrictEquals(typeof service._patch, "function"); + }); + + test("._remove", () => { + assertStrictEquals(typeof service._remove, "function"); + }); + + test(".$get", () => { + assertStrictEquals(typeof service.$get, "function"); + }); + + test(".$find", () => { + assertStrictEquals(typeof service.$find, "function"); + }); + + test(".$create", () => { + assertStrictEquals(typeof service.$create, "function"); + }); + + test(".$update", () => { + assertStrictEquals(typeof service.$update, "function"); + }); + + test(".$patch", () => { + assertStrictEquals(typeof service.$patch, "function"); + }); + + test(".$remove", () => { + assertStrictEquals(typeof service.$remove, "function"); + }); + }); + }); +}; diff --git a/main/adapter-tests/src/declarations.ts b/main/adapter-tests/src/declarations.ts new file mode 100644 index 0000000000..5df8149496 --- /dev/null +++ b/main/adapter-tests/src/declarations.ts @@ -0,0 +1,102 @@ +export type AdapterTest = (name: AdapterTestName, runner: any) => void; + +export type AdapterBasicTest = ( + name: AdapterBasicTestName, + runner: any, +) => void; +export type AdapterMethodsTest = ( + name: AdapterMethodsTestName, + runner: any, +) => void; +export type AdapterSyntaxTest = ( + name: AdapterSyntaxTestName, + runner: any, +) => void; + +export type AdapterTestName = + | AdapterBasicTestName + | AdapterMethodsTestName + | AdapterSyntaxTestName; + +export type AdapterBasicTestName = + | ".id" + | ".options" + | ".events" + | "._get" + | "._find" + | "._create" + | "._update" + | "._patch" + | "._remove" + | ".$get" + | ".$find" + | ".$create" + | ".$update" + | ".$patch" + | ".$remove"; + +export type AdapterMethodsTestName = + | ".get" + | ".get + $select" + | ".get + id + query" + | ".get + NotFound" + | ".get + id + query id" + | ".find" + | ".remove" + | ".remove + $select" + | ".remove + id + query" + | ".remove + multi" + | ".remove + multi no pagination" + | ".remove + id + query id" + | ".update" + | ".update + $select" + | ".update + id + query" + | ".update + NotFound" + | ".update + query + NotFound" + | ".update + id + query id" + | ".patch" + | ".patch + $select" + | ".patch + id + query" + | ".patch multiple" + | ".patch multiple no pagination" + | ".patch multi query same" + | ".patch multi query changed" + | ".patch + NotFound" + | ".patch + query + NotFound" + | ".patch + id + query id" + | ".create" + | ".create + $select" + | ".create multi" + | "internal .find" + | "internal .get" + | "internal .create" + | "internal .update" + | "internal .patch" + | "internal .remove"; + +export type AdapterSyntaxTestName = + | ".find + equal" + | ".find + equal multiple" + | ".find + $sort" + | ".find + $sort + string" + | ".find + $limit" + | ".find + $limit 0" + | ".find + $skip" + | ".find + $select" + | ".find + $or" + | ".find + $in" + | ".find + $nin" + | ".find + $lt" + | ".find + $lte" + | ".find + $gt" + | ".find + $gte" + | ".find + $ne" + | ".find + $gt + $lt + $sort" + | ".find + $or nested + $sort" + | "params.adapter + paginate" + | "params.adapter + multi" + | ".find + paginate" + | ".find + paginate + query" + | ".find + paginate + $limit + $skip" + | ".find + paginate + $limit 0" + | ".find + paginate + params"; diff --git a/main/adapter-tests/src/index.ts b/main/adapter-tests/src/index.ts new file mode 100644 index 0000000000..a379abb27f --- /dev/null +++ b/main/adapter-tests/src/index.ts @@ -0,0 +1,59 @@ +import basicTests from "./basic.ts"; +import { AdapterTestName } from "./declarations.ts"; +import methodTests from "./methods.ts"; +import syntaxTests from "./syntax.ts"; +import { afterAll, describe, it } from "../../commons/mod.ts"; + +const adapterTests = (testNames: AdapterTestName[]) => { + return (app: any, errors: any, serviceName: any, idProp = "id") => { + if (!serviceName) { + throw new Error("You must pass a service name"); + } + + const skippedTests: AdapterTestName[] = []; + const allTests: AdapterTestName[] = []; + + const test = (name: AdapterTestName, runner: any) => { + const skip = !testNames.includes(name); + const its = skip ? it.ignore : it; + + if (skip) { + skippedTests.push(name); + } + + allTests.push(name); + + its(name, runner); + }; + + describe(`Adapter tests for '${serviceName}' service with '${idProp}' id property`, () => { + afterAll(() => { + testNames.forEach((name) => { + if (!allTests.includes(name)) { + console.error( + `WARNING: '${name}' test is not part of the test suite`, + ); + } + }); + if (skippedTests.length) { + console.log( + `\nSkipped the following ${skippedTests.length} Feathers adapter test(s) out of ${allTests.length} total:`, + ); + console.log(JSON.stringify(skippedTests, null, " ")); + } + }); + + basicTests(test, app, errors, serviceName, idProp); + methodTests(test, app, errors, serviceName, idProp); + syntaxTests(test, app, errors, serviceName, idProp); + }); + }; +}; + +export * from "./declarations.ts"; + +export default adapterTests; + +// if (typeof module !== 'undefined') { +// module.exports = Object.assign(adapterTests, module.exports) +// } diff --git a/main/adapter-tests/src/methods.ts b/main/adapter-tests/src/methods.ts new file mode 100644 index 0000000000..0b96ad9475 --- /dev/null +++ b/main/adapter-tests/src/methods.ts @@ -0,0 +1,844 @@ +import { + afterEach, + assert, + assertEquals, + assertStrictEquals, + beforeAll, + beforeEach, + describe, +} from "../../commons/mod.ts"; +import { AdapterMethodsTest } from "./declarations.ts"; + +export default ( + test: AdapterMethodsTest, + app: any, + _errors: any, + serviceName: string, + idProp: string, +) => { + describe(" Methods", () => { + let doug: any; + let service: any; + + beforeEach(async () => { + service = app.service(serviceName); + doug = await app.service(serviceName).create({ + name: "Doug", + age: 32, + }); + }); + + afterEach(async () => { + try { + await app.service(serviceName).remove(doug[idProp]); + } catch (error: any) {} + }); + + describe("get", () => { + test(".get", async () => { + const data = await service.get(doug[idProp]); + + assertStrictEquals( + data[idProp].toString(), + doug[idProp].toString(), + `${idProp} id matches`, + ); + assertStrictEquals(data.name, "Doug", "data.name matches"); + assertStrictEquals(data.age, 32, "data.age matches"); + }); + + test(".get + $select", async () => { + const data = await service.get(doug[idProp], { + query: { $select: ["name"] }, + }); + + assertStrictEquals( + data[idProp].toString(), + doug[idProp].toString(), + `${idProp} id property matches`, + ); + assertStrictEquals(data.name, "Doug", "data.name matches"); + assert(!data.age, "data.age is falsy"); + }); + + test(".get + id + query", async () => { + try { + await service.get(doug[idProp], { + query: { name: "Tester" }, + }); + throw new Error("Should never get here"); + } catch (error: any) { + assertStrictEquals( + error.name, + "NotFound", + "Got a NotFound Feathers error", + ); + } + }); + + test(".get + NotFound", async () => { + try { + await service.get("568225fbfe21222432e836ff"); + throw new Error("Should never get here"); + } catch (error: any) { + assertStrictEquals( + error.name, + "NotFound", + "Error is a NotFound Feathers error", + ); + } + }); + + test(".get + id + query id", async () => { + const alice = await service.create({ + name: "Alice", + age: 12, + }); + + try { + await service.get(doug[idProp], { + query: { [idProp]: alice[idProp] }, + }); + throw new Error("Should never get here"); + } catch (error: any) { + assertStrictEquals( + error.name, + "NotFound", + "Got a NotFound Feathers error", + ); + } + + await service.remove(alice[idProp]); + }); + }); + + describe("find", () => { + test(".find", async () => { + const data = await service.find(); + + assert(Array.isArray(data), "Data is an array"); + assertStrictEquals(data.length, 1, "Got one entry"); + }); + }); + + describe("remove", () => { + test(".remove", async () => { + const data = await service.remove(doug[idProp]); + + assertStrictEquals(data.name, "Doug", "data.name matches"); + }); + + test(".remove + $select", async () => { + const data = await service.remove(doug[idProp], { + query: { $select: ["name"] }, + }); + + assertStrictEquals(data.name, "Doug", "data.name matches"); + assert(!data.age, "data.age is falsy"); + }); + + test(".remove + id + query", async () => { + try { + await service.remove(doug[idProp], { + query: { name: "Tester" }, + }); + throw new Error("Should never get here"); + } catch (error: any) { + assertStrictEquals( + error.name, + "NotFound", + "Got a NotFound Feathers error", + ); + } + }); + + test(".remove + multi", async () => { + try { + await service.remove(null); + throw new Error("Should never get here"); + } catch (error: any) { + assertStrictEquals( + error.name, + "MethodNotAllowed", + "Removing multiple without option set throws MethodNotAllowed", + ); + } + + service.options.multi = ["remove"]; + + await service.create({ name: "Dave", age: 29, created: true }); + await service.create({ + name: "David", + age: 3, + created: true, + }); + + const data = await service.remove(null, { + query: { created: true }, + }); + + assertStrictEquals(data.length, 2); + + const names = data.map((person: any) => person.name); + + assert(names.includes("Dave"), "Dave removed"); + assert(names.includes("David"), "David removed"); + }); + + test(".remove + multi no pagination", async () => { + try { + await service.remove(doug[idProp]); + } catch (error: any) {} + + const count = 14; + const defaultPaginate = 10; + + assert( + count > defaultPaginate, + "count is bigger than default pagination", + ); + + const multiBefore = service.options.multi; + const paginateBefore = service.options.paginate; + + try { + service.options.multi = true; + service.options.paginate = { + default: defaultPaginate, + max: 100, + }; + + const emptyItems = await service.find({ paginate: false }); + assertStrictEquals(emptyItems.length, 0, "no items before"); + + const createdItems = await service.create( + Array.from(Array(count)).map((_, i) => ({ + name: `name-${i}`, + age: 3, + created: true, + })), + ); + assertStrictEquals( + createdItems.length, + count, + `created ${count} items`, + ); + + const foundItems = await service.find({ paginate: false }); + assertStrictEquals( + foundItems.length, + count, + `created ${count} items`, + ); + + const foundPaginatedItems = await service.find({}); + assertStrictEquals( + foundPaginatedItems.data.length, + defaultPaginate, + "found paginated items", + ); + + const allItems = await service.remove(null, { + query: { created: true }, + }); + + assertStrictEquals( + allItems.length, + count, + `removed all ${count} items`, + ); + } finally { + await service.remove(null, { + query: { created: true }, + paginate: false, + }); + + service.options.multi = multiBefore; + service.options.paginate = paginateBefore; + } + }); + + test(".remove + id + query id", async () => { + const alice = await service.create({ + name: "Alice", + age: 12, + }); + + try { + await service.remove(doug[idProp], { + query: { [idProp]: alice[idProp] }, + }); + throw new Error("Should never get here"); + } catch (error: any) { + assertStrictEquals( + error.name, + "NotFound", + "Got a NotFound Feathers error", + ); + } + + await service.remove(alice[idProp]); + }); + }); + + describe("update", () => { + test(".update", async () => { + const originalData = { [idProp]: doug[idProp], name: "Dougler" }; + const originalCopy = Object.assign({}, originalData); + + const data = await service.update(doug[idProp], originalData); + + assertEquals( + originalData, + originalCopy, + "data was not modified", + ); + assertStrictEquals( + data[idProp].toString(), + doug[idProp].toString(), + `${idProp} id matches`, + ); + assertStrictEquals(data.name, "Dougler", "data.name matches"); + assert(!data.age, "data.age is falsy"); + }); + + test(".update + $select", async () => { + const originalData = { + [idProp]: doug[idProp], + name: "Dougler", + age: 10, + }; + + const data = await service.update(doug[idProp], originalData, { + query: { $select: ["name"] }, + }); + + assertStrictEquals(data.name, "Dougler", "data.name matches"); + assert(!data.age, "data.age is falsy"); + }); + + test(".update + id + query", async () => { + try { + await service.update( + doug[idProp], + { + name: "Dougler", + }, + { + query: { name: "Tester" }, + }, + ); + throw new Error("Should never get here"); + } catch (error: any) { + assertStrictEquals( + error.name, + "NotFound", + "Got a NotFound Feathers error", + ); + } + }); + + test(".update + NotFound", async () => { + try { + await service.update("568225fbfe21222432e836ff", { + name: "NotFound", + }); + throw new Error("Should never get here"); + } catch (error: any) { + assertStrictEquals( + error.name, + "NotFound", + "Error is a NotFound Feathers error", + ); + } + }); + + test(".update + query + NotFound", async () => { + const dave = await service.create({ name: "Dave" }); + try { + await service.update(dave[idProp], { name: "UpdatedDave" }, { + query: { name: "NotDave" }, + }); + throw new Error("Should never get here"); + } catch (error: any) { + assertStrictEquals( + error.name, + "NotFound", + "Error is a NotFound Feathers error", + ); + } + await service.remove(dave[idProp]); + }); + + test(".update + id + query id", async () => { + const alice = await service.create({ + name: "Alice", + age: 12, + }); + + try { + await service.update( + doug[idProp], + { + name: "Dougler", + age: 33, + }, + { + query: { [idProp]: alice[idProp] }, + }, + ); + throw new Error("Should never get here"); + } catch (error: any) { + assertStrictEquals( + error.name, + "NotFound", + "Got a NotFound Feathers error", + ); + } + + await service.remove(alice[idProp]); + }); + }); + + describe("patch", () => { + test(".patch", async () => { + const originalData = { [idProp]: doug[idProp], name: "PatchDoug" }; + const originalCopy = Object.assign({}, originalData); + + const data = await service.patch(doug[idProp], originalData); + + assertEquals( + originalData, + originalCopy, + "original data was not modified", + ); + assertStrictEquals( + data[idProp].toString(), + doug[idProp].toString(), + `${idProp} id matches`, + ); + assertStrictEquals(data.name, "PatchDoug", "data.name matches"); + assertStrictEquals(data.age, 32, "data.age matches"); + }); + + test(".patch + $select", async () => { + const originalData = { [idProp]: doug[idProp], name: "PatchDoug" }; + + const data = await service.patch(doug[idProp], originalData, { + query: { $select: ["name"] }, + }); + + assertStrictEquals(data.name, "PatchDoug", "data.name matches"); + assert(!data.age, "data.age is falsy"); + }); + + test(".patch + id + query", async () => { + try { + await service.patch( + doug[idProp], + { + name: "id patched doug", + }, + { + query: { name: "Tester" }, + }, + ); + throw new Error("Should never get here"); + } catch (error: any) { + assertStrictEquals( + error.name, + "NotFound", + "Got a NotFound Feathers error", + ); + } + }); + + test(".patch multiple", async () => { + try { + await service.patch(null, {}); + throw new Error("Should never get here"); + } catch (error: any) { + assertStrictEquals( + error.name, + "MethodNotAllowed", + "Removing multiple without option set throws MethodNotAllowed", + ); + } + + const params = { + query: { created: true }, + }; + const dave = await service.create({ + name: "Dave", + age: 29, + created: true, + }); + const david = await service.create({ + name: "David", + age: 3, + created: true, + }); + + service.options.multi = ["patch"]; + + const data = await service.patch( + null, + { + age: 2, + }, + params, + ); + + assertStrictEquals(data.length, 2, "returned two entries"); + assertStrictEquals(data[0].age, 2, "First entry age was updated"); + assertStrictEquals(data[1].age, 2, "Second entry age was updated"); + + await service.remove(dave[idProp]); + await service.remove(david[idProp]); + }); + + test(".patch multiple no pagination", async () => { + try { + await service.remove(doug[idProp]); + } catch (error: any) {} + + const count = 14; + const defaultPaginate = 10; + + assert( + count > defaultPaginate, + "count is bigger than default pagination", + ); + + const multiBefore = service.options.multi; + const paginateBefore = service.options.paginate; + + let ids: any[]; + + try { + service.options.multi = true; + service.options.paginate = { + default: defaultPaginate, + max: 100, + }; + + const emptyItems = await service.find({ paginate: false }); + assertStrictEquals(emptyItems.length, 0, "no items before"); + + const createdItems = await service.create( + Array.from(Array(count)).map((_, i) => ({ + name: `name-${i}`, + age: 3, + created: true, + })), + ); + assertStrictEquals( + createdItems.length, + count, + `created ${count} items`, + ); + ids = createdItems.map((item: any) => item[idProp]); + + const foundItems = await service.find({ paginate: false }); + assertStrictEquals( + foundItems.length, + count, + `created ${count} items`, + ); + + const foundPaginatedItems = await service.find({}); + assertStrictEquals( + foundPaginatedItems.data.length, + defaultPaginate, + "found paginated data", + ); + + const allItems = await service.patch(null, { age: 4 }, { + query: { created: true }, + }); + + assertStrictEquals( + allItems.length, + count, + `patched all ${count} items`, + ); + } finally { + service.options.multi = multiBefore; + service.options.paginate = paginateBefore; + if (ids!) { + await Promise.all(ids.map((id) => service.remove(id))); + } + } + }); + + test(".patch multi query same", async () => { + const service = app.service(serviceName); + const multiBefore = service.options.multi; + + service.options.multi = true; + + const params = { + query: { age: { $lt: 10 } }, + }; + const dave = await service.create({ + name: "Dave", + age: 8, + created: true, + }); + const david = await service.create({ + name: "David", + age: 4, + created: true, + }); + + const data = await service.patch( + null, + { + age: 2, + }, + params, + ); + + assertStrictEquals(data.length, 2, "returned two entries"); + assertStrictEquals(data[0].age, 2, "First entry age was updated"); + assertStrictEquals(data[1].age, 2, "Second entry age was updated"); + + await service.remove(dave[idProp]); + await service.remove(david[idProp]); + + service.options.multi = multiBefore; + }); + + test(".patch multi query changed", async () => { + const service = app.service(serviceName); + const multiBefore = service.options.multi; + + service.options.multi = true; + + const params = { + query: { age: 10 }, + }; + const dave = await service.create({ + name: "Dave", + age: 10, + created: true, + }); + const david = await service.create({ + name: "David", + age: 10, + created: true, + }); + + const data = await service.patch( + null, + { + age: 2, + }, + params, + ); + + assertStrictEquals(data.length, 2, "returned two entries"); + assertStrictEquals(data[0].age, 2, "First entry age was updated"); + assertStrictEquals(data[1].age, 2, "Second entry age was updated"); + + await service.remove(dave[idProp]); + await service.remove(david[idProp]); + + service.options.multi = multiBefore; + }); + + test(".patch + NotFound", async () => { + try { + await service.patch("568225fbfe21222432e836ff", { + name: "PatchDoug", + }); + throw new Error("Should never get here"); + } catch (error: any) { + assertStrictEquals( + error.name, + "NotFound", + "Error is a NotFound Feathers error", + ); + } + }); + + test(".patch + query + NotFound", async () => { + const dave = await service.create({ name: "Dave" }); + try { + await service.patch(dave[idProp], { name: "PatchedDave" }, { + query: { name: "NotDave" }, + }); + throw new Error("Should never get here"); + } catch (error: any) { + assertStrictEquals( + error.name, + "NotFound", + "Error is a NotFound Feathers error", + ); + } + await service.remove(dave[idProp]); + }); + + test(".patch + id + query id", async () => { + const alice = await service.create({ + name: "Alice", + age: 12, + }); + + try { + await service.patch( + doug[idProp], + { + age: 33, + }, + { + query: { [idProp]: alice[idProp] }, + }, + ); + throw new Error("Should never get here"); + } catch (error: any) { + assertStrictEquals( + error.name, + "NotFound", + "Got a NotFound Feathers error", + ); + } + + await service.remove(alice[idProp]); + }); + }); + + describe("create", () => { + test(".create", async () => { + const originalData = { + name: "Bill", + age: 40, + }; + const originalCopy = Object.assign({}, originalData); + + const data = await service.create(originalData); + + assertEquals( + originalData, + originalCopy, + "original data was not modified", + ); + assert(data instanceof Object, "data is an object"); + assertStrictEquals(data.name, "Bill", "data.name matches"); + + await service.remove(data[idProp]); + }); + + test(".create + $select", async () => { + const originalData = { + name: "William", + age: 23, + }; + + const data = await service.create(originalData, { + query: { $select: ["name"] }, + }); + + assertStrictEquals(data.name, "William", "data.name matches"); + assert(!data.age, "data.age is falsy"); + + await service.remove(data[idProp]); + }); + + test(".create multi", async () => { + try { + await service.create([], {}); + throw new Error("Should never get here"); + } catch (error: any) { + assertStrictEquals( + error.name, + "MethodNotAllowed", + "Removing multiple without option set throws MethodNotAllowed", + ); + } + + const items = [ + { + name: "Gerald", + age: 18, + }, + { + name: "Herald", + age: 18, + }, + ]; + + service.options.multi = ["create", "patch"]; + + const data = await service.create(items); + + assert(Array.isArray(data), "data is an array"); + assert(typeof data[0][idProp] !== "undefined", "id is set"); + assertStrictEquals(data[0].name, "Gerald", "first name matches"); + assert(typeof data[1][idProp] !== "undefined", "id is set"); + assertStrictEquals(data[1].name, "Herald", "second name macthes"); + + await service.remove(data[0][idProp]); + await service.remove(data[1][idProp]); + }); + }); + + describe("doesn't call public methods internally", () => { + let throwing: any; + + beforeAll(() => { + throwing = Object.assign(Object.create(app.service(serviceName)), { + get store() { + return app.service(serviceName).store; + }, + + find() { + throw new Error("find method called"); + }, + get() { + throw new Error("get method called"); + }, + create() { + throw new Error("create method called"); + }, + update() { + throw new Error("update method called"); + }, + patch() { + throw new Error("patch method called"); + }, + remove() { + throw new Error("remove method called"); + }, + }); + }); + + test("internal .find", () => + app.service(serviceName).find.call(throwing)); + + test("internal .get", () => service.get.call(throwing, doug[idProp])); + + test("internal .create", async () => { + const bob = await service.create.call(throwing, { + name: "Bob", + age: 25, + }); + + await service.remove(bob[idProp]); + }); + + test("internal .update", () => + service.update.call(throwing, doug[idProp], { + name: "Dougler", + })); + + test("internal .patch", () => + service.patch.call(throwing, doug[idProp], { + name: "PatchDoug", + })); + + test("internal .remove", () => + service.remove.call(throwing, doug[idProp])); + }); + }); +}; diff --git a/main/adapter-tests/src/syntax.ts b/main/adapter-tests/src/syntax.ts new file mode 100644 index 0000000000..1a82e73c2f --- /dev/null +++ b/main/adapter-tests/src/syntax.ts @@ -0,0 +1,408 @@ +import { + afterEach, + assert, + assertEquals, + assertRejects, + assertStrictEquals, + beforeEach, + describe, +} from "../../commons/mod.ts"; +import { AdapterSyntaxTest } from "./declarations.ts"; + +export default ( + test: AdapterSyntaxTest, + app: any, + _errors: any, + serviceName: string, + idProp: string, +) => { + describe("Query Syntax", () => { + let bob: any; + let alice: any; + let doug: any; + let service: any; + + beforeEach(async () => { + service = app.service(serviceName); + bob = await app.service(serviceName).create({ + name: "Bob", + age: 25, + }); + doug = await app.service(serviceName).create({ + name: "Doug", + age: 32, + }); + alice = await app.service(serviceName).create({ + name: "Alice", + age: 19, + }); + }); + + afterEach(async () => { + await service.remove(bob[idProp]); + await service.remove(alice[idProp]); + await service.remove(doug[idProp]); + }); + + test(".find + equal", async () => { + const params = { query: { name: "Alice" } }; + const data = await service.find(params); + + assert(Array.isArray(data)); + assertStrictEquals(data.length, 1); + assertStrictEquals(data[0].name, "Alice"); + }); + + test(".find + equal multiple", async () => { + const data = await service.find({ + query: { name: "Alice", age: 20 }, + }); + + assertStrictEquals(data.length, 0); + }); + + describe("special filters", () => { + test(".find + $sort", async () => { + let data = await service.find({ + query: { + $sort: { name: 1 }, + }, + }); + + assertStrictEquals(data.length, 3); + assertStrictEquals(data[0].name, "Alice"); + assertStrictEquals(data[1].name, "Bob"); + assertStrictEquals(data[2].name, "Doug"); + + data = await service.find({ + query: { + $sort: { name: -1 }, + }, + }); + + assertStrictEquals(data.length, 3); + assertStrictEquals(data[0].name, "Doug"); + assertStrictEquals(data[1].name, "Bob"); + assertStrictEquals(data[2].name, "Alice"); + }); + + test(".find + $sort + string", async () => { + const data = await service.find({ + query: { + $sort: { name: "1" }, + }, + }); + + assertStrictEquals(data.length, 3); + assertStrictEquals(data[0].name, "Alice"); + assertStrictEquals(data[1].name, "Bob"); + assertStrictEquals(data[2].name, "Doug"); + }); + + test(".find + $limit", async () => { + const data = await service.find({ + query: { + $limit: 2, + }, + }); + + assertStrictEquals(data.length, 2); + }); + + test(".find + $limit 0", async () => { + const data = await service.find({ + query: { + $limit: 0, + }, + }); + + assertStrictEquals(data.length, 0); + }); + + test(".find + $skip", async () => { + const data = await service.find({ + query: { + $sort: { name: 1 }, + $skip: 1, + }, + }); + + assertStrictEquals(data.length, 2); + assertStrictEquals(data[0].name, "Bob"); + assertStrictEquals(data[1].name, "Doug"); + }); + + test(".find + $select", async () => { + const data = await service.find({ + query: { + name: "Alice", + $select: ["name"], + }, + }); + + assertStrictEquals(data.length, 1); + assertStrictEquals(data[0].name, "Alice"); + assertStrictEquals(data[0].age, undefined); + }); + + test(".find + $or", async () => { + const data = await service.find({ + query: { + $or: [{ name: "Alice" }, { name: "Bob" }], + $sort: { name: 1 }, + }, + }); + + assertStrictEquals(data.length, 2); + assertStrictEquals(data[0].name, "Alice"); + assertStrictEquals(data[1].name, "Bob"); + }); + + test(".find + $in", async () => { + const data = await service.find({ + query: { + name: { + $in: ["Alice", "Bob"], + }, + $sort: { name: 1 }, + }, + }); + + assertStrictEquals(data.length, 2); + assertStrictEquals(data[0].name, "Alice"); + assertStrictEquals(data[1].name, "Bob"); + }); + + test(".find + $nin", async () => { + const data = await service.find({ + query: { + name: { + $nin: ["Alice", "Bob"], + }, + }, + }); + + assertStrictEquals(data.length, 1); + assertStrictEquals(data[0].name, "Doug"); + }); + + test(".find + $lt", async () => { + const data = await service.find({ + query: { + age: { + $lt: 30, + }, + }, + }); + + assertStrictEquals(data.length, 2); + }); + + test(".find + $lte", async () => { + const data = await service.find({ + query: { + age: { + $lte: 25, + }, + }, + }); + + assertStrictEquals(data.length, 2); + }); + + test(".find + $gt", async () => { + const data = await service.find({ + query: { + age: { + $gt: 30, + }, + }, + }); + + assertStrictEquals(data.length, 1); + }); + + test(".find + $gte", async () => { + const data = await service.find({ + query: { + age: { + $gte: 25, + }, + }, + }); + + assertStrictEquals(data.length, 2); + }); + + test(".find + $ne", async () => { + const data = await service.find({ + query: { + age: { + $ne: 25, + }, + }, + }); + + assertStrictEquals(data.length, 2); + }); + }); + + test(".find + $gt + $lt + $sort", async () => { + const params = { + query: { + age: { + $gt: 18, + $lt: 30, + }, + $sort: { name: 1 }, + }, + }; + + const data = await service.find(params); + + assertStrictEquals(data.length, 2); + assertStrictEquals(data[0].name, "Alice"); + assertStrictEquals(data[1].name, "Bob"); + }); + + test(".find + $or nested + $sort", async () => { + const params = { + query: { + $or: [ + { name: "Doug" }, + { + age: { + $gte: 18, + $lt: 25, + }, + }, + ], + $sort: { name: 1 }, + }, + }; + + const data = await service.find(params); + + assertStrictEquals(data.length, 2); + assertStrictEquals(data[0].name, "Alice"); + assertStrictEquals(data[1].name, "Doug"); + }); + + describe("params.adapter", () => { + test("params.adapter + paginate", async () => { + const page = await service.find({ + adapter: { + paginate: { default: 3 }, + }, + }); + + assertStrictEquals(page.limit, 3); + assertStrictEquals(page.skip, 0); + }); + + test("params.adapter + multi", async () => { + const items = [ + { + name: "Garald", + age: 200, + }, + { + name: "Harald", + age: 24, + }, + ]; + const multiParams = { + adapter: { + multi: ["create"], + }, + }; + const users = await service.create(items, multiParams); + + assertStrictEquals(users.length, 2); + + await service.remove(users[0][idProp]); + await service.remove(users[1][idProp]); + await assertRejects( + () => service.patch(null, { age: 2 }, multiParams),"Can not patch multiple entries", + ); + }); + }); + + describe("paginate", function () { + beforeEach(() => { + service.options.paginate = { + default: 1, + max: 2, + }; + }); + + afterEach(() => { + service.options.paginate = {}; + }); + + test(".find + paginate", async () => { + const page = await service.find({ + query: { $sort: { name: -1 } }, + }); + + assertStrictEquals(page.total, 3); + assertStrictEquals(page.limit, 1); + assertStrictEquals(page.skip, 0); + assertStrictEquals(page.data[0].name, "Doug"); + }); + + test(".find + paginate + query", async () => { + const page = await service.find({ + query: { + $sort: { name: -1 }, + name: "Doug", + }, + }); + + assertStrictEquals(page.total, 1); + assertStrictEquals(page.limit, 1); + assertStrictEquals(page.skip, 0); + assertStrictEquals(page.data[0].name, "Doug"); + }); + + test(".find + paginate + $limit + $skip", async () => { + const params = { + query: { + $skip: 1, + $limit: 4, + $sort: { name: -1 }, + }, + }; + + const page = await service.find(params); + + assertStrictEquals(page.total, 3); + assertStrictEquals(page.limit, 2); + assertStrictEquals(page.skip, 1); + assertStrictEquals(page.data[0].name, "Bob"); + assertStrictEquals(page.data[1].name, "Alice"); + }); + + test(".find + paginate + $limit 0", async () => { + const page = await service.find({ + query: { $limit: 0 }, + }); + + assertStrictEquals(page.total, 3); + assertStrictEquals(page.data.length, 0); + }); + + test(".find + paginate + params", async () => { + const page = await service.find({ paginate: { default: 3 } }); + + assertStrictEquals(page.limit, 3); + assertStrictEquals(page.skip, 0); + + const results = await service.find({ paginate: false }); + + assert(Array.isArray(results)); + assertStrictEquals(results.length, 3); + }); + }); + }); +}; diff --git a/main/adapter-tests/test/index.test.ts b/main/adapter-tests/test/index.test.ts new file mode 100644 index 0000000000..f7faab8fb0 --- /dev/null +++ b/main/adapter-tests/test/index.test.ts @@ -0,0 +1,85 @@ +import { assert, describe, it } from "../../commons/mod.ts"; +import adapterTests from "../mod.ts"; + +const testSuite = adapterTests([ + ".events", + "._get", + "._find", + "._create", + "._update", + "._patch", + "._remove", + ".$get", + ".$find", + ".$create", + ".$update", + ".$patch", + ".$remove", + ".get", + ".get + $select", + ".get + id + query", + ".get + NotFound", + ".find", + ".remove", + ".remove + $select", + ".remove + id + query", + ".remove + multi", + ".remove + multi no pagination", + ".update", + ".update + $select", + ".update + id + query", + ".update + NotFound", + ".patch", + ".patch + $select", + ".patch + id + query", + ".patch multiple", + ".patch multiple no pagination", + ".patch multi query changed", + ".patch multi query same", + ".patch + NotFound", + ".create", + ".create + $select", + ".create multi", + "internal .find", + "internal .get", + "internal .create", + "internal .update", + "internal .patch", + "internal .remove", + ".find + equal", + ".find + equal multiple", + ".find + $sort", + ".find + $sort + string", + ".find + $limit", + ".find + $limit 0", + ".find + $skip", + ".find + $select", + ".find + $or", + ".find + $in", + ".find + $nin", + ".find + $lt", + ".find + $lte", + ".find + $gt", + ".find + $gte", + ".find + $ne", + ".find + $gt + $lt + $sort", + ".find + $or nested + $sort", + ".find + paginate", + ".find + paginate + $limit + $skip", + ".find + paginate + $limit 0", + ".find + paginate + params", + ".get + id + query id", + ".remove + id + query id", + ".update + id + query id", + ".patch + id + query id", +]); + +describe("Feathers Memory Service", () => { + it("loads the test suite", () => { + assert(typeof testSuite === "function"); + }); + + it.ignore("exports as CommonJS", () => { + // assert.equal(typeof require("../lib"), "function"); + }); +}); diff --git a/main/commons/LICENSE b/main/commons/LICENSE index 3f395cc665..59604f46f3 100644 --- a/main/commons/LICENSE +++ b/main/commons/LICENSE @@ -1,6 +1,6 @@ The MIT License (MIT) -Copyright (c) 2021 Feathers +Copyright (c) 2022 Feathers Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated documentation files (the "Software"), to deal diff --git a/main/commons/mod.ts b/main/commons/mod.ts new file mode 100644 index 0000000000..3b3419b271 --- /dev/null +++ b/main/commons/mod.ts @@ -0,0 +1 @@ +export * from "./src/index.ts"; diff --git a/main/commons/src/events.ts b/main/commons/src/events.js similarity index 50% rename from main/commons/src/events.ts rename to main/commons/src/events.js index 96090a2b47..febb8e88ac 100644 --- a/main/commons/src/events.ts +++ b/main/commons/src/events.js @@ -1,101 +1,89 @@ -/* eslint-disable no-console */ -// deno-lint-ignore-file no-explicit-any -// deno-lint-ignore-file no-implicit-any - -// Adapted from node_modules/events/events.js for Deno - -// Copyright Joyent, Inc. and other Node contributors. +/* eslint-disable no-console */ +// deno-lint-ignore-file no-explicit-any +// deno-lint-ignore-file no-implicit-any +// Adapted from node_modules/events/events.js for Deno +// Copyright Joyent, Inc. and other Node contributors. // -// Permission is hereby granted, free of charge, to any person obtaining a -// copy of this software and associated documentation files (the -// "Software"), to deal in the Software without restriction, including -// without limitation the rights to use, copy, modify, merge, publish, -// distribute, sublicense, and/or sell copies of the Software, and to permit -// persons to whom the Software is furnished to do so, subject to the -// following conditions: +// Permission is hereby granted, free of charge, to any person obtaining a +// copy of this software and associated documentation files (the +// "Software"), to deal in the Software without restriction, including +// without limitation the rights to use, copy, modify, merge, publish, +// distribute, sublicense, and/or sell copies of the Software, and to permit +// persons to whom the Software is furnished to do so, subject to the +// following conditions: // -// The above copyright notice and this permission notice shall be included -// in all copies or substantial portions of the Software. +// The above copyright notice and this permission notice shall be included +// in all copies or substantial portions of the Software. // -// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS -// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF -// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN -// NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, -// DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR -// OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE -// USE OR OTHER DEALINGS IN THE SOFTWARE. - -const R = typeof Reflect === 'object' ? Reflect : null; -const ReflectApply = R && typeof R.apply === 'function' +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS +// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF +// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN +// NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, +// DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR +// OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE +// USE OR OTHER DEALINGS IN THE SOFTWARE. +const R = typeof Reflect === "object" ? Reflect : null; +const ReflectApply = R && typeof R.apply === "function" ? R.apply - : function ReflectApply (target: any, receiver: any, args: any) { + : function ReflectApply(target, receiver, args) { return Function.prototype.apply.call(target, receiver, args); }; - -let ReflectOwnKeys: any; -if (R && typeof R.ownKeys === 'function') { +let ReflectOwnKeys; +if (R && typeof R.ownKeys === "function") { ReflectOwnKeys = R.ownKeys; } else if (Object.getOwnPropertySymbols) { - ReflectOwnKeys = function ReflectOwnKeys (target: any) { - return Object.getOwnPropertyNames(target) - // @ts-ignore suppress + ReflectOwnKeys = function ReflectOwnKeys(target) { + return Object.getOwnPropertyNames(target) // @ts-ignore suppress .concat(Object.getOwnPropertySymbols(target)); }; } else { - ReflectOwnKeys = function ReflectOwnKeys (target: any) { + ReflectOwnKeys = function ReflectOwnKeys(target) { return Object.getOwnPropertyNames(target); }; } - -function ProcessEmitWarning (warning: any) { +function ProcessEmitWarning(warning) { if (console && console.warn) console.warn(warning); } - -const NumberIsNaN = Number.isNaN || function NumberIsNaN (value) { - return value !== value; -}; - -function EventEmitter (this: any) { +const NumberIsNaN = Number.isNaN || + function NumberIsNaN(value) { + return value !== value; + }; +function EventEmitter() { EventEmitter.init.call(this); } - -// Backwards-compat with node 0.10.x +// Backwards-compat with node 0.10.x EventEmitter.EventEmitter = EventEmitter; - EventEmitter.prototype._events = undefined; EventEmitter.prototype._eventsCount = 0; EventEmitter.prototype._maxListeners = undefined; - -// By default EventEmitters will print a warning if more than 10 listeners are -// added to it. This is a useful default which helps finding memory leaks. +// By default EventEmitters will print a warning if more than 10 listeners are +// added to it. This is a useful default which helps finding memory leaks. let defaultMaxListeners = 10; - -function checkListener (listener: any) { - if (typeof listener !== 'function') { +function checkListener(listener) { + if (typeof listener !== "function") { throw new TypeError( - 'The "listener" argument must be of type Function. Received type ' + - typeof listener + 'The "listener" argument must be of type Function. Received type ' + + typeof listener, ); } } - -Object.defineProperty(EventEmitter, 'defaultMaxListeners', { +Object.defineProperty(EventEmitter, "defaultMaxListeners", { enumerable: true, - get () { + get() { return defaultMaxListeners; }, - set (arg) { - if (typeof arg !== 'number' || arg < 0 || NumberIsNaN(arg)) { + set(arg) { + if (typeof arg !== "number" || arg < 0 || NumberIsNaN(arg)) { throw new RangeError( - 'The value of "defaultMaxListeners" is out of range. It must be a non-negative number. Received ' + - arg + '.' + 'The value of "defaultMaxListeners" is out of range. It must be a non-negative number. Received ' + + arg + + ".", ); } defaultMaxListeners = arg; - } + }, }); - -EventEmitter.init = function (this: { _events: any, _eventsCount: number, _maxListeners: number | undefined }) { +EventEmitter.init = function () { if ( this._events === undefined || this._events === Object.getPrototypeOf(this)._events @@ -103,73 +91,62 @@ EventEmitter.init = function (this: { _events: any, _eventsCount: number, _maxLi this._events = Object.create(null); this._eventsCount = 0; } - this._maxListeners = this._maxListeners || undefined; }; - -// Obviously not all Emitters should be limited to 10. This function allows -// that to be increased. Set to zero for unlimited. -EventEmitter.prototype.setMaxListeners = function setMaxListeners (n: number) { - if (typeof n !== 'number' || n < 0 || NumberIsNaN(n)) { +// Obviously not all Emitters should be limited to 10. This function allows +// that to be increased. Set to zero for unlimited. +EventEmitter.prototype.setMaxListeners = function setMaxListeners(n) { + if (typeof n !== "number" || n < 0 || NumberIsNaN(n)) { throw new RangeError( - 'The value of "n" is out of range. It must be a non-negative number. Received ' + - n + '.' + 'The value of "n" is out of range. It must be a non-negative number. Received ' + + n + + ".", ); } this._maxListeners = n; return this; }; - -function _getMaxListeners (that: any) { +function _getMaxListeners(that) { if (that._maxListeners === undefined) { - // @ts-ignore suppress + // @ts-ignore suppress return EventEmitter.defaultMaxListeners; } return that._maxListeners; } - -EventEmitter.prototype.getMaxListeners = function getMaxListeners () { +EventEmitter.prototype.getMaxListeners = function getMaxListeners() { return _getMaxListeners(this); }; - -EventEmitter.prototype.emit = function emit (type: any) { +EventEmitter.prototype.emit = function emit(type) { const args = []; for (let i = 1; i < arguments.length; i++) args.push(arguments[i]); - let doError = (type === 'error'); - + let doError = type === "error"; const events = this._events; if (events !== undefined) { doError = doError && events.error === undefined; } else if (!doError) { return false; - } - - // If there is no 'error' event listener then throw. + } // If there is no 'error' event listener then throw. if (doError) { let er; if (args.length > 0) { er = args[0]; } if (er instanceof Error) { - // Note: The comments on the `throw` lines are intentional, they show - // up in Node's output if this results in an unhandled exception. - throw er; // Unhandled 'error' event - } - // At least give some kind of context to the user - const err: any = new Error( - 'Unhandled error.' + (er ? ' (' + er.message + ')' : '') + // Note: The comments on the `throw` lines are intentional, they show + // up in Node's output if this results in an unhandled exception. + throw er; // Unhandled 'error' event + } // At least give some kind of context to the user + const err = new Error( + "Unhandled error." + (er ? " (" + er.message + ")" : ""), ); err.context = er; - throw err; // Unhandled 'error' event + throw err; // Unhandled 'error' event } - const handler = events[type]; - if (handler === undefined) { return false; } - - if (typeof handler === 'function') { + if (typeof handler === "function") { ReflectApply(handler, this, args); } else { const len = handler.length; @@ -178,89 +155,77 @@ EventEmitter.prototype.emit = function emit (type: any) { ReflectApply(listeners[i], this, args); } } - return true; }; - -function _addListener (target: any, type: any, listener: any, prepend: any) { +function _addListener(target, type, listener, prepend) { let m; let events; let existing; - checkListener(listener); - events = target._events; if (events === undefined) { events = target._events = Object.create(null); target._eventsCount = 0; } else { - // To avoid recursion in the case that type === "newListener"! Before - // adding it to the listeners, first emit "newListener". + // To avoid recursion in the case that type === "newListener"! Before + // adding it to the listeners, first emit "newListener". if (events.newListener !== undefined) { target.emit( - 'newListener', + "newListener", type, - listener.listener ? listener.listener : listener - ); - - // Re-assign `events` because a newListener handler could have caused the - // this._events to be assigned to a new object + listener.listener ? listener.listener : listener, + ); // Re-assign `events` because a newListener handler could have caused the // this._events to be assigned to a new object events = target._events; } existing = events[type]; } - if (existing === undefined) { - // Optimize the case of one listener. Don't need the extra array object. + // Optimize the case of one listener. Don't need the extra array object. existing = events[type] = listener; ++target._eventsCount; } else { - if (typeof existing === 'function') { - // Adding the second element, need to change to array. + if (typeof existing === "function") { + // Adding the second element, need to change to array. existing = events[type] = prepend ? [listener, existing] - : [existing, listener]; - // If we've already got an array, just append. + : [existing, listener]; // If we've already got an array, just append. } else if (prepend) { existing.unshift(listener); } else { existing.push(listener); - } - - // Check for listener leak + } // Check for listener leak m = _getMaxListeners(target); if (m > 0 && existing.length > m && !existing.warned) { - existing.warned = true; - // No error code for this since it is a Warning - // eslint-disable-next-line no-restricted-syntax - const w: any = new Error( - 'Possible EventEmitter memory leak detected. ' + - existing.length + ' ' + String(type) + ' listeners ' + - 'added. Use emitter.setMaxListeners() to ' + - 'increase limit' + existing.warned = true; // No error code for this since it is a Warning // eslint-disable-next-line no-restricted-syntax + const w = new Error( + "Possible EventEmitter memory leak detected. " + + existing.length + + " " + + String(type) + + " listeners " + + "added. Use emitter.setMaxListeners() to " + + "increase limit", ); - w.name = 'MaxListenersExceededWarning'; + w.name = "MaxListenersExceededWarning"; w.emitter = target; w.type = type; w.count = existing.length; ProcessEmitWarning(w); } } - return target; } - -EventEmitter.prototype.addListener = function addListener (type: any, listener: any) { +EventEmitter.prototype.addListener = function addListener(type, listener) { return _addListener(this, type, listener, false); }; - EventEmitter.prototype.on = EventEmitter.prototype.addListener; - -EventEmitter.prototype.prependListener = function prependListener (type: any, listener: any) { +EventEmitter.prototype.prependListener = function prependListener( + type, + listener, +) { return _addListener(this, type, listener, true); }; - -function onceWrapper (this: any) { +function onceWrapper() { if (!this.fired) { this.target.removeListener(this.type, this.wrapFn); this.fired = true; @@ -270,63 +235,60 @@ function onceWrapper (this: any) { return this.listener.apply(this.target, arguments); } } - -function _onceWrap (target: any, type: any, listener: any) { +function _onceWrap(target, type, listener) { const state = { fired: false, wrapFn: undefined, target, type, - listener + listener, }; - const wrapped: any = onceWrapper.bind(state); + const wrapped = onceWrapper.bind(state); wrapped.listener = listener; state.wrapFn = wrapped; return wrapped; } - -EventEmitter.prototype.once = function once (type: any, listener: any) { +EventEmitter.prototype.once = function once(type, listener) { checkListener(listener); this.on(type, _onceWrap(this, type, listener)); return this; }; - -EventEmitter.prototype.prependOnceListener = function prependOnceListener (type: any, listener: any) { +EventEmitter.prototype.prependOnceListener = function prependOnceListener( + type, + listener, +) { checkListener(listener); this.prependListener(type, _onceWrap(this, type, listener)); return this; }; - -// Emits a 'removeListener' event if and only if the listener was removed. -EventEmitter.prototype.removeListener = function removeListener (type: any, listener: any ) { +// Emits a 'removeListener' event if and only if the listener was removed. +EventEmitter.prototype.removeListener = function removeListener( + type, + listener, +) { const events = this._events; const list = events[type]; let position; let i; let originalListener; - checkListener(listener); - if (events === undefined) { return this; } - if (list === undefined) { return this; } - if (list === listener || list.listener === listener) { if (--this._eventsCount === 0) { this._events = Object.create(null); } else { delete events[type]; if (events.removeListener) { - this.emit('removeListener', type, list.listener || listener); + this.emit("removeListener", type, list.listener || listener); } } - } else if (typeof list !== 'function') { + } else if (typeof list !== "function") { position = -1; - for (i = list.length - 1; i >= 0; i--) { if (list[i] === listener || list[i].listener === listener) { originalListener = list[i].listener; @@ -334,41 +296,31 @@ EventEmitter.prototype.removeListener = function removeListener (type: any, list break; } } - if (position < 0) { return this; } - if (position === 0) { list.shift(); } else { spliceOne(list, position); } - if (list.length === 1) { events[type] = list[0]; } - if (events.removeListener !== undefined) { - this.emit('removeListener', type, originalListener || listener); + this.emit("removeListener", type, originalListener || listener); } } - return this; }; - EventEmitter.prototype.off = EventEmitter.prototype.removeListener; - -EventEmitter.prototype.removeAllListeners = function removeAllListeners (type: any) { +EventEmitter.prototype.removeAllListeners = function removeAllListeners(type) { const events = this._events; const listeners = events[type]; let i; - if (events === undefined) { return this; - } - - // not listening for removeListener, no need to emit + } // not listening for removeListener, no need to emit if (events.removeListener === undefined) { if (arguments.length === 0) { this._events = Object.create(null); @@ -381,155 +333,130 @@ EventEmitter.prototype.removeAllListeners = function removeAllListeners (type: a } } return this; - } - - // emit removeListener for all listeners on all events + } // emit removeListener for all listeners on all events if (arguments.length === 0) { const keys = Object.keys(events); for (i = 0; i < keys.length; ++i) { const key = keys[i]; - if (key === 'removeListener') continue; + if (key === "removeListener") continue; this.removeAllListeners(key); } - this.removeAllListeners('removeListener'); + this.removeAllListeners("removeListener"); this._events = Object.create(null); this._eventsCount = 0; return this; } - - if (typeof listeners === 'function') { + if (typeof listeners === "function") { this.removeListener(type, listeners); } else if (listeners !== undefined) { - // LIFO order + // LIFO order for (i = listeners.length - 1; i >= 0; i--) { this.removeListener(type, listeners[i]); } } - return this; }; - -function _listeners (target: any, type: any, unwrap: any) { +function _listeners(target, type, unwrap) { const events = target._events; - if (events === undefined) { return []; } - const evlistener = events[type]; if (evlistener === undefined) { return []; } - - if (typeof evlistener === 'function') { + if (typeof evlistener === "function") { return unwrap ? [evlistener.listener || evlistener] : [evlistener]; } - return unwrap ? unwrapListeners(evlistener) : arrayClone(evlistener, evlistener.length); } - -EventEmitter.prototype.listeners = function listeners (type: any) { +EventEmitter.prototype.listeners = function listeners(type) { return _listeners(this, type, true); }; - -EventEmitter.prototype.rawListeners = function rawListeners (type: any) { +EventEmitter.prototype.rawListeners = function rawListeners(type) { return _listeners(this, type, false); }; - -EventEmitter.listenerCount = function (emitter: any, type: any) { - if (typeof emitter.listenerCount === 'function') { +EventEmitter.listenerCount = function (emitter, type) { + if (typeof emitter.listenerCount === "function") { return emitter.listenerCount(type); } else { return listenerCount.call(emitter, type); } }; - EventEmitter.prototype.listenerCount = listenerCount; -function listenerCount (this: any, type: any) { +function listenerCount(type) { const events = this._events; - if (events !== undefined) { const evlistener = events[type]; - - if (typeof evlistener === 'function') { + if (typeof evlistener === "function") { return 1; } else if (evlistener !== undefined) { return evlistener.length; } } - return 0; } - -EventEmitter.prototype.eventNames = function eventNames () { +EventEmitter.prototype.eventNames = function eventNames() { return this._eventsCount > 0 ? ReflectOwnKeys(this._events) : []; }; - -function arrayClone (arr: any, n: any) { +function arrayClone(arr, n) { const copy = new Array(n); for (let i = 0; i < n; ++i) { copy[i] = arr[i]; } return copy; } - -function spliceOne (list: any, index: any) { +function spliceOne(list, index) { for (; index + 1 < list.length; index++) { list[index] = list[index + 1]; } list.pop(); } - -function unwrapListeners (arr: any) { +function unwrapListeners(arr) { const ret = new Array(arr.length); for (let i = 0; i < ret.length; ++i) { ret[i] = arr[i].listener || arr[i]; } return ret; } - -function once (emitter: any, name: any) { +function once(emitter, name) { return new Promise(function (resolve, reject) { - function errorListener (err: Error) { + function errorListener(err) { emitter.removeListener(name, resolver); reject(err); } - - function resolver () { - if (typeof emitter.removeListener === 'function') { - emitter.removeListener('error', errorListener); + function resolver() { + if (typeof emitter.removeListener === "function") { + emitter.removeListener("error", errorListener); } resolve([].slice.call(arguments)); } - eventTargetAgnosticAddListener(emitter, name, resolver, { once: true }); - if (name !== 'error') { + if (name !== "error") { addErrorHandlerIfEventEmitter(emitter, errorListener, { once: true }); } }); } - -function addErrorHandlerIfEventEmitter (emitter: any, handler: any, flags: any) { - if (typeof emitter.on === 'function') { - eventTargetAgnosticAddListener(emitter, 'error', handler, flags); +function addErrorHandlerIfEventEmitter(emitter, handler, flags) { + if (typeof emitter.on === "function") { + eventTargetAgnosticAddListener(emitter, "error", handler, flags); } } - -function eventTargetAgnosticAddListener (emitter: any, name: any, listener: any, flags: any) { - if (typeof emitter.on === 'function') { +function eventTargetAgnosticAddListener(emitter, name, listener, flags) { + if (typeof emitter.on === "function") { if (flags.once) { emitter.once(name, listener); } else { emitter.on(name, listener); } - } else if (typeof emitter.addEventListener === 'function') { - // EventTarget does not have `error` event semantics like Node - // EventEmitters, we do not listen for `error` events here. - emitter.addEventListener(name, function wrapListener (arg: any) { - // IE does not have builtin `{ once: true }` support so we - // have to do it manually. + } else if (typeof emitter.addEventListener === "function") { + // EventTarget does not have `error` event semantics like Node + // EventEmitters, we do not listen for `error` events here. + emitter.addEventListener(name, function wrapListener(arg) { + // IE does not have builtin `{ once: true }` support so we + // have to do it manually. if (flags.once) { emitter.removeEventListener(name, wrapListener); } @@ -537,10 +464,9 @@ function eventTargetAgnosticAddListener (emitter: any, name: any, listener: any, }); } else { throw new TypeError( - 'The "emitter" argument must be of type EventEmitter. Received type ' + - typeof emitter + 'The "emitter" argument must be of type EventEmitter. Received type ' + + typeof emitter, ); } } - export { EventEmitter }; diff --git a/main/commons/src/index.ts b/main/commons/src/index.ts index c77f51ad0f..273c78aae2 100644 --- a/main/commons/src/index.ts +++ b/main/commons/src/index.ts @@ -1,69 +1,69 @@ -export * from './testing.ts'; +export * from "./testing.ts"; // Removes all leading and trailing slashes from a path -export function stripSlashes (name: string) { - return name.replace(/^(\/+)|(\/+)$/g, ''); +export function stripSlashes(name: string) { + return name.replace(/^(\/+)|(\/+)$/g, ""); } export type KeyValueCallback = (value: any, key: string) => T; // A set of lodash-y utility functions that use ES6 export const _ = { - each (obj: any, callback: KeyValueCallback) { - if (obj && typeof obj.forEach === 'function') { + each(obj: any, callback: KeyValueCallback) { + if (obj && typeof obj.forEach === "function") { obj.forEach(callback); } else if (_.isObject(obj)) { - Object.keys(obj).forEach(key => callback(obj[key], key)); + Object.keys(obj).forEach((key) => callback(obj[key], key)); } }, - some (value: any, callback: KeyValueCallback) { + some(value: any, callback: KeyValueCallback) { return Object.keys(value) - .map(key => [ value[key], key ]) + .map((key) => [value[key], key]) .some(([val, key]) => callback(val, key)); }, - every (value: any, callback: KeyValueCallback) { + every(value: any, callback: KeyValueCallback) { return Object.keys(value) - .map(key => [ value[key], key ]) + .map((key) => [value[key], key]) .every(([val, key]) => callback(val, key)); }, - keys (obj: any) { + keys(obj: any) { return Object.keys(obj); }, - values (obj: any) { - return _.keys(obj).map(key => obj[key]); + values(obj: any) { + return _.keys(obj).map((key) => obj[key]); }, - isMatch (obj: any, item: any) { - return _.keys(item).every(key => obj[key] === item[key]); + isMatch(obj: any, item: any) { + return _.keys(item).every((key) => obj[key] === item[key]); }, - isEmpty (obj: any) { + isEmpty(obj: any) { return _.keys(obj).length === 0; }, - isObject (item: any) { - return (typeof item === 'object' && !Array.isArray(item) && item !== null); + isObject(item: any) { + return typeof item === "object" && !Array.isArray(item) && item !== null; }, - isObjectOrArray (value: any) { - return typeof value === 'object' && value !== null; + isObjectOrArray(value: any) { + return typeof value === "object" && value !== null; }, - extend (first: any, ...rest: any[]) { + extend(first: any, ...rest: any[]) { return Object.assign(first, ...rest); }, - omit (obj: any, ...keys: string[]) { + omit(obj: any, ...keys: string[]) { const result = _.extend({}, obj); - keys.forEach(key => delete result[key]); + keys.forEach((key) => delete result[key]); return result; }, - pick (source: any, ...keys: string[]) { + pick(source: any, ...keys: string[]) { return keys.reduce((result: { [key: string]: any }, key) => { if (source[key] !== undefined) { result[key] = source[key]; @@ -74,9 +74,9 @@ export const _ = { }, // Recursively merge the source object into the target object - merge (target: any, source: any) { + merge(target: any, source: any) { if (_.isObject(target) && _.isObject(source)) { - Object.keys(source).forEach(key => { + Object.keys(source).forEach((key) => { if (_.isObject(source[key])) { if (!target[key]) { Object.assign(target, { [key]: {} }); @@ -89,17 +89,18 @@ export const _ = { }); } return target; - } + }, }; // Duck-checks if an object looks like a promise -export function isPromise (result: any) { - return _.isObject(result) && - typeof result.then === 'function'; +export function isPromise(result: any) { + return _.isObject(result) && typeof result.then === "function"; } -export function createSymbol (name: string) { - return typeof Symbol !== 'undefined' ? Symbol(name) : name; +export function createSymbol(name: string) { + return typeof Symbol !== "undefined" ? Symbol(name) : name; } -export * from './debug.ts'; +export * from "./debug.ts"; + +export * from "./events.js"; diff --git a/main/commons/src/testing.ts b/main/commons/src/testing.ts index a4b438e101..55bbaffacd 100644 --- a/main/commons/src/testing.ts +++ b/main/commons/src/testing.ts @@ -1,20 +1,16 @@ // https://deno.land/manual/testing/assertions -import * as denoAssert from 'https://deno.land/std@0.114.0/testing/asserts.ts'; +import * as denoAssert from "https://deno.land/std@0.159.0/testing/asserts.ts"; -const { assertEquals } = denoAssert +const { assertEquals } = denoAssert; -export * from 'https://deno.land/std@0.114.0/testing/asserts.ts'; +export * from "https://deno.land/std@0.159.0/testing/bdd.ts"; -export const it = (name: string, fn: () => any, only = false) => Deno.test({ - only, - name, - fn -}); +export * from "https://deno.land/std@0.159.0/testing/asserts.ts"; -it.only = (name: string, fn: () => any) => it(name, fn, true); - -export const assert = { - deepStrictEqual (actual: unknown, expected: unknown, msg?: string) { - return assertEquals(actual, expected, msg) - } +export function assertDeepStrictEquals( + actual: unknown, + expected: unknown, + msg?: string +) { + return assertEquals(actual, expected, msg); } diff --git a/main/commons/test/debug.test.ts b/main/commons/test/debug.test.ts index eac1f9f8c1..80a83afd2a 100644 --- a/main/commons/test/debug.test.ts +++ b/main/commons/test/debug.test.ts @@ -1,28 +1,30 @@ -import { it, assertEquals, assertStrictEquals } from '../src/testing.ts'; -import { createDebug, setDebug, noopDebug } from '../src/index.ts'; +import { it, assertEquals, assertStrictEquals } from "../src/testing.ts"; +import { createDebug, setDebug, noopDebug } from "../src/index.ts"; -const myDebug = createDebug('hello test'); +const myDebug = createDebug("hello test"); -it('default debug does nothing', () => { - assertStrictEquals(myDebug('hi', 'there'), undefined); +it("default debug does nothing", () => { + assertStrictEquals(myDebug("hi", "there"), undefined); }); -it('can set custom debug later', () => { +it("can set custom debug later", () => { let call; - const customDebug = (name: string) => (...args: any[]) => { - call = [ name ].concat(args); - } + const customDebug = + (name: string) => + (...args: any[]) => { + call = [name].concat(args); + }; setDebug(customDebug); - assertStrictEquals(myDebug('hi', 'there'), undefined); - assertEquals(call, [ 'hello test', 'hi', 'there' ]); + assertStrictEquals(myDebug("hi", "there"), undefined); + assertEquals(call, ["hello test", "hi", "there"]); - const newDebug = createDebug('other test'); + const newDebug = createDebug("other test"); - assertStrictEquals(newDebug('other', 'there'), undefined); - assertEquals(call, [ 'other test', 'other', 'there' ]); + assertStrictEquals(newDebug("other", "there"), undefined); + assertEquals(call, ["other test", "other", "there"]); setDebug(noopDebug); }); diff --git a/main/commons/test/module.test.ts b/main/commons/test/module.test.ts index b64291d195..6755594fde 100644 --- a/main/commons/test/module.test.ts +++ b/main/commons/test/module.test.ts @@ -1,24 +1,24 @@ -import { it, assertStrictEquals } from '../src/testing.ts'; -import { _ } from '../src/index.ts'; -import * as commons from '../src/index.ts' +import { it, assertStrictEquals } from "../src/testing.ts"; +import { _ } from "../src/index.ts"; +import * as commons from "../src/index.ts"; -it('commons: is commonjs compatible', () => { - assertStrictEquals(typeof commons, 'object'); - assertStrictEquals(typeof commons.stripSlashes, 'function'); - assertStrictEquals(typeof commons._, 'object'); +it("commons: is commonjs compatible", () => { + assertStrictEquals(typeof commons, "object"); + assertStrictEquals(typeof commons.stripSlashes, "function"); + assertStrictEquals(typeof commons._, "object"); }); -it('commons: exposes lodash methods under _', () => { - assertStrictEquals(typeof _.each, 'function'); - assertStrictEquals(typeof _.some, 'function'); - assertStrictEquals(typeof _.every, 'function'); - assertStrictEquals(typeof _.keys, 'function'); - assertStrictEquals(typeof _.values, 'function'); - assertStrictEquals(typeof _.isMatch, 'function'); - assertStrictEquals(typeof _.isEmpty, 'function'); - assertStrictEquals(typeof _.isObject, 'function'); - assertStrictEquals(typeof _.extend, 'function'); - assertStrictEquals(typeof _.omit, 'function'); - assertStrictEquals(typeof _.pick, 'function'); - assertStrictEquals(typeof _.merge, 'function'); +it("commons: exposes lodash methods under _", () => { + assertStrictEquals(typeof _.each, "function"); + assertStrictEquals(typeof _.some, "function"); + assertStrictEquals(typeof _.every, "function"); + assertStrictEquals(typeof _.keys, "function"); + assertStrictEquals(typeof _.values, "function"); + assertStrictEquals(typeof _.isMatch, "function"); + assertStrictEquals(typeof _.isEmpty, "function"); + assertStrictEquals(typeof _.isObject, "function"); + assertStrictEquals(typeof _.extend, "function"); + assertStrictEquals(typeof _.omit, "function"); + assertStrictEquals(typeof _.pick, "function"); + assertStrictEquals(typeof _.merge, "function"); }); diff --git a/main/commons/test/utils.test.ts b/main/commons/test/utils.test.ts index 7eb07dca9b..f16dbb0c42 100644 --- a/main/commons/test/utils.test.ts +++ b/main/commons/test/utils.test.ts @@ -1,161 +1,217 @@ /* tslint:disable:no-unused-expression */ -import { it, assert, assertEquals, assertStrictEquals } from '../src/testing.ts'; -import { _, stripSlashes, isPromise, createSymbol } from '../src/index.ts'; - -it('stripSlashes', () => { - assertStrictEquals(stripSlashes('some/thing'), 'some/thing'); - assertStrictEquals(stripSlashes('/some/thing'), 'some/thing'); - assertStrictEquals(stripSlashes('some/thing/'), 'some/thing'); - assertStrictEquals(stripSlashes('/some/thing/'), 'some/thing'); - assertStrictEquals(stripSlashes('//some/thing/'), 'some/thing'); - assertStrictEquals(stripSlashes('//some//thing////'), 'some//thing'); -}); - -it('isPromise', () => { +import { + it, + assert, + assertEquals, + assertStrictEquals, +} from "../src/testing.ts"; +import { _, stripSlashes, isPromise, createSymbol } from "../src/index.ts"; + +it("stripSlashes", () => { + assertStrictEquals(stripSlashes("some/thing"), "some/thing"); + assertStrictEquals(stripSlashes("/some/thing"), "some/thing"); + assertStrictEquals(stripSlashes("some/thing/"), "some/thing"); + assertStrictEquals(stripSlashes("/some/thing/"), "some/thing"); + assertStrictEquals(stripSlashes("//some/thing/"), "some/thing"); + assertStrictEquals(stripSlashes("//some//thing////"), "some//thing"); +}); + +it("isPromise", () => { assertStrictEquals(isPromise(Promise.resolve()), true); - assert(isPromise({ - then () {} - })); + assert( + isPromise({ + then() {}, + }) + ); assertStrictEquals(isPromise(null), false); }); -it('createSymbol', () => { - assertStrictEquals(typeof createSymbol('a test'), 'symbol'); +it("createSymbol", () => { + assertStrictEquals(typeof createSymbol("a test"), "symbol"); }); -it('isObject', () => { +it("isObject", () => { assertStrictEquals(_.isObject({}), true); assertStrictEquals(_.isObject([]), false); assertStrictEquals(_.isObject(null), false); }); -it('isObjectOrArray', () => { +it("isObjectOrArray", () => { assertStrictEquals(_.isObjectOrArray({}), true); assertStrictEquals(_.isObjectOrArray([]), true); assertStrictEquals(_.isObjectOrArray(null), false); }); -it('each', () => { - _.each({ hi: 'there' }, (value, key) => { - assertStrictEquals(key, 'hi'); - assertStrictEquals(value, 'there'); +it("each", () => { + _.each({ hi: "there" }, (value, key) => { + assertStrictEquals(key, "hi"); + assertStrictEquals(value, "there"); }); - _.each([ 'hi' ], (value, key) => { + _.each(["hi"], (value, key) => { assertStrictEquals(key, 0); - assertStrictEquals(value, 'hi'); + assertStrictEquals(value, "hi"); }); - _.each('moo', () => { - throw new Error('Should never get here') + _.each("moo", () => { + throw new Error("Should never get here"); }); }); -it('some', () => { - assert(_.some([ 'a', 'b' ], current => current === 'a')); - assert(!_.some([ 'a', 'b' ], current => current === 'c')); +it("some", () => { + assert(_.some(["a", "b"], (current) => current === "a")); + assert(!_.some(["a", "b"], (current) => current === "c")); }); -it('every', () => { - assert(_.every([ 'a', 'a' ], current => current === 'a')); - assert(!_.every([ 'a', 'b' ], current => current === 'a')); +it("every", () => { + assert(_.every(["a", "a"], (current) => current === "a")); + assert(!_.every(["a", "b"], (current) => current === "a")); }); -it('keys', () => { - const data = { hi: 'there', name: 'David' }; - assertEquals(_.keys(data), [ 'hi', 'name' ]); +it("keys", () => { + const data = { hi: "there", name: "David" }; + assertEquals(_.keys(data), ["hi", "name"]); }); -it('values', () => { - const data = { hi: 'there', name: 'David' }; - assertEquals(_.values(data), [ 'there', 'David' ]); +it("values", () => { + const data = { hi: "there", name: "David" }; + assertEquals(_.values(data), ["there", "David"]); }); -it('isMatch', () => { - assert(_.isMatch({ - test: 'me', hi: 'you', more: true - }, { - test: 'me', hi: 'you' - })); +it("isMatch", () => { + assert( + _.isMatch( + { + test: "me", + hi: "you", + more: true, + }, + { + test: "me", + hi: "you", + } + ) + ); - assert(!_.isMatch({ - test: 'me', hi: 'you', more: true - }, { - test: 'me', hi: 'there' - })); + assert( + !_.isMatch( + { + test: "me", + hi: "you", + more: true, + }, + { + test: "me", + hi: "there", + } + ) + ); }); -it('isEmpty', () => { +it("isEmpty", () => { assert(_.isEmpty({})); - assert(!_.isEmpty({ name: 'David' })); -}); - -it('extend', () => { - assertEquals(_.extend({ hi: 'there' }, { name: 'david' }), { - hi: 'there', - name: 'david' - }); + assert(!_.isEmpty({ name: "David" })); }); -it('omit', () => { - assertEquals(_.omit({ - name: 'David', - first: 1, - second: 2 - }, 'first', 'second'), { - name: 'David' +it("extend", () => { + assertEquals(_.extend({ hi: "there" }, { name: "david" }), { + hi: "there", + name: "david", }); }); -it('pick', () => { - assertEquals(_.pick({ - name: 'David', - first: 1, - second: 2 - }, 'first', 'second'), { - first: 1, - second: 2 - }); - - assertEquals(_.pick({ - name: 'David', - first: 1 - }, 'first', 'second'), { - first: 1 - }); +it("omit", () => { + assertEquals( + _.omit( + { + name: "David", + first: 1, + second: 2, + }, + "first", + "second" + ), + { + name: "David", + } + ); +}); + +it("pick", () => { + assertEquals( + _.pick( + { + name: "David", + first: 1, + second: 2, + }, + "first", + "second" + ), + { + first: 1, + second: 2, + } + ); + + assertEquals( + _.pick( + { + name: "David", + first: 1, + }, + "first", + "second" + ), + { + first: 1, + } + ); }); -it('merge', () => { - assertEquals(_.merge({ hi: 'there' }, { name: 'david' }), { - hi: 'there', - name: 'david' +it("merge", () => { + assertEquals(_.merge({ hi: "there" }, { name: "david" }), { + hi: "there", + name: "david", }); - assertEquals(_.merge({}, { - name: 'david', - nested: { obj: true } - }), { - name: 'david', - nested: { obj: true } - }); + assertEquals( + _.merge( + {}, + { + name: "david", + nested: { obj: true }, + } + ), + { + name: "david", + nested: { obj: true }, + } + ); - assertEquals(_.merge({ name: 'david' }, {}), { - name: 'david' + assertEquals(_.merge({ name: "david" }, {}), { + name: "david", }); - assertEquals(_.merge({ - hi: 'there', - my: { - name: { is: 'david' }, - number: { is: 1 } + assertEquals( + _.merge( + { + hi: "there", + my: { + name: { is: "david" }, + number: { is: 1 }, + }, + }, + { my: { name: { is: "eric" } } } + ), + { + hi: "there", + my: { + number: { is: 1 }, + name: { is: "eric" }, + }, } - }, { my: { name: { is: 'eric' } } }), { - hi: 'there', - my: { - number: { is: 1 }, - name: { is: 'eric' } - } - }); + ); - assertStrictEquals(_.merge('hello', {}), 'hello'); + assertStrictEquals(_.merge("hello", {}), "hello"); }); diff --git a/main/errors/LICENSE b/main/errors/LICENSE index 3f395cc665..59604f46f3 100644 --- a/main/errors/LICENSE +++ b/main/errors/LICENSE @@ -1,6 +1,6 @@ The MIT License (MIT) -Copyright (c) 2021 Feathers +Copyright (c) 2022 Feathers Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated documentation files (the "Software"), to deal diff --git a/main/errors/mod.ts b/main/errors/mod.ts new file mode 100644 index 0000000000..3b3419b271 --- /dev/null +++ b/main/errors/mod.ts @@ -0,0 +1 @@ +export * from "./src/index.ts"; diff --git a/main/errors/src/index.ts b/main/errors/src/index.ts index 8d7e155356..e9b99d69d1 100644 --- a/main/errors/src/index.ts +++ b/main/errors/src/index.ts @@ -8,9 +8,14 @@ export interface FeathersErrorJSON { } export type DynamicError = Error & { [key: string]: any }; -export type ErrorMessage = string | DynamicError | { [key: string]: any } | any[]; - -interface ErrorProperties extends Omit { +export type ErrorMessage = + | null + | string + | DynamicError + | { [key: string]: any } + | any[]; + +interface ErrorProperties extends Omit { type: string; } @@ -21,19 +26,26 @@ export class FeathersError extends Error { readonly data: any; readonly errors: any; - constructor (err: ErrorMessage | undefined, name: string, code: number, className: string, _data: any) { - let msg = typeof err === 'string' ? err : 'Error'; + constructor( + err: ErrorMessage | undefined, + name: string, + code: number, + className: string, + _data: any + ) { + let msg = typeof err === "string" ? err : "Error"; const properties: ErrorProperties = { name, code, className, - type: 'FeathersError' + type: "FeathersError", }; if (Array.isArray(_data)) { properties.data = _data; - } else if (typeof err === 'object' || _data !== undefined) { - const { message, errors, ...rest } = typeof err === 'object' ? err : _data; + } else if (typeof err === "object" || _data !== undefined) { + const { message, errors, ...rest } = + err !== null && typeof err === "object" ? err : _data; msg = message || msg; properties.errors = errors; @@ -44,12 +56,12 @@ export class FeathersError extends Error { Object.assign(this, properties); } - toJSON () { + toJSON() { const result: FeathersErrorJSON = { name: this.name, message: this.message, code: this.code, - className: this.className + className: this.className, }; if (this.data !== undefined) { @@ -65,120 +77,120 @@ export class FeathersError extends Error { } export class BadRequest extends FeathersError { - constructor (message?: ErrorMessage, data?: any) { - super(message, 'BadRequest', 400, 'bad-request', data); + constructor(message?: ErrorMessage, data?: any) { + super(message, "BadRequest", 400, "bad-request", data); } } // 401 - Not Authenticated -export class NotAuthenticated extends FeathersError{ - constructor (message?: ErrorMessage, data?: any) { - super(message, 'NotAuthenticated', 401, 'not-authenticated', data); +export class NotAuthenticated extends FeathersError { + constructor(message?: ErrorMessage, data?: any) { + super(message, "NotAuthenticated", 401, "not-authenticated", data); } } // 402 - Payment Error export class PaymentError extends FeathersError { - constructor (message?: ErrorMessage, data?: any) { - super(message, 'PaymentError', 402, 'payment-error', data); + constructor(message?: ErrorMessage, data?: any) { + super(message, "PaymentError", 402, "payment-error", data); } } // 403 - Forbidden export class Forbidden extends FeathersError { - constructor (message?: ErrorMessage, data?: any) { - super(message, 'Forbidden', 403, 'forbidden', data); + constructor(message?: ErrorMessage, data?: any) { + super(message, "Forbidden", 403, "forbidden", data); } } // 404 - Not Found export class NotFound extends FeathersError { - constructor (message?: ErrorMessage, data?: any) { - super(message, 'NotFound', 404, 'not-found', data); + constructor(message?: ErrorMessage, data?: any) { + super(message, "NotFound", 404, "not-found", data); } } // 405 - Method Not Allowed export class MethodNotAllowed extends FeathersError { - constructor (message?: ErrorMessage, data?: any) { - super(message, 'MethodNotAllowed', 405, 'method-not-allowed', data); + constructor(message?: ErrorMessage, data?: any) { + super(message, "MethodNotAllowed", 405, "method-not-allowed", data); } } // 406 - Not Acceptable export class NotAcceptable extends FeathersError { - constructor (message?: ErrorMessage, data?: any) { - super(message, 'NotAcceptable', 406, 'not-acceptable', data); + constructor(message?: ErrorMessage, data?: any) { + super(message, "NotAcceptable", 406, "not-acceptable", data); } } // 408 - Timeout export class Timeout extends FeathersError { - constructor (message?: ErrorMessage, data?: any) { - super(message, 'Timeout', 408, 'timeout', data); + constructor(message?: ErrorMessage, data?: any) { + super(message, "Timeout", 408, "timeout", data); } } // 409 - Conflict export class Conflict extends FeathersError { - constructor (message?: ErrorMessage, data?: any) { - super(message, 'Conflict', 409, 'conflict', data); + constructor(message?: ErrorMessage, data?: any) { + super(message, "Conflict", 409, "conflict", data); } } // 410 - Gone export class Gone extends FeathersError { - constructor (message?: ErrorMessage, data?: any) { - super(message, 'Gone', 410, 'gone', data); + constructor(message?: ErrorMessage, data?: any) { + super(message, "Gone", 410, "gone", data); } } // 411 - Length Required export class LengthRequired extends FeathersError { - constructor (message?: ErrorMessage, data?: any) { - super(message, 'LengthRequired', 411, 'length-required', data); + constructor(message?: ErrorMessage, data?: any) { + super(message, "LengthRequired", 411, "length-required", data); } } // 422 Unprocessable export class Unprocessable extends FeathersError { - constructor (message?: ErrorMessage, data?: any) { - super(message, 'Unprocessable', 422, 'unprocessable', data); + constructor(message?: ErrorMessage, data?: any) { + super(message, "Unprocessable", 422, "unprocessable", data); } } // 429 Too Many Requests export class TooManyRequests extends FeathersError { - constructor (message?: ErrorMessage, data?: any) { - super(message, 'TooManyRequests', 429, 'too-many-requests', data); + constructor(message?: ErrorMessage, data?: any) { + super(message, "TooManyRequests", 429, "too-many-requests", data); } } // 500 - General Error export class GeneralError extends FeathersError { - constructor (message?: ErrorMessage, data?: any) { - super(message, 'GeneralError', 500, 'general-error', data); + constructor(message?: ErrorMessage, data?: any) { + super(message, "GeneralError", 500, "general-error", data); } } // 501 - Not Implemented export class NotImplemented extends FeathersError { - constructor (message?: ErrorMessage, data?: any) { - super(message, 'NotImplemented', 501, 'not-implemented', data); + constructor(message?: ErrorMessage, data?: any) { + super(message, "NotImplemented", 501, "not-implemented", data); } } // 502 - Bad Gateway export class BadGateway extends FeathersError { - constructor (message?: ErrorMessage, data?: any) { - super(message, 'BadGateway', 502, 'bad-gateway', data); + constructor(message?: ErrorMessage, data?: any) { + super(message, "BadGateway", 502, "bad-gateway", data); } } // 503 - Unavailable export class Unavailable extends FeathersError { - constructor (message?: ErrorMessage, data?: any) { - super(message, 'Unavailable', 503, 'unavailable', data); + constructor(message?: ErrorMessage, data?: any) { + super(message, "Unavailable", 503, "unavailable", data); } } @@ -252,10 +264,10 @@ export const errors = { 500: GeneralError, 501: NotImplemented, 502: BadGateway, - 503: Unavailable -} + 503: Unavailable, +}; -export function convert (error: any) { +export function convert(error: any) { if (!error) { return error; } @@ -265,7 +277,7 @@ export function convert (error: any) { ? new FeathersError(error.message, error.data) : new Error(error.message || error); - if (typeof error === 'object') { + if (typeof error === "object") { Object.assign(result, error); } diff --git a/main/feathers/LICENSE b/main/feathers/LICENSE new file mode 100644 index 0000000000..59604f46f3 --- /dev/null +++ b/main/feathers/LICENSE @@ -0,0 +1,22 @@ +The MIT License (MIT) + +Copyright (c) 2022 Feathers + +Permission is hereby granted, free of charge, to any person obtaining a copy +of this software and associated documentation files (the "Software"), to deal +in the Software without restriction, including without limitation the rights +to use, copy, modify, merge, publish, distribute, sublicense, and/or sell +copies of the Software, and to permit persons to whom the Software is +furnished to do so, subject to the following conditions: + +The above copyright notice and this permission notice shall be included in all +copies or substantial portions of the Software. + +THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE +AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, +OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE +SOFTWARE. + diff --git a/readme.md b/main/feathers/README.md similarity index 85% rename from readme.md rename to main/feathers/README.md index 4890b8cee7..246462b472 100644 --- a/readme.md +++ b/main/feathers/README.md @@ -1,39 +1,37 @@ -Feathers logo - -## A framework for real-time applications and REST APIs with JavaScript and TypeScript - -[![CI](https://github.com/feathersjs/feathers/workflows/CI/badge.svg)](https://github.com/feathersjs/feathers/actions?query=workflow%3ACI) -[![Maintainability](https://api.codeclimate.com/v1/badges/cb5ec42a2d0cc1a47a02/maintainability)](https://codeclimate.com/github/feathersjs/feathers/maintainability) -[![Test Coverage](https://api.codeclimate.com/v1/badges/cb5ec42a2d0cc1a47a02/test_coverage)](https://codeclimate.com/github/feathersjs/feathers/test_coverage) -[![Download Status](https://img.shields.io/npm/dm/@feathersjs/feathers.svg?style=flat-square)](https://www.npmjs.com/package/@feathersjs/feathers) - -[![Slack Status](https://img.shields.io/badge/Slack-Join-brightgreen)](http://slack.feathersjs.com) -[![Telegram Status](https://img.shields.io/badge/Telegram_RU_chat:-Feathers-216bc1.svg?style=flat)](https://t.me/featherjs) - -Feathers is a lightweight web-framework for creating real-time applications and REST APIs using JavaScript or TypeScript. - -Feathers can interact with any backend technology, supports over a dozen databases and works with any frontend technology like React, VueJS, Angular, React Native, Android or iOS. - -## Getting started - -You can build your first real-time and REST API in just 4 commands: - -```bash -$ npm install -g @feathersjs/cli -$ mkdir my-new-app -$ cd my-new-app/ -$ feathers generate app -$ npm start -``` - -To learn more about Feathers visit the website at [feathersjs.com](http://feathersjs.com) or jump right into [the Feathers guides](http://docs.feathersjs.com/guides). - -## Documentation - -The [Feathers docs](http://docs.feathersjs.com) are loaded with awesome stuff and tell you every thing you need to know about using and configuring Feathers. - -## License - -Copyright (c) 2021 [Feathers contributors](https://github.com/feathersjs/feathers/graphs/contributors) - -Licensed under the [MIT license](LICENSE). +Feathers logo + +## A framework for real-time applications and REST APIs with JavaScript and TypeScript + +[![CI](https://github.com/feathersjs/feathers/workflows/CI/badge.svg)](https://github.com/feathersjs/feathers/actions?query=workflow%3ACI) +[![Maintainability](https://api.codeclimate.com/v1/badges/cb5ec42a2d0cc1a47a02/maintainability)](https://codeclimate.com/github/feathersjs/feathers/maintainability) +[![Test Coverage](https://api.codeclimate.com/v1/badges/cb5ec42a2d0cc1a47a02/test_coverage)](https://codeclimate.com/github/feathersjs/feathers/test_coverage) +[![Download Status](https://img.shields.io/npm/dm/@feathersjs/feathers.svg?style=flat-square)](https://www.npmjs.com/package/@feathersjs/feathers) +[![Discord](https://badgen.net/badge/icon/discord?icon=discord&label)](https://discord.gg/qa8kez8QBx) + +Feathers is a lightweight web-framework for creating real-time applications and REST APIs using JavaScript or TypeScript. + +Feathers can interact with any backend technology, supports over a dozen databases and works with any frontend technology like React, VueJS, Angular, React Native, Android or iOS. + +## Getting started + +You can build your first real-time and REST API in just 4 commands: + +```bash +$ npm install -g @feathersjs/cli +$ mkdir my-new-app +$ cd my-new-app/ +$ feathers generate app +$ npm start +``` + +To learn more about Feathers visit the website at [feathersjs.com](http://feathersjs.com) or jump right into [the Feathers guides](http://docs.feathersjs.com/guides). + +## Documentation + +The [Feathers docs](http://docs.feathersjs.com) are loaded with awesome stuff and tell you every thing you need to know about using and configuring Feathers. + +## License + +Copyright (c) 2022 [Feathers contributors](https://github.com/feathersjs/feathers/graphs/contributors) + +Licensed under the [MIT license](LICENSE). diff --git a/main/feathers/mod.ts b/main/feathers/mod.ts new file mode 100644 index 0000000000..3b3419b271 --- /dev/null +++ b/main/feathers/mod.ts @@ -0,0 +1 @@ +export * from "./src/index.ts"; diff --git a/main/feathers/src/application.ts b/main/feathers/src/application.ts new file mode 100644 index 0000000000..19db08556f --- /dev/null +++ b/main/feathers/src/application.ts @@ -0,0 +1,253 @@ +import version from "./version.ts"; +import { EventEmitter } from "../../commons/mod.ts"; +import { stripSlashes, createDebug } from "../../commons/mod.ts"; +import { + HOOKS, + hooks, + middleware, +} from "https://deno.land/x/hooks@v0.7.5/src/index.ts"; +import { eventHook, eventMixin } from "./events.ts"; +import { hookMixin } from "./hooks.ts"; +import { wrapService, getServiceOptions, protectedMethods } from "./service.ts"; +import { + FeathersApplication, + ServiceMixin, + Service, + ServiceOptions, + ServiceInterface, + Application, + FeathersService, + ApplicationHookOptions, +} from "./declarations.ts"; +import { enableHooks } from "./hooks.ts"; + +const debug = createDebug("@feathersjs/feathers"); + +export class Feathers + extends EventEmitter + implements FeathersApplication +{ + services: Services = {} as Services; + settings: Settings = {} as Settings; + mixins: ServiceMixin>[] = [ + hookMixin, + eventMixin, + ]; + version: string = version; + _isSetup = false; + + protected registerHooks: (this: any, allHooks: any) => any; + + constructor() { + super(); + this.registerHooks = enableHooks(this); + this.registerHooks({ + around: [eventHook], + }); + } + + get(name: L): Settings[L] { + return this.settings[name]; + } + + set(name: L, value: Settings[L]) { + this.settings[name] = value; + return this; + } + + configure(callback: (this: this, app: this) => void) { + callback.call(this, this); + + return this; + } + + defaultService(location: string): ServiceInterface { + throw new Error(`Can not find service '${location}'`); + } + + service( + location: L + ): FeathersService< + this, + keyof any extends keyof Services ? Service : Services[L] + > { + const path = (stripSlashes(location) || "/") as L; + const current = this.services[path]; + + if (typeof current === "undefined") { + this.use(path, this.defaultService(path) as any); + return this.service(path); + } + + return current as any; + } + + protected _setup() { + this._isSetup = true; + + return Object.keys(this.services as object) + .reduce( + (current, path) => + current.then(() => { + const service: any = this.service(path as any); + + if (typeof service.setup === "function") { + debug(`Setting up service for \`${path}\``); + + return service.setup(this, path); + } + }), + Promise.resolve() + ) + .then(() => this); + } + + get setup() { + return this._setup; + } + + set setup(value) { + this._setup = (value as any)[HOOKS] + ? value + : hooks( + value, + middleware().params("server").props({ + app: this, + }) + ); + } + + protected _teardown() { + this._isSetup = false; + + return Object.keys(this.services as object) + .reduce( + (current, path) => + current.then(() => { + const service: any = this.service(path as any); + + if (typeof service.teardown === "function") { + debug(`Tearing down service for \`${path}\``); + + return service.teardown(this, path); + } + }), + Promise.resolve() + ) + .then(() => this); + } + + get teardown() { + return this._teardown; + } + + set teardown(value) { + this._teardown = (value as any)[HOOKS] + ? value + : hooks( + value, + middleware().params("server").props({ + app: this, + }) + ); + } + + use( + path: L, + service: keyof any extends keyof Services + ? ServiceInterface | Application + : Services[L], + options?: ServiceOptions + ): this { + if (typeof path !== "string") { + throw new Error(`'${path}' is not a valid service path.`); + } + + const location = (stripSlashes(path) || "/") as L; + const subApp = service as Application; + const isSubApp = typeof subApp.service === "function" && subApp.services; + + if (isSubApp) { + Object.keys(subApp.services).forEach((subPath) => + this.use( + `${location}/${subPath}` as any, + subApp.service(subPath) as any + ) + ); + + return this; + } + + const protoService = wrapService(location, service, options); + const serviceOptions = getServiceOptions(protoService); + + for (const name of protectedMethods) { + if (serviceOptions.methods?.includes(name)) { + throw new Error( + `'${name}' on service '${location}' is not allowed as a custom method name` + ); + } + } + + debug(`Registering new service at \`${location}\``); + + // Add all the mixins + this.mixins.forEach((fn) => + fn.call(this, protoService, location, serviceOptions) + ); + + this.services[location] = protoService; + + // If we ran setup already, set this service up explicitly, this will not `await` + if (this._isSetup && typeof protoService.setup === "function") { + debug(`Setting up service for \`${location}\``); + protoService.setup(this, location); + } + + return this; + } + + async unuse( + location: L + ): Promise< + FeathersService< + this, + keyof any extends keyof Services ? Service : Services[L] + > + > { + const path = (stripSlashes(location) || "/") as L; + const service = this.services[path] as Service; + + if (service && typeof service.teardown === "function") { + await service.teardown(this as any, path); + } + + delete this.services[path]; + + return service as any; + } + + hooks(hookMap: ApplicationHookOptions) { + const untypedMap = hookMap as any; + + if ( + untypedMap.before || + untypedMap.after || + untypedMap.error || + untypedMap.around + ) { + // regular hooks for all service methods + this.registerHooks(untypedMap); + } else if (untypedMap.setup || untypedMap.teardown) { + // .setup and .teardown application hooks + hooks(this, untypedMap); + } else { + // Other registration formats are just `around` hooks + this.registerHooks({ + around: untypedMap, + }); + } + + return this; + } +} diff --git a/main/feathers/src/declarations.ts b/main/feathers/src/declarations.ts new file mode 100644 index 0000000000..ec9b062c5d --- /dev/null +++ b/main/feathers/src/declarations.ts @@ -0,0 +1,499 @@ +import { EventEmitter } from "../../commons/mod.ts"; +import { + NextFunction, + HookContext as BaseHookContext, +} from "https://deno.land/x/hooks@v0.7.5/src/index.ts"; + +type SelfOrArray = S | S[]; +type OptionalPick = Pick>; + +export type { NextFunction }; + +/** + * The object returned from `.find` call by standard database adapters + */ +export interface Paginated { + total: number; + limit: number; + skip: number; + data: T[]; +} + +/** + * Options that can be passed when registering a service via `app.use(name, service, options)` + */ +export interface ServiceOptions { + events?: string[] | readonly string[]; + methods?: string[] | readonly string[]; + serviceEvents?: string[] | readonly string[]; + routeParams?: { [key: string]: any }; +} + +export interface ClientService< + Result = any, + Data = Partial, + PatchData = Data, + FindResult = Paginated, + P = Params +> { + find(params?: P): Promise; + + get(id: Id, params?: P): Promise; + + create(data: Data[], params?: P): Promise; + create(data: Data, params?: P): Promise; + + update(id: Id, data: Data, params?: P): Promise; + update(id: NullableId, data: Data, params?: P): Promise; + update(id: null, data: Data, params?: P): Promise; + + patch( + id: NullableId, + data: PatchData, + params?: P + ): Promise; + patch(id: Id, data: PatchData, params?: P): Promise; + patch(id: null, data: PatchData, params?: P): Promise; + + remove(id: NullableId, params?: P): Promise; + remove(id: Id, params?: P): Promise; + remove(id: null, params?: P): Promise; +} + +export interface ServiceMethods, P = Params> { + find(params?: P): Promise; + + get(id: Id, params?: P): Promise; + + create(data: D, params?: P): Promise; + + update(id: NullableId, data: D, params?: P): Promise; + + patch(id: NullableId, data: D, params?: P): Promise; + + remove(id: NullableId, params?: P): Promise; + + setup?(app: Application, path: string): Promise; + + teardown?(app: Application, path: string): Promise; +} + +export interface ServiceOverloads, P = Params> { + create?(data: D[], params?: P): Promise; + + update?(id: Id, data: D, params?: P): Promise; + + update?(id: null, data: D, params?: P): Promise; + + patch?(id: Id, data: D, params?: P): Promise; + + patch?(id: null, data: D, params?: P): Promise; + + remove?(id: Id, params?: P): Promise; + + remove?(id: null, params?: P): Promise; +} + +export type Service, P = Params> = ServiceMethods< + T, + D, + P +> & + ServiceOverloads; + +export type ServiceInterface, P = Params> = Partial< + ServiceMethods +>; + +export interface ServiceAddons + extends EventEmitter { + id?: string; + hooks(options: HookOptions): this; +} + +export interface ServiceHookOverloads { + find(params: P, context: HookContext): Promise; + + get(id: Id, params: P, context: HookContext): Promise; + + create( + data: ServiceGenericData | ServiceGenericData[], + params: P, + context: HookContext + ): Promise; + + update( + id: NullableId, + data: ServiceGenericData, + params: P, + context: HookContext + ): Promise; + + patch( + id: NullableId, + data: ServiceGenericData, + params: P, + context: HookContext + ): Promise; + + remove(id: NullableId, params: P, context: HookContext): Promise; +} + +export type FeathersService = S & + ServiceAddons & + OptionalPick, keyof S>; + +export type CustomMethods = { + [K in keyof T]: (data: T[K][0], params?: Params) => Promise; +}; + +/** + * An interface usually use by transport clients that represents a e.g. HTTP or websocket + * connection that can be configured on the application. + */ +export type TransportConnection = { + (app: Application): void; + Service: any; + service: ( + name: L + ) => keyof any extends keyof Services ? ServiceInterface : Services[L]; +}; + +/** + * The interface for a custom service method. Can e.g. be used to type client side services. + */ +export type CustomMethod = ( + data: T, + params?: P +) => Promise; + +export type ServiceMixin = ( + service: FeathersService, + path: string, + options: ServiceOptions +) => void; + +export type ServiceGenericType = S extends ServiceInterface + ? T + : any; +export type ServiceGenericData = S extends ServiceInterface< + infer _T, + infer D +> + ? D + : any; +export type ServiceGenericParams = S extends ServiceInterface< + infer _T, + infer _D, + infer P +> + ? P + : any; + +export interface FeathersApplication { + /** + * The Feathers application version + */ + version: string; + + /** + * A list of callbacks that run when a new service is registered + */ + mixins: ServiceMixin>[]; + + /** + * The index of all services keyed by their path. + * + * __Important:__ Services should always be retrieved via `app.service('name')` + * not via `app.services`. + */ + services: Services; + + /** + * The application settings that can be used via + * `app.get` and `app.set` + */ + settings: Settings; + + /** + * A private-ish indicator if `app.setup()` has been called already + */ + _isSetup: boolean; + + /** + * Retrieve an application setting by name + * + * @param name The setting name + */ + get(name: L): Settings[L]; + + /** + * Set an application setting + * + * @param name The setting name + * @param value The setting value + */ + set(name: L, value: Settings[L]): this; + + /** + * Runs a callback configure function with the current application instance. + * + * @param callback The callback `(app: Application) => {}` to run + */ + configure(callback: (this: this, app: this) => void): this; + + /** + * Returns a fallback service instance that will be registered + * when no service was found. Usually throws a `NotFound` error + * but also used to instantiate client side services. + * + * @param location The path of the service + */ + defaultService(location: string): ServiceInterface; + + /** + * Register a new service or a sub-app. When passed another + * Feathers application, all its services will be re-registered + * with the `path` prefix. + * + * @param path The path for the service to register + * @param service The service object to register or another + * Feathers application to use a sub-app under the `path` prefix. + * @param options The options for this service + */ + use( + path: L, + service: keyof any extends keyof Services + ? ServiceInterface | Application + : Services[L], + options?: ServiceOptions + ): this; + + /** + * Unregister an existing service. + * + * @param path The name of the service to unregister + */ + unuse( + path: L + ): Promise< + FeathersService< + this, + keyof any extends keyof Services ? Service : Services[L] + > + >; + + /** + * Get the Feathers service instance for a path. This will + * be the service originally registered with Feathers functionality + * like hooks and events added. + * + * @param path The name of the service. + */ + service( + path: L + ): FeathersService< + this, + keyof any extends keyof Services ? Service : Services[L] + >; + + /** + * Set up the application and call all services `.setup` method if available. + * + * @param server A server instance (optional) + */ + setup(server?: any): Promise; + + /** + * Tear down the application and call all services `.teardown` method if available. + * + * @param server A server instance (optional) + */ + teardown(server?: any): Promise; + + /** + * Register application level hooks. + * + * @param map The application hook settings. + */ + hooks(map: ApplicationHookOptions): this; +} + +// This needs to be an interface instead of a type +// so that the declaration can be extended by other modules +export interface Application + extends FeathersApplication, + EventEmitter {} + +export type Id = number | string; +export type NullableId = Id | null; + +export interface Query { + [key: string]: any; +} + +export interface Params { + query?: Q; + provider?: string; + route?: { [key: string]: any }; + headers?: { [key: string]: any }; +} + +export interface Http { + /** + * A writeable, optional property with status code override. + */ + status?: number; + /** + * A writeable, optional property with headers. + */ + headers?: { [key: string]: string | string[] }; + /** + * A writeable, optional property with `Location` header's value. + */ + location?: string; +} + +export interface HookContext + extends BaseHookContext> { + /** + * A read only property that contains the Feathers application object. This can be used to + * retrieve other services (via context.app.service('name')) or configuration values. + */ + readonly app: A; + /** + * A read only property with the name of the service method (one of find, get, + * create, update, patch, remove). + */ + readonly method: string; + /** + * A read only property and contains the service name (or path) without leading or + * trailing slashes. + */ + readonly path: string; + /** + * A read only property and contains the service this hook currently runs on. + */ + readonly service: S; + /** + * A read only property with the hook type (one of before, after or error). + * Will be `null` for asynchronous hooks. + */ + readonly type: null | "before" | "after" | "error"; + /** + * The list of method arguments. Should not be modified, modify the + * `params`, `data` and `id` properties instead. + */ + readonly arguments: any[]; + /** + * A writeable property containing the data of a create, update and patch service + * method call. + */ + data?: ServiceGenericData; + /** + * A writeable property with the error object that was thrown in a failed method call. + * It is only available in error hooks. + */ + error?: any; + /** + * A writeable property and the id for a get, remove, update and patch service + * method call. For remove, update and patch context.id can also be null when + * modifying multiple entries. In all other cases it will be undefined. + */ + id?: Id; + /** + * A writeable property that contains the service method parameters (including + * params.query). + */ + params: ServiceGenericParams; + /** + * A writeable property containing the result of the successful service method call. + * It is only available in after hooks. + * + * `context.result` can also be set in + * + * - A before hook to skip the actual service method (database) call + * - An error hook to swallow the error and return a result instead + */ + result?: ServiceGenericType; + /** + * A writeable, optional property and contains a 'safe' version of the data that + * should be sent to any client. If context.dispatch has not been set context.result + * will be sent to the client instead. + */ + dispatch?: ServiceGenericType; + /** + * A writeable, optional property that allows to override the standard HTTP status + * code that should be returned. + * + * @deprecated Use `http.status` instead. + */ + statusCode?: number; + /** + * A writeable, optional property with options specific to HTTP transports. + */ + http?: Http; + /** + * The event emitted by this method. Can be set to `null` to skip event emitting. + */ + event: string | null; +} + +// Regular hook typings +export type HookFunction = ( + this: S, + context: HookContext +) => + | Promise | void> + | HookContext + | void; + +export type Hook = HookFunction; + +type HookMethodMap = { + [L in keyof S]?: SelfOrArray>; +} & { all?: SelfOrArray> }; + +type HookTypeMap = SelfOrArray> | HookMethodMap; + +// New @feathersjs/hook typings +export type AroundHookFunction = ( + context: HookContext, + next: NextFunction +) => Promise; + +export type AroundHookMap = { + [L in keyof S]?: AroundHookFunction[]; +} & { all?: AroundHookFunction[] }; + +export type HookMap = { + around?: AroundHookMap; + before?: HookTypeMap; + after?: HookTypeMap; + error?: HookTypeMap; +}; + +export type HookOptions = + | AroundHookMap + | AroundHookFunction[] + | HookMap; + +export interface ApplicationHookContext + extends BaseHookContext { + app: A; + server: any; +} + +export type ApplicationHookFunction = ( + context: ApplicationHookContext, + next: NextFunction +) => Promise; + +export type ApplicationHookMap = { + setup?: ApplicationHookFunction[]; + teardown?: ApplicationHookFunction[]; +}; + +export type ApplicationHookOptions = + | HookOptions + | ApplicationHookMap; diff --git a/main/feathers/src/events.ts b/main/feathers/src/events.ts new file mode 100644 index 0000000000..89743b894d --- /dev/null +++ b/main/feathers/src/events.ts @@ -0,0 +1,36 @@ +import { EventEmitter } from "../../commons/mod.ts"; +import { NextFunction } from "https://deno.land/x/hooks@v0.7.5/src/index.ts"; +import { HookContext, FeathersService } from "./declarations.ts"; +import { getServiceOptions, defaultEventMap } from "./service.ts"; + +export function eventHook(context: HookContext, next: NextFunction) { + const { events } = getServiceOptions((context as any).self); + const defaultEvent = (defaultEventMap as any)[context.method] || null; + + context.event = defaultEvent; + + return next().then(() => { + // Send the event only if the service does not do so already (indicated in the `events` option) + // This is used for custom events and for client services receiving event from the server + if (typeof context.event === "string" && !events?.includes(context.event)) { + const results = Array.isArray(context.result) + ? context.result + : [context.result]; + + results.forEach((element) => { + return (context as any).self.emit(context.event, element, context); + }); + } + }); +} + +export function eventMixin(service: FeathersService) { + const isEmitter = + typeof service.on === "function" && typeof service.emit === "function"; + + if (!isEmitter) { + Object.assign(service, EventEmitter.prototype); + } + + return service; +} diff --git a/main/feathers/src/hooks.ts b/main/feathers/src/hooks.ts new file mode 100644 index 0000000000..e8d61f21b6 --- /dev/null +++ b/main/feathers/src/hooks.ts @@ -0,0 +1,241 @@ +import { + getManager, + HookContextData, + HookManager, + HookMap as BaseHookMap, + hooks, + Middleware, + collect, +} from "https://deno.land/x/hooks@v0.7.5/src/index.ts"; +import { + Service, + ServiceOptions, + HookContext, + FeathersService, + HookMap, + AroundHookFunction, + HookFunction, +} from "./declarations.ts"; +import { defaultServiceArguments, getHookMethods } from "./service.ts"; + +type HookType = "before" | "after" | "error" | "around"; + +type ConvertedMap = { [type in HookType]: ReturnType }; + +type HookStore = { + around: { [method: string]: AroundHookFunction[] }; + before: { [method: string]: HookFunction[] }; + after: { [method: string]: HookFunction[] }; + error: { [method: string]: HookFunction[] }; + collected: { [method: string]: AroundHookFunction[] }; +}; + +type HookEnabled = { __hooks: HookStore }; + +const types: HookType[] = ["before", "after", "error", "around"]; + +const isType = (value: any): value is HookType => types.includes(value); + +// Converts different hook registration formats into the +// same internal format +export function convertHookData(input: any) { + const result: { [method: string]: HookFunction[] | AroundHookFunction[] } = + {}; + + if (Array.isArray(input)) { + result.all = input; + } else if (typeof input !== "object") { + result.all = [input]; + } else { + for (const key of Object.keys(input)) { + const value = input[key]; + result[key] = Array.isArray(value) ? value : [value]; + } + } + + return result; +} + +export function collectHooks(target: HookEnabled, method: string) { + const { collected, around } = target.__hooks; + + return [ + ...(around.all || []), + ...(around[method] || []), + ...(collected.all || []), + ...(collected[method] || []), + ] as AroundHookFunction[]; +} + +// Add `.hooks` functionality to an object +export function enableHooks(object: any) { + const store: HookStore = { + around: {}, + before: {}, + after: {}, + error: {}, + collected: {}, + }; + + Object.defineProperty(object, "__hooks", { + configurable: true, + value: store, + writable: true, + }); + + return function registerHooks(this: HookEnabled, input: HookMap) { + const store = this.__hooks; + const map = Object.keys(input).reduce((map, type) => { + if (!isType(type)) { + throw new Error(`'${type}' is not a valid hook type`); + } + + map[type] = convertHookData(input[type]); + + return map; + }, {} as ConvertedMap); + const types = Object.keys(map) as HookType[]; + + types.forEach((type) => + Object.keys(map[type]).forEach((method) => { + const mapHooks = map[type][method]; + const storeHooks: any[] = (store[type][method] ||= []); + + storeHooks.push(...mapHooks); + + if ( + store.before[method] || + store.after[method] || + store.error[method] + ) { + const collected = collect({ + before: store.before[method] || [], + after: store.after[method] || [], + error: store.error[method] || [], + }); + + store.collected[method] = [collected]; + } + }) + ); + + return this; + }; +} + +export function createContext( + service: Service, + method: string, + data: HookContextData = {} +) { + const createContext = (service as any)[method].createContext; + + if (typeof createContext !== "function") { + throw new Error(`Can not create context for method ${method}`); + } + + return createContext(data) as HookContext; +} + +export class FeathersHookManager extends HookManager { + constructor(public app: A, public method: string) { + super(); + this._middleware = []; + } + + collectMiddleware(self: any, args: any[]): Middleware[] { + const appHooks = collectHooks(this.app as any as HookEnabled, this.method); + const middleware = super.collectMiddleware(self, args); + const methodHooks = collectHooks(self, this.method); + + return [...appHooks, ...middleware, ...methodHooks]; + } + + initializeContext(self: any, args: any[], context: HookContext) { + const ctx = super.initializeContext(self, args, context); + + ctx.params = ctx.params || {}; + + return ctx; + } + + middleware(mw: Middleware[]) { + this._middleware!.push(...mw); + return this; + } +} + +export function hookMixin( + this: A, + service: FeathersService, + path: string, + options: ServiceOptions +) { + if (typeof service.hooks === "function") { + return service; + } + + const hookMethods = getHookMethods(service, options); + + const serviceMethodHooks = hookMethods.reduce((res, method) => { + const params = (defaultServiceArguments as any)[method] || [ + "data", + "params", + ]; + + res[method] = new FeathersHookManager(this, method) + .params(...params) + .props({ + app: this, + path, + method, + service, + event: null, + type: null, + get statusCode() { + return this.http?.status; + }, + set statusCode(value: number) { + this.http = this.http || {}; + this.http.status = value; + }, + }); + + return res; + }, {} as BaseHookMap); + + const registerHooks = enableHooks(service); + + hooks(service, serviceMethodHooks); + + service.hooks = function (this: any, hookOptions: any) { + if ( + hookOptions.before || + hookOptions.after || + hookOptions.error || + hookOptions.around + ) { + return registerHooks.call(this, hookOptions); + } + + if (Array.isArray(hookOptions)) { + return hooks(this, hookOptions); + } + + Object.keys(hookOptions).forEach((method) => { + const manager = getManager(this[method]); + + if (!(manager instanceof FeathersHookManager)) { + throw new Error( + `Method ${method} is not a Feathers hooks enabled service method` + ); + } + + manager.middleware(hookOptions[method]); + }); + + return this; + }; + + return service; +} diff --git a/main/feathers/src/index.ts b/main/feathers/src/index.ts new file mode 100644 index 0000000000..6297735366 --- /dev/null +++ b/main/feathers/src/index.ts @@ -0,0 +1,16 @@ +import { setDebug } from "../../commons/mod.ts"; + +import version from "./version.ts"; +import { Feathers } from "./application.ts"; +import { Application } from "./declarations.ts"; + +export function feathers() { + return new Feathers() as unknown as Application; +} + +feathers.setDebug = setDebug; + +export { version, Feathers }; +export * from "./hooks.ts"; +export * from "./declarations.ts"; +export * from "./service.ts"; diff --git a/main/feathers/src/service.ts b/main/feathers/src/service.ts new file mode 100644 index 0000000000..8ba266ff74 --- /dev/null +++ b/main/feathers/src/service.ts @@ -0,0 +1,105 @@ +import { EventEmitter } from "../../commons/mod.ts"; +import { createSymbol } from "../../commons/mod.ts"; +import { ServiceOptions } from "./declarations.ts"; + +export const SERVICE = createSymbol("@feathersjs/service"); + +export const defaultServiceArguments = { + find: ["params"], + get: ["id", "params"], + create: ["data", "params"], + update: ["id", "data", "params"], + patch: ["id", "data", "params"], + remove: ["id", "params"], +}; +export const defaultServiceMethods = [ + "find", + "get", + "create", + "update", + "patch", + "remove", +]; + +export const defaultEventMap = { + create: "created", + update: "updated", + patch: "patched", + remove: "removed", +}; + +export const protectedMethods = Object.keys(Object.prototype) + .concat(Object.keys(EventEmitter.prototype)) + .concat([ + "all", + "around", + "before", + "after", + "error", + "hooks", + "setup", + "teardown", + "publish", + ]); + +export function getHookMethods(service: any, options: ServiceOptions) { + const { methods } = options; + + return (defaultServiceMethods as any as string[]) + .filter((m) => typeof service[m] === "function" && !methods?.includes(m)) + .concat(methods || []); +} + +export function getServiceOptions( + service: any, + options: ServiceOptions = {} +): ServiceOptions { + const existingOptions = service[SERVICE]; + + if (existingOptions) { + return existingOptions; + } + + const { + methods = defaultServiceMethods.filter( + (method) => typeof service[method] === "function" + ) || [], + events = service.events || [], + } = options; + const { serviceEvents = Object.values(defaultEventMap).concat(events) } = + options; + + return { + ...options, + events, + methods, + serviceEvents, + }; +} + +export function wrapService( + location: string, + service: any, + options?: ServiceOptions +) { + // Do nothing if this is already an initialized + if (service[SERVICE]) { + return service; + } + + const protoService = Object.create(service); + const serviceOptions = getServiceOptions(service, options); + + if ( + Object.keys(serviceOptions.methods!).length === 0 && + typeof service.setup !== "function" + ) { + throw new Error(`Invalid service object passed for path \`${location}\``); + } + + Object.defineProperty(protoService, SERVICE, { + value: serviceOptions, + }); + + return protoService; +} diff --git a/main/feathers/src/version.ts b/main/feathers/src/version.ts new file mode 100644 index 0000000000..c08db0d7a7 --- /dev/null +++ b/main/feathers/src/version.ts @@ -0,0 +1 @@ +export default "development"; diff --git a/main/feathers/test/application.test.ts b/main/feathers/test/application.test.ts new file mode 100644 index 0000000000..d6e3f9f5c7 --- /dev/null +++ b/main/feathers/test/application.test.ts @@ -0,0 +1,537 @@ +// deno-lint-ignore-file require-await +/* eslint-disable @typescript-eslint/ban-ts-comment, @typescript-eslint/no-empty-function */ +import { + describe, + it, + assertStrictEquals, + assert, + assertInstanceOf, + assertThrows, + assertEquals, +} from "../../commons/mod.ts"; +import { feathers, Feathers, getServiceOptions, Id, version } from "../mod.ts"; + +describe("Feathers application", () => { + it("initializes", () => { + const app = feathers(); + + assertInstanceOf(app, Feathers); + }); + + it("sets the version on main and app instance", () => { + const app = feathers(); + + assert(version > "5.0.0"); + assert(app.version > "5.0.0"); + }); + + it("is an event emitter", async () => { + const app = feathers(); + const original = { hello: "world" }; + + app.on("test", (data: any) => { + assertStrictEquals(original, data); + }); + + app.emit("test", original); + }); + + it("uses .defaultService if available", async () => { + const app = feathers(); + + assertThrows(() => app.service("/todos/"), "Can not find service 'todos'"); + + app.defaultService = function (location: string) { + assertStrictEquals(location, "todos"); + return { + async get(id: string) { + return { + id, + description: `You have to do ${id}!`, + }; + }, + }; + }; + + const data = await app.service("/todos/").get("dishes"); + + assertEquals(data, { + id: "dishes", + description: "You have to do dishes!", + }); + }); + + it("additionally passes `app` as .configure parameter (#558)", () => { + feathers().configure(function (app) { + assertStrictEquals(this, app); + }); + }); + + describe("Services", () => { + it("calling .use with invalid path throws", () => { + const app = feathers(); + + assertThrows( + // @ts-ignore + () => app.use(null, {}), + "'null' is not a valid service path." + ); + + assertThrows( + // @ts-ignore + () => app.use({}, {}), + "'[object Object]' is not a valid service path." + ); + }); + + it("calling .use with a non service object throws", () => { + const app = feathers(); + + // @ts-ignore + assertThrows(() => app.use("/bla", function () {}), { + message: "Invalid service object passed for path `bla`", + }); + }); + + it("registers and wraps a new service and can unregister (#2035)", async () => { + const dummyService = { + async setup(this: any, _app: any, path: string) { + this.path = path; + }, + + async teardown(this: any, _app: any, path: string) { + this.path = path; + }, + + async create(data: any) { + return data; + }, + }; + + const app = feathers<{ dummy: typeof dummyService }>().use( + "dummy", + dummyService + ); + const wrappedService = app.service("dummy"); + + assertStrictEquals( + Object.getPrototypeOf(wrappedService), + dummyService, + "Object points to original service prototype" + ); + + const data = await wrappedService.create({ + message: "Test message", + }); + + assertStrictEquals(data.message, "Test message"); + + await app.unuse("dummy"); + + assertStrictEquals(Object.keys(app.services).length, 0); + assertThrows(() => app.service("dummy"), "Can not find service 'dummy'"); + }); + + it("can not register custom methods on a protected methods", async () => { + const dummyService = { + async create(data: any) { + return data; + }, + // deno-lint-ignore require-await + async removeListener(data: any) { + return data; + }, + async setup() {}, + + async teardown() {}, + }; + + assertThrows( + () => + feathers().use("/dummy", dummyService, { + methods: ["create", "removeListener"], + }), + "'removeListener' on service 'dummy' is not allowed as a custom method name" + ); + assertThrows( + () => + feathers().use("/dummy", dummyService, { + methods: ["create", "setup"], + }), + "'setup' on service 'dummy' is not allowed as a custom method name" + ); + assertThrows( + () => + feathers().use("/dummy", dummyService, { + methods: ["create", "teardown"], + }), + "'teardown' on service 'dummy' is not allowed as a custom method name" + ); + }); + + it("can use a root level service", async () => { + const app = feathers().use("/", { + // deno-lint-ignore require-await + async get(id: string) { + return { id }; + }, + }); + + const result = await app.service("/").get("test"); + + assertEquals(result, { id: "test" }); + }); + + it("services can be re-used (#566)", async () => { + const app1 = feathers(); + const app2 = feathers(); + + app2.use("/dummy", { + // deno-lint-ignore require-await + async create(data: any) { + return data; + }, + }); + + const dummy = app2.service("dummy"); + + dummy.hooks({ + before: { + create: [ + (hook) => { + hook.data = Object.assign(hook.data || {}, { fromHook: true }); + }, + ], + }, + }); + + dummy.on("created", (data: any) => { + assertEquals(data, { + message: "Hi", + fromHook: true, + }); + }); + + app1.use("/testing", app2.service("dummy")); + + await app1.service("testing").create({ message: "Hi" }); + }); + + it("async hooks run before regular hooks", async () => { + const app = feathers(); + + app.use("/dummy", { + async create(data: any) { + return data; + }, + }); + + const dummy = app.service("dummy"); + + dummy.hooks({ + before: { + create(ctx) { + ctx.data!.order.push("before"); + }, + }, + }); + + dummy.hooks([ + async (ctx: any, next: any) => { + ctx.data.order = ["async"]; + await next(); + }, + ]); + + const result = await dummy.create({ + message: "hi", + }); + + assertEquals(result, { + message: "hi", + order: ["async", "before"], + }); + }); + + it("services conserve Symbols", () => { + const TEST = Symbol("test"); + const dummyService = { + [TEST]: true, + + async setup(this: any, _app: any, path: string) { + this.path = path; + }, + + async create(data: any) { + return data; + }, + }; + + const app = feathers().use("/dummy", dummyService); + const wrappedService = app.service("dummy"); + + assert((wrappedService as any)[TEST]); + }); + + it("methods conserve Symbols", () => { + const TEST = Symbol("test"); + const dummyService = { + async setup(this: any, _app: any, path: string) { + this.path = path; + }, + + async create(data: any) { + return data; + }, + }; + + (dummyService.create as any)[TEST] = true; + + const app = feathers().use("/dummy", dummyService); + const wrappedService = app.service("dummy"); + + assert((wrappedService.create as any)[TEST]); + }); + }); + + describe("Express app options compatibility", function () { + describe(".set()", () => { + it("should set a value", () => { + const app = feathers(); + app.set("foo", "bar"); + assertStrictEquals(app.get("foo"), "bar"); + }); + + it("should return the app", () => { + const app = feathers(); + assertStrictEquals(app.set("foo", "bar"), app); + }); + + it("should return the app when undefined", () => { + const app = feathers(); + assertStrictEquals(app.set("foo", undefined), app); + }); + }); + + describe(".get()", () => { + it("should return undefined when unset", () => { + const app = feathers(); + assertStrictEquals(app.get("foo"), undefined); + }); + + it("should otherwise return the value", () => { + const app = feathers(); + app.set("foo", "bar"); + assertStrictEquals(app.get("foo"), "bar"); + }); + }); + }); + + describe(".setup and .teardown", () => { + it("app.setup and app.teardown calls .setup and .teardown on all services", async () => { + const app = feathers(); + let setupCount = 0; + let teardownCount = 0; + + app.use("/dummy", { + async setup(appRef: any, path: any) { + setupCount++; + assertStrictEquals(appRef, app); + assertStrictEquals(path, "dummy"); + }, + + async teardown(appRef: any, path: any) { + teardownCount++; + assertStrictEquals(appRef, app); + assertStrictEquals(path, "dummy"); + }, + }); + + app.use("/simple", { + get(id: string) { + return Promise.resolve({ id }); + }, + }); + + app.use("/dummy2", { + async setup(appRef: any, path: any) { + setupCount++; + assertStrictEquals(appRef, app); + assertStrictEquals(path, "dummy2"); + }, + + async teardown(appRef: any, path: any) { + teardownCount++; + assertStrictEquals(appRef, app); + assertStrictEquals(path, "dummy2"); + }, + }); + + await app.setup(); + + assert((app as any)._isSetup); + assertStrictEquals(setupCount, 2); + + await app.teardown(); + + assert(!(app as any)._isSetup); + assertStrictEquals(teardownCount, 2); + }); + + it("registering app.setup but while still pending will be set up", () => { + const app = feathers(); + + app.setup(); + + app.use("/dummy", { + async setup(appRef: any, path: any) { + assert((app as any)._isSetup); + assertStrictEquals(appRef, app); + assertStrictEquals(path, "dummy"); + }, + }); + }); + }); + + describe(".teardown", () => { + it("app.teardown calls .teardown on all services", async () => { + const app = feathers(); + let teardownCount = 0; + + app.use("/dummy", { + async setup() {}, + async teardown(appRef: any, path: any) { + teardownCount++; + assertStrictEquals(appRef, app); + assertStrictEquals(path, "dummy"); + }, + }); + + app.use("/simple", { + get(id: string) { + return Promise.resolve({ id }); + }, + }); + + app.use("/dummy2", { + async setup() {}, + async teardown(appRef: any, path: any) { + teardownCount++; + assertStrictEquals(appRef, app); + assertStrictEquals(path, "dummy2"); + }, + }); + + await app.setup(); + await app.teardown(); + + assertEquals((app as any)._isSetup, false); + assertStrictEquals(teardownCount, 2); + }); + }); + + describe("mixins", () => { + class Dummy { + dummy = true; + async get(id: Id) { + return { id }; + } + } + + it("are getting called with a service and default options", () => { + const app = feathers(); + let mixinRan = false; + + app.mixins.push(function (service: any, location: any, options: any) { + assert(service.dummy); + assertStrictEquals(location, "dummy"); + assertEquals(options, getServiceOptions(new Dummy())); + mixinRan = true; + }); + + app.use("/dummy", new Dummy()); + + assert(mixinRan); + + app.setup(); + }); + + it("are getting called with a service and service options", () => { + const app = feathers(); + const opts = { events: ["bla"] }; + + let mixinRan = false; + + app.mixins.push(function (service: any, location: any, options: any) { + assert(service.dummy); + assertStrictEquals(location, "dummy"); + assertEquals(options, getServiceOptions(new Dummy(), opts)); + mixinRan = true; + }); + + app.use("/dummy", new Dummy(), opts); + + assert(mixinRan); + + app.setup(); + }); + }); + + describe("sub apps", () => { + it("re-registers sub-app services with prefix", (done) => { + const app = feathers(); + const subApp = feathers(); + + subApp + .use("/service1", { + async get(id: string) { + return { + id, + name: "service1", + }; + }, + }) + .use("/service2", { + async get(id: string) { + return { + id, + name: "service2", + }; + }, + + async create(data: any) { + return data; + }, + }); + + app.use("/api/", subApp); + + app.service("/api/service2").once("created", async (data: any) => { + assertEquals(data, { + message: "This is a test", + }); + + subApp.service("service2").once("created", (data: any) => { + assertEquals(data, { + message: "This is another test", + }); + }); + + await app.service("api/service2").create({ + message: "This is another test", + }); + }); + (async () => { + let data = await app.service("/api/service1").get(10); + assertStrictEquals(data.name, "service1"); + + data = await app.service("/api/service2").get(1); + assertStrictEquals(data.name, "service2"); + + await subApp.service("service2").create({ + message: "This is a test", + }); + })(); + }); + }); +}); diff --git a/main/feathers/test/declarations.test.ts b/main/feathers/test/declarations.test.ts new file mode 100644 index 0000000000..3b6f083fc0 --- /dev/null +++ b/main/feathers/test/declarations.test.ts @@ -0,0 +1,118 @@ +// deno-lint-ignore-file require-await +import { assert, describe, it } from "../../commons/mod.ts"; +import { hooks } from "https://deno.land/x/hooks@v0.7.5/src/index.ts"; +import { + feathers, + ServiceInterface, + Application, + HookContext, + NextFunction, +} from "../mod.ts"; + +interface Todo { + id: number; + message: string; + completed: boolean; +} + +interface TodoData { + message: string; + completed?: boolean; +} + +class TodoService implements ServiceInterface { + constructor(public todos: Todo[] = []) {} + + async find() { + return this.todos; + } + + async create(data: TodoData) { + const { completed = false } = data; + const todo: Todo = { + id: this.todos.length, + completed, + message: data.message, + }; + + this.todos.push(todo); + + return todo; + } + + async setup(app: Application) { + assert(app); + } +} + +interface Configuration { + port: number; +} + +interface Services { + todos: TodoService; + v2: Application, Configuration>; +} + +type MainApp = Application; + +const myHook = async (context: HookContext, next: NextFunction) => { + assert(context.app.service("todos")); + await next(); +}; + +hooks(TodoService.prototype, [ + async (_ctx: HookContext, next) => { + await next(); + }, +]); + +hooks(TodoService, { + create: [myHook], +}); + +describe("Feathers typings", () => { + it("initializes the app with proper types", async () => { + const app: MainApp = feathers(); + const app2 = feathers, Configuration>(); + + app.set("port", 80); + app.use("todos", new TodoService()); + app.use("v2", app2); + + const service = app.service("todos"); + + service.on("created", (data: unknown) => { + assert(data); + }); + + service.hooks({ + before: { + all: [], + create: [ + async (context) => { + const { result, data } = context; + + assert(result); + assert(data); + assert(context.app.service("todos")); + }, + ], + }, + }); + + service.hooks({ + create: [ + async (context, next) => { + assert(context); + await next(); + }, + async (context, next) => { + assert(context); + await next(); + }, + myHook, + ], + }); + }); +}); diff --git a/main/feathers/test/events.test.ts b/main/feathers/test/events.test.ts new file mode 100644 index 0000000000..6a6ab0f551 --- /dev/null +++ b/main/feathers/test/events.test.ts @@ -0,0 +1,328 @@ +// deno-lint-ignore-file require-await +import { + describe, + it, + assertStrictEquals, + assertEquals, + unreachable, + assert, +} from "../../commons/mod.ts"; +import { EventEmitter } from "../../commons/mod.ts"; + +import { feathers } from "../mod.ts"; + +describe("Service events", () => { + it("app is an event emitter", () => { + const app = feathers(); + + assertStrictEquals(typeof app.on, "function"); + + app.on("test", (data: any) => { + assertEquals(data, { message: "app" }); + }); + + app.emit("test", { message: "app" }); + }); + + it("works with service that is already an EventEmitter", async () => { + const app = feathers(); + const service: any = new EventEmitter(); + + service.create = async function (data: any) { + return data; + }; + + service.on("created", (data: any) => { + assertEquals(data, { + message: "testing", + }); + }); + + app.use("/emitter", service); + + await app.service("emitter").create({ + message: "testing", + }); + }); + + describe("emits event data on a service", () => { + it(".create and created", async () => { + const app = feathers().use("/creator", { + async create(data: any) { + return data; + }, + }); + + const service = app.service("creator"); + + service.on("created", (data: any) => { + assertEquals(data, { message: "Hello" }); + }); + + await service.create({ message: "Hello" }); + }); + + it("allows to skip event emitting", async () => { + const app = feathers().use("/creator", { + async create(data: any) { + return data; + }, + }); + + const service = app.service("creator"); + + service.hooks({ + before: { + create(context: any) { + context.event = null; + + return context; + }, + }, + }); + + service.on("created", () => { + unreachable(); + }); + + await service.create({ message: "Hello" }); + }); + + it(".update and updated", async () => { + const app = feathers().use("/creator", { + async update(id: any, data: any) { + return Object.assign({ id }, data); + }, + }); + + const service = app.service("creator"); + + service.on("updated", (data: any) => { + assertEquals(data, { id: 10, message: "Hello" }); + }); + + await service.update(10, { message: "Hello" }); + }); + + it(".patch and patched", async () => { + const app = feathers().use("/creator", { + async patch(id: any, data: any) { + return Object.assign({ id }, data); + }, + }); + + const service = app.service("creator"); + + service.on("patched", (data: any) => { + assertEquals(data, { id: 12, message: "Hello" }); + }); + + await service.patch(12, { message: "Hello" }); + }); + + it(".remove and removed", async () => { + const app = feathers().use("/creator", { + async remove(id: any) { + return { id }; + }, + }); + + const service = app.service("creator"); + + service.on("removed", (data: any) => { + assertEquals(data, { id: 22 }); + }); + + await service.remove(22); + }); + }); + + describe("emits event data arrays on a service", () => { + it(".create and created with array", async () => { + const app = feathers().use("/creator", { + async create(data: any) { + if (Array.isArray(data)) { + return Promise.all( + data.map((current) => (this as any).create(current)) + ); + } + + return data; + }, + }); + + const service = app.service("creator"); + const createItems = [{ message: "Hello 0" }, { message: "Hello 1" }]; + + const events = Promise.all( + createItems.map((element, index) => { + return new Promise((resolve) => { + service.on("created", (data: any) => { + if (data.message === element.message) { + assertEquals(data, { message: `Hello ${index}` }); + resolve(); + } + }); + }); + }) + ); + + await service.create(createItems); + await events; + }); + + it(".update and updated with array", async () => { + const app = feathers().use("/creator", { + async update(id: any, data: any) { + if (Array.isArray(data)) { + return Promise.all( + data.map((current, index) => (this as any).update(index, current)) + ); + } + return Object.assign({ id }, data); + }, + }); + + const service = app.service("creator"); + const updateItems = [{ message: "Hello 0" }, { message: "Hello 1" }]; + + const events = Promise.all( + updateItems.map((element, index) => { + return new Promise((resolve) => { + service.on("updated", (data: any) => { + if (data.message === element.message) { + assertEquals(data, { + id: index, + message: `Hello ${index}`, + }); + resolve(); + } + }); + }); + }) + ); + + await service.update(null, updateItems); + await events; + }); + + it(".patch and patched with array", async () => { + const app = feathers().use("/creator", { + async patch(id: any, data: any) { + if (Array.isArray(data)) { + return Promise.all( + data.map((current, index) => (this as any).patch(index, current)) + ); + } + return Object.assign({ id }, data); + }, + }); + + const service = app.service("creator"); + const patchItems = [{ message: "Hello 0" }, { message: "Hello 1" }]; + + const events = Promise.all( + patchItems.map((element, index) => { + return new Promise((resolve) => { + service.on("patched", (data: any) => { + if (data.message === element.message) { + assertEquals(data, { + id: index, + message: `Hello ${index}`, + }); + resolve(); + } + }); + }); + }) + ); + + await service.patch(null, patchItems); + await events; + }); + + it(".remove and removed with array", async () => { + const removeItems = [{ message: "Hello 0" }, { message: "Hello 1" }]; + + const app = feathers().use("/creator", { + async remove(id: any, data: any) { + if (id === null) { + return Promise.all( + removeItems.map((current, index) => + (this as any).remove(index, current) + ) + ); + } + return Object.assign({ id }, data); + }, + }); + + const service = app.service("creator"); + + const events = Promise.all( + removeItems.map((element, index) => { + return new Promise((resolve) => { + service.on("removed", (data: any) => { + if (data.message === element.message) { + assertEquals(data, { + id: index, + message: `Hello ${index}`, + }); + resolve(); + } + }); + }); + }) + ); + + await service.remove(null); + await events; + }); + }); + + describe("event format", () => { + it("also emits the actual hook object", (done) => { + const app = feathers().use("/creator", { + async create(data: any) { + return data; + }, + }); + + const service = app.service("creator"); + + service.hooks({ + after(hook: any) { + hook.changed = true; + }, + }); + + service.on("created", (data: any, hook: any) => { + assertEquals(data, { message: "Hi" }); + assert(hook.changed); + assertStrictEquals(hook.service, service); + assertStrictEquals(hook.method, "create"); + assertStrictEquals(hook.type, null); + }); + + service.create({ message: "Hi" }); + }); + + it("events indicated by the service are not sent automatically", async () => { + class Creator { + events = ["created"]; + async create(data: any) { + return data; + } + } + const app = feathers().use("/creator", new Creator()); + const service = app.service("creator"); + + service.on("created", (data: any) => { + assertEquals(data, { message: "custom event" }); + }); + + await service.create({ message: "hello" }); + service.emit("created", { message: "custom event" }); + }); + }); +}); diff --git a/main/feathers/test/hooks/after.test.ts b/main/feathers/test/hooks/after.test.ts new file mode 100644 index 0000000000..74d4e9e651 --- /dev/null +++ b/main/feathers/test/hooks/after.test.ts @@ -0,0 +1,392 @@ +// deno-lint-ignore-file require-await +import { + describe, + it, + assertEquals, + assertRejects, + assertStrictEquals, + unreachable, + assert, +} from "../../../commons/mod.ts"; +import { feathers, Id } from "../../mod.ts"; + +describe("`after` hooks", () => { + it(".after hooks can return a promise", async () => { + const app = feathers().use("/dummy", { + async get(id: Id) { + return { + id, + description: `You have to do ${id}`, + }; + }, + + async find() { + return []; + }, + }); + const service = app.service("dummy"); + + service.hooks({ + after: { + async get(hook) { + hook.result.ran = true; + return hook; + }, + + async find() { + throw new Error("You can not see this"); + }, + }, + }); + + const data = await service.get("laundry", {}); + + assertEquals(data, { + id: "laundry", + description: "You have to do laundry", + ran: true, + }); + + await assertRejects(() => service.find({}), "You can not see this"); + }); + + it(".after hooks do not need to return anything", async () => { + const app = feathers().use("/dummy", { + async get(id: Id) { + return { + id, + description: `You have to do ${id}`, + }; + }, + + async find() { + return []; + }, + }); + const service = app.service("dummy"); + + service.hooks({ + after: { + get(context) { + context.result.ran = true; + }, + + find() { + throw new Error("You can not see this"); + }, + }, + }); + + const data = await service.get("laundry"); + + assertEquals(data, { + id: "laundry", + description: "You have to do laundry", + ran: true, + }); + + await assertRejects(() => service.find(), "You can not see this"); + }); + + it("gets mixed into a service and modifies data", async () => { + const dummyService = { + async create(data: any) { + return data; + }, + }; + + const app = feathers().use("/dummy", dummyService); + const service = app.service("dummy"); + + service.hooks({ + after: { + create(context) { + assertStrictEquals(context.type, "after"); + + context.result.some = "thing"; + + return context; + }, + }, + }); + + const data = await service.create({ my: "data" }); + + assertEquals({ my: "data", some: "thing" }, data, "Got modified data"); + }); + + it("also makes the app available at hook.app", async () => { + const dummyService = { + async create(data: any) { + return data; + }, + }; + + const app = feathers().use("/dummy", dummyService); + const service = app.service("dummy"); + + service.hooks({ + after: { + create(context) { + context.result.appPresent = typeof context.app !== "undefined"; + assertStrictEquals(context.result.appPresent, true); + + return context; + }, + }, + }); + + const data = await service.create({ my: "data" }); + + assertEquals( + { my: "data", appPresent: true }, + data, + "The app was present in the hook." + ); + }); + + it("returns errors", async () => { + const dummyService = { + async update(_id: any, data: any) { + return data; + }, + }; + + const app = feathers().use("/dummy", dummyService); + const service = app.service("dummy"); + + service.hooks({ + after: { + update() { + throw new Error("This did not work"); + }, + }, + }); + + await assertRejects( + () => service.update(1, { my: "data" }), + "This did not work" + ); + }); + + it("does not run after hook when there is an error", async () => { + const dummyService = { + async remove() { + throw new Error("Error removing item"); + }, + }; + + const app = feathers().use("/dummy", dummyService); + const service = app.service("dummy"); + + service.hooks({ + after: { + remove() { + unreachable(); + }, + }, + }); + + await assertRejects(() => service.remove(1, {}), "Error removing item"); + }); + + it("adds .after() and chains multiple hooks for the same method", async () => { + const dummyService = { + async create(data: any) { + return data; + }, + }; + + const app = feathers().use("/dummy", dummyService); + const service = app.service("dummy"); + + service.hooks({ + after: { + create(context) { + context.result.some = "thing"; + + return context; + }, + }, + }); + + service.hooks({ + after: { + create(context) { + context.result.other = "stuff"; + }, + }, + }); + + const data = await service.create({ my: "data" }); + + assertEquals( + { + my: "data", + some: "thing", + other: "stuff", + }, + data, + "Got modified data" + ); + }); + + it("chains multiple after hooks using array syntax", async () => { + const dummyService = { + async create(data: any) { + return data; + }, + }; + + const app = feathers().use("/dummy", dummyService); + const service = app.service("dummy"); + + service.hooks({ + after: { + create: [ + function (context) { + context.result.some = "thing"; + + return context; + }, + function (context) { + context.result.other = "stuff"; + + return context; + }, + ], + }, + }); + + const data = await service.create({ my: "data" }); + + assertEquals( + { + my: "data", + some: "thing", + other: "stuff", + }, + data, + "Got modified data" + ); + }); + + it(".after hooks run in the correct order (#13)", async () => { + const app = feathers().use("/dummy", { + async get(id: any) { + return { id }; + }, + }); + const service = app.service("dummy"); + + service.hooks({ + after: { + get(context) { + context.result.items = ["first"]; + + return context; + }, + }, + }); + + service.hooks({ + after: { + get: [ + function (context) { + context.result.items.push("second"); + + return context; + }, + function (context) { + context.result.items.push("third"); + + return context; + }, + ], + }, + }); + + const data = await service.get(10); + + assertEquals(data.items, ["first", "second", "third"]); + }); + + it("after all hooks (#11)", async () => { + const app = feathers().use("/dummy", { + async get(id: any) { + const items: any[] = []; + + return { id, items }; + }, + + async find() { + return []; + }, + }); + + const service = app.service("dummy"); + + service.hooks({ + after: { + all(context) { + context.result.afterAllObject = true; + + return context; + }, + }, + }); + + service.hooks({ + after: [ + function (context) { + context.result.afterAllMethodArray = true; + + return context; + }, + ], + }); + + let data = await service.find({}); + + assert(data.afterAllObject); + assert(data.afterAllMethodArray); + + data = await service.get(1, {}); + + assert(data.afterAllObject); + assert(data.afterAllMethodArray); + }); + + it("after hooks have service as context and keep it in service method (#17)", async () => { + class Dummy { + number = 42; + async get(id: any) { + return { + id, + number: this.number, + }; + } + } + const app = feathers().use("/dummy", new Dummy()); + + const service = app.service("dummy"); + + service.hooks({ + after: { + get(this: any, hook) { + hook.result.test = this.number + 1; + + return hook; + }, + }, + }); + + const data = await service.get(10); + + assertEquals(data, { + id: 10, + number: 42, + test: 43, + }); + }); +}); diff --git a/main/feathers/test/hooks/app.test.ts b/main/feathers/test/hooks/app.test.ts new file mode 100644 index 0000000000..402460da8f --- /dev/null +++ b/main/feathers/test/hooks/app.test.ts @@ -0,0 +1,349 @@ +// deno-lint-ignore-file require-await +import { + describe, + it, + beforeEach, + assertStrictEquals, + assertEquals, + assertObjectMatch, + assertRejects, +} from "../../../commons/mod.ts"; + +import { + feathers, + Application, + ApplicationHookMap, + ServiceInterface, + Params, +} from "../../mod.ts"; + +type Todo = { + id?: string; + params?: TodoParams; + data?: any; + test?: string; + order?: string[]; +}; + +interface TodoParams extends Params { + order: string[]; + ran: boolean; +} + +type TodoService = ServiceInterface & { + customMethod(data: any, params?: TodoParams): Promise; +}; + +type App = Application<{ todos: TodoService }>; + +describe("app.hooks", () => { + let app: App; + + beforeEach(() => { + app = feathers<{ todos: TodoService }>().use( + "todos", + { + async get(id: any, params: any) { + if (id === "error") { + throw new Error("Something went wrong"); + } + + return { id, params }; + }, + + async create(data: any, params: any) { + return { data, params }; + }, + + async customMethod(data: any, params: TodoParams) { + return { data, params }; + }, + }, + { + methods: ["get", "create", "customMethod"], + } + ); + }); + + it("app has the .hooks method", () => { + assertStrictEquals(typeof app.hooks, "function"); + }); + + it(".setup and .teardown special hooks", async () => { + const app = feathers(); + + // Test that setup and teardown can be overwritten + const oldSetup = app.setup; + app.setup = function (arg: any) { + return oldSetup.call(this, arg); + }; + const oldTeardown = app.teardown; + app.teardown = function (arg: any) { + return oldTeardown.call(this, arg); + }; + + const order: string[] = []; + const hooks: ApplicationHookMap = { + setup: [ + async (context, next) => { + assertStrictEquals(context.app, app); + order.push("setup 1"); + await next(); + }, + async (_context, next) => { + order.push("setup 2"); + await next(); + order.push("setup after"); + }, + ], + teardown: [ + async (context, next) => { + assertStrictEquals(context.app, app); + order.push("teardown 1"); + await next(); + }, + async (_context, next) => { + order.push("teardown 2"); + await next(); + }, + ], + }; + + app.hooks(hooks); + + await app.setup(); + await app.teardown(); + + assertEquals(order, [ + "setup 1", + "setup 2", + "setup after", + "teardown 1", + "teardown 2", + ]); + }); + + describe("app.hooks([ async ])", () => { + it("basic app async hook, works with custom method", async () => { + const service = app.service("todos"); + + app.hooks([ + async (context, next) => { + assertStrictEquals(context.app, app); + await next(); + context.params.ran = true; + }, + ]); + + let result = await service.get("test"); + + assertObjectMatch(result, { + id: "test", + params: { ran: true }, + }); + + const data = { test: "hi" }; + + result = await service.create(data); + + assertObjectMatch(result, { + data, + params: { ran: true }, + }); + + result = await service.customMethod("custom test"); + + assertObjectMatch(result, { + data: "custom test", + params: { ran: true }, + }); + }); + }); + + describe("app.hooks({ method: [ async ] })", () => { + it("basic app async method hook", async () => { + const service = app.service("todos"); + + app.hooks({ + get: [ + async (context, next) => { + assertStrictEquals(context.app, app); + await next(); + context.params.ran = true; + }, + ], + }); + + const result = await service.get("test"); + + assertObjectMatch(result, { + id: "test", + params: { ran: true }, + }); + }); + }); + + describe("app.hooks({ before })", () => { + it("basic app before hook, works with custom method", async () => { + const service = app.service("todos"); + + app.hooks({ + before(context) { + assertStrictEquals(context.app, app); + context.params.ran = true; + }, + }); + + let result = await service.get("test"); + + assertObjectMatch(result, { + id: "test", + params: { ran: true }, + }); + + const data = { test: "hi" }; + + result = await service.create(data); + + assertObjectMatch(result, { + data, + params: { ran: true }, + }); + + result = await service.customMethod("custom with before"); + + assertObjectMatch(result, { + data: "custom with before", + params: { ran: true }, + }); + }); + + it("app before hooks always run first", async () => { + app.service("todos").hooks({ + before(context) { + assertStrictEquals(context.app, app); + context.params.order.push("service.before"); + }, + }); + + app.service("todos").hooks({ + before(context) { + assertStrictEquals(context.app, app); + context.params.order.push("service.before 1"); + }, + }); + + app.hooks({ + before(context) { + assertStrictEquals(context.app, app); + context.params.order = []; + context.params.order.push("app.before"); + }, + }); + + const result = await app.service("todos").get("test"); + + assertObjectMatch(result, { + id: "test", + params: { + order: ["app.before", "service.before", "service.before 1"], + }, + }); + }); + }); + + describe("app.hooks({ after })", () => { + it("basic app after hook", async () => { + app.hooks({ + after(context) { + assertStrictEquals(context.app, app); + context.result.ran = true; + }, + }); + + const result = await app.service("todos").get("test"); + + assertObjectMatch(result, { + id: "test", + params: {}, + ran: true, + }); + }); + + it("app after hooks always run last", async () => { + app.hooks({ + after(context) { + assertStrictEquals(context.app, app); + context.result.order.push("app.after"); + }, + }); + + app.service("todos").hooks({ + after(context) { + assertStrictEquals(context.app, app); + context.result!.order = []; + context.result!.order.push("service.after"); + }, + }); + + app.service("todos").hooks({ + after(context) { + assertStrictEquals(context.app, app); + context.result!.order!.push("service.after 1"); + }, + }); + + const result = await app.service("todos").get("test"); + + assertObjectMatch(result, { + id: "test", + params: {}, + order: ["service.after", "service.after 1", "app.after"], + }); + }); + }); + + describe("app.hooks({ error })", () => { + it("basic app error hook", async () => { + app.hooks({ + error(context) { + assertStrictEquals(context.app, app); + context.error = new Error("App hook ran"); + }, + }); + + await assertRejects( + () => app.service("todos").get("error"), + "App hook ran" + ); + }); + + it("app error hooks always run last", async () => { + app.hooks({ + error(context) { + assertStrictEquals(context.app, app); + context.error = new Error(`${context.error.message} app.after`); + }, + }); + + app.service("todos").hooks({ + error(context) { + assertStrictEquals(context.app, app); + context.error = new Error(`${context.error.message} service.after`); + }, + }); + + app.service("todos").hooks({ + error(context) { + assertStrictEquals(context.app, app); + context.error = new Error(`${context.error.message} service.after 1`); + }, + }); + + await assertRejects( + () => app.service("todos").get("error"), + "Something went wrong service.after service.after 1 app.after" + ); + }); + }); +}); diff --git a/main/feathers/test/hooks/around.test.ts b/main/feathers/test/hooks/around.test.ts new file mode 100644 index 0000000000..8b8046e236 --- /dev/null +++ b/main/feathers/test/hooks/around.test.ts @@ -0,0 +1,411 @@ +// deno-lint-ignore-file require-await +import { + describe, + it, + assertStrictEquals, + assertEquals, + assertRejects, + unreachable, + assert, +} from "../../../commons/mod.ts"; +import { feathers, Params, ServiceInterface } from "../../mod.ts"; + +describe("`around` hooks", () => { + it("around hooks can set hook.result which will skip service method", async () => { + const app = feathers().use("/dummy", { + async get() { + unreachable(); + }, + }); + const service = app.service("dummy"); + + service.hooks({ + get: [ + async (hook, next) => { + hook.result = { + id: hook.id, + message: "Set from hook", + }; + + await next(); + }, + ], + }); + + const data = await service.get(10, {}); + + assertEquals(data, { + id: 10, + message: "Set from hook", + }); + }); + + it("works with traditional registration format, all syntax and app hooks", async () => { + const app = feathers().use("/dummy", { + async get() { + unreachable(); + }, + }); + const service = app.service("dummy"); + + app.hooks([ + async function (this: any, hook, next) { + hook.result = { + id: hook.id, + app: "Set from app around all", + }; + + await next(); + }, + ]); + + service.hooks({ + around: { + all: [ + async (hook, next) => { + hook.result = { + ...hook.result, + all: "Set from around all", + }; + + await next(); + }, + ], + get: [ + async (hook, next) => { + hook.result = { + ...hook.result, + get: "Set from around get", + }; + + await next(); + }, + ], + }, + }); + + const data = await service.get(10, {}); + + assertEquals(data, { + id: 10, + app: "Set from app around all", + all: "Set from around all", + get: "Set from around get", + }); + }); + + it("gets mixed into a service and modifies data", async () => { + const dummyService = { + async create(data: any, params: any) { + assertEquals( + data, + { + some: "thing", + modified: "data", + }, + "Data modified" + ); + + assertEquals( + params, + { + modified: "params", + }, + "Params modified" + ); + + return data; + }, + }; + const app = feathers().use("/dummy", dummyService); + const service = app.service("dummy"); + + service.hooks({ + create: [ + async (hook, next) => { + assertStrictEquals(hook.type, null); + + hook.data!.modified = "data"; + + Object.assign(hook.params, { + modified: "params", + }); + + await next(); + }, + ], + }); + + const data = await service.create({ some: "thing" }); + + assertEquals( + data, + { + some: "thing", + modified: "data", + }, + "Data got modified" + ); + }); + + it("contains the app object at hook.app", async () => { + const someServiceConfig = { + async create(data: any) { + return data; + }, + }; + const app = feathers().use("/some-service", someServiceConfig); + const someService = app.service("some-service"); + + someService.hooks({ + create: [ + async (hook, next) => { + hook.data!.appPresent = typeof hook.app !== "undefined"; + assertStrictEquals(hook.data!.appPresent, true); + return next(); + }, + ], + }); + + const data = await someService.create({ some: "thing" }); + + assertEquals( + data, + { + some: "thing", + appPresent: true, + }, + "App object was present" + ); + }); + + it("passes errors", async () => { + const dummyService = { + update() { + unreachable(); + }, + }; + const app = feathers().use("/dummy", dummyService); + const service = app.service("dummy"); + + service.hooks({ + update: [ + async () => { + throw new Error("You are not allowed to update"); + }, + ], + }); + + await assertRejects( + () => service.update(1, {}), + "You are not allowed to update" + ); + }); + + it("does not run after hook when there is an error", async () => { + const dummyService = { + async remove() { + throw new Error("Error removing item"); + }, + }; + const app = feathers().use("/dummy", dummyService); + const service = app.service("dummy"); + + service.hooks({ + remove: [ + async (_context, next) => { + await next(); + + unreachable(); + }, + ], + }); + + await assertRejects(() => service.remove(1, {}), "Error removing item"); + }); + + it("adds .hooks() and chains multiple hooks for the same method", async () => { + interface DummyParams extends Params { + modified: string; + } + + class DummyService implements ServiceInterface { + create(data: any, params?: any) { + assertEquals( + data, + { + some: "thing", + modified: "second data", + }, + "Data modified" + ); + + assertEquals( + params, + { + modified: "params", + }, + "Params modified" + ); + + return Promise.resolve(data); + } + } + + const app = feathers<{ dummy: DummyService }>().use( + "dummy", + new DummyService() + ); + const service = app.service("dummy"); + + service.hooks({ + create: [ + async (hook, next) => { + hook.params.modified = "params"; + + await next(); + }, + async (hook, next) => { + hook.data.modified = "second data"; + + next(); + }, + ], + }); + + await service.create({ some: "thing" }); + }); + + it("around hooks run in the correct order", async () => { + interface DummyParams extends Params<{ name: string }> { + items: string[]; + } + + class DummyService implements ServiceInterface { + async get(id: any, params?: DummyParams) { + assertEquals(params!.items, ["first", "second", "third"]); + + return { + id, + items: [] as string[], + }; + } + } + + const app = feathers<{ dummy: DummyService }>().use( + "dummy", + new DummyService() + ); + const service = app.service("dummy"); + + service.hooks({ + get: [ + async (hook, next) => { + hook.params.items = ["first"]; + await next(); + }, + ], + }); + + service.hooks({ + get: [ + async function (hook, next) { + hook.params.items.push("second"); + next(); + }, + async function (hook, next) { + hook.params.items.push("third"); + next(); + }, + ], + }); + + await service.get(10); + }); + + it("around all hooks (#11)", async () => { + interface DummyParams extends Params { + asyncAllObject: boolean; + asyncAllMethodArray: boolean; + } + + type DummyService = ServiceInterface; + + const app = feathers<{ dummy: DummyService }>().use("dummy", { + async get(id: any, params: any) { + assert(params.asyncAllObject); + assert(params.asyncAllMethodArray); + + return { + id, + items: [], + }; + }, + + async find(params: any) { + assert(params.asyncAllObject); + assert(params.asyncAllMethodArray); + + return []; + }, + }); + + const service = app.service("dummy"); + + service.hooks([ + async (hook, next) => { + hook.params.asyncAllObject = true; + next(); + }, + ]); + + service.hooks([ + async function (hook, next) { + hook.params.asyncAllMethodArray = true; + next(); + }, + ]); + + await service.find(); + }); + + it("around hooks have service as context and keep it in service method (#17)", async () => { + interface DummyParams extends Params { + test: number; + } + + class Dummy implements ServiceInterface { + number = 42; + + async get(id: any, params?: DummyParams) { + return { + id, + number: (this as any).number, + test: params?.test, + }; + } + } + + const app = feathers<{ dummy: Dummy }>().use("dummy", new Dummy()); + + const service = app.service("dummy"); + + service.hooks({ + get: [ + async function (this: any, hook, next) { + hook.params.test = this.number + 2; + + await next(); + }, + ], + }); + + const data = await service.get(10); + + assertEquals(data, { + id: 10, + number: 42, + test: 44, + }); + }); +}); diff --git a/main/feathers/test/hooks/before.test.ts b/main/feathers/test/hooks/before.test.ts new file mode 100644 index 0000000000..0196769528 --- /dev/null +++ b/main/feathers/test/hooks/before.test.ts @@ -0,0 +1,512 @@ +// deno-lint-ignore-file require-await +import { + describe, + it, + assertEquals, + assertRejects, + assertStrictEquals, + unreachable, + assert, +} from "../../../commons/mod.ts"; +import { feathers, Params, ServiceInterface } from "../../mod.ts"; + +describe("`before` hooks", () => { + it(".before hooks can return a promise", async () => { + interface DummyParams extends Params { + ran: boolean; + } + + type DummyService = ServiceInterface; + + const app = feathers<{ dummy: DummyService }>().use("dummy", { + async get(id: any, params: DummyParams) { + assert(params.ran, "Ran through promise hook"); + + return { + id, + description: `You have to do ${id}`, + }; + }, + + async remove() { + unreachable(); + }, + }); + const service = app.service("dummy"); + + service.hooks({ + before: { + get(context) { + return new Promise((resolve) => { + context.params.ran = true; + resolve(); + }); + }, + + remove() { + return new Promise((_resolve, reject) => { + reject(new Error("This did not work")); + }); + }, + + find: [], + }, + }); + + await service.get("dishes"); + await assertRejects(() => service.remove(10), "This did not work"); + }); + + it(".before hooks do not need to return anything", async () => { + interface DummyParams extends Params { + ran: boolean; + } + + type DummyService = ServiceInterface; + + const app = feathers<{ dummy: DummyService }>().use("dummy", { + async get(id: any, params: any) { + assert(params.ran, "Ran through promise hook"); + + return { + id, + description: `You have to do ${id}`, + }; + }, + + async remove() { + unreachable(); + }, + }); + const service = app.service("dummy"); + + service.hooks({ + before: { + get(context) { + context.params.ran = true; + }, + + remove() { + throw new Error("This did not work"); + }, + }, + }); + + await service.get("dishes"); + await assertRejects(() => service.remove(10), "This did not work"); + }); + + it(".before hooks can set context.result which will skip service method", async () => { + const app = feathers().use("/dummy", { + async get() { + unreachable(); + }, + }); + const service = app.service("dummy"); + + service.hooks({ + before: { + get(context) { + context.result = { + id: context.id, + message: "Set from hook", + }; + }, + }, + }); + + const data = await service.get(10, {}); + + assertEquals(data, { + id: 10, + message: "Set from hook", + }); + }); + + it("gets mixed into a service and modifies data", async () => { + const dummyService = { + async create(data: any, params: any) { + assertEquals( + data, + { + some: "thing", + modified: "data", + }, + "Data modified" + ); + + assertEquals( + params, + { + modified: "params", + }, + "Params modified" + ); + + return data; + }, + }; + const app = feathers().use("/dummy", dummyService); + const service = app.service("dummy"); + + service.hooks({ + before: { + create(context) { + assertStrictEquals(context.type, "before"); + + context.data!.modified = "data"; + + Object.assign(context.params, { + modified: "params", + }); + + return context; + }, + }, + }); + + const data = await service.create({ some: "thing" }); + + assertEquals( + data, + { + some: "thing", + modified: "data", + }, + "Data got modified" + ); + }); + + it("contains the app object at context.app", async () => { + const someServiceConfig = { + async create(data: any) { + return data; + }, + }; + const app = feathers().use("/some-service", someServiceConfig); + const someService = app.service("some-service"); + + someService.hooks({ + before: { + create(context) { + context.data!.appPresent = typeof context.app !== "undefined"; + assertStrictEquals(context.data!.appPresent, true); + + return context; + }, + }, + }); + + const data = await someService.create({ some: "thing" }); + + assertEquals( + data, + { + some: "thing", + appPresent: true, + }, + "App object was present" + ); + }); + + it("passes errors", async () => { + const dummyService = { + update() { + unreachable(); + }, + }; + + const app = feathers().use("/dummy", dummyService); + const service = app.service("dummy"); + + service.hooks({ + before: { + update() { + throw new Error("You are not allowed to update"); + }, + }, + }); + + await assertRejects( + () => service.update(1, {}), + "You are not allowed to update" + ); + }); + + it("calling back with no arguments uses the old ones", async () => { + interface DummyParams extends Params { + my: string; + } + + type DummyService = ServiceInterface; + + const dummyService = { + async remove(id: any, params: any) { + assertStrictEquals(id, 1, "Got id"); + assertEquals(params, { my: "param" }); + + return { id }; + }, + }; + const app = feathers<{ dummy: DummyService }>().use("dummy", dummyService); + const service = app.service("dummy"); + + service.hooks({ + before: { + remove(context) { + return context; + }, + }, + }); + + await service.remove(1, { my: "param" }); + }); + + it("adds .hooks() and chains multiple hooks for the same method", async () => { + interface DummyParams extends Params { + modified: string; + } + + type DummyService = ServiceInterface; + + const dummyService = { + async create(data: any, params: any) { + assertEquals( + data, + { + some: "thing", + modified: "second data", + }, + "Data modified" + ); + + assertEquals( + params, + { + modified: "params", + }, + "Params modified" + ); + + return data; + }, + }; + const app = feathers<{ dummy: DummyService }>().use("dummy", dummyService); + const service = app.service("dummy"); + + service.hooks({ + before: { + create(context) { + context.params.modified = "params"; + + return context; + }, + }, + }); + + service.hooks({ + before: { + create(context) { + context.data.modified = "second data"; + + return context; + }, + }, + }); + + await service.create({ some: "thing" }); + }); + + it("chains multiple before hooks using array syntax", async () => { + interface DummyParams extends Params { + modified: string; + } + + type DummyService = ServiceInterface; + + const dummyService = { + async create(data: any, params: any) { + assertEquals( + data, + { + some: "thing", + modified: "second data", + }, + "Data modified" + ); + + assertEquals( + params, + { + modified: "params", + }, + "Params modified" + ); + + return data; + }, + }; + + const app = feathers<{ dummy: DummyService }>().use("dummy", dummyService); + const service = app.service("dummy"); + + service.hooks({ + before: { + create: [ + function (context) { + context.params.modified = "params"; + + return context; + }, + function (context) { + context.data.modified = "second data"; + + return context; + }, + ], + }, + }); + + await service.create({ some: "thing" }); + }); + + it(".before hooks run in the correct order (#13)", async () => { + interface DummyParams extends Params { + items: string[]; + } + + type DummyService = ServiceInterface; + + const app = feathers<{ dummy: DummyService }>().use("dummy", { + async get(id: any, params: any) { + assertEquals(params.items, ["first", "second", "third"]); + + return { + id, + items: [], + }; + }, + }); + const service = app.service("dummy"); + + service.hooks({ + before: { + get(context) { + context.params.items = ["first"]; + + return context; + }, + }, + }); + + service.hooks({ + before: { + get: [ + function (context) { + context.params.items.push("second"); + + return context; + }, + function (context) { + context.params.items.push("third"); + + return context; + }, + ], + }, + }); + + await service.get(10); + }); + + it("before all hooks (#11)", async () => { + interface DummyParams extends Params { + beforeAllObject: boolean; + beforeAllMethodArray: boolean; + } + + type DummyService = ServiceInterface; + + const app = feathers<{ dummy: DummyService }>().use("dummy", { + async get(id: any, params: any) { + assert(params.beforeAllObject); + assert(params.beforeAllMethodArray); + + return { + id, + items: [], + }; + }, + + async find(params: any) { + assert(params.beforeAllObject); + assert(params.beforeAllMethodArray); + + return []; + }, + }); + + const service = app.service("dummy"); + + service.hooks({ + before: { + all(context) { + context.params.beforeAllObject = true; + + return context; + }, + }, + }); + + service.hooks({ + before: [ + function (context) { + context.params.beforeAllMethodArray = true; + + return context; + }, + ], + }); + + await service.find(); + }); + + it("before hooks have service as context and keep it in service method (#17)", async () => { + interface DummyParams extends Params { + test: number; + } + + class Dummy implements ServiceInterface { + number = 42; + + async get(id: any, params?: DummyParams) { + return { + id, + number: this.number, + test: params?.test, + }; + } + } + + const app = feathers<{ dummy: Dummy }>().use("dummy", new Dummy()); + const service = app.service("dummy"); + + service.hooks({ + before: { + get(this: any, context) { + context.params.test = this.number + 2; + + return context; + }, + }, + }); + + const data = await service.get(10); + + assertEquals(data, { + id: 10, + number: 42, + test: 44, + }); + }); +}); diff --git a/main/feathers/test/hooks/error.test.ts b/main/feathers/test/hooks/error.test.ts new file mode 100644 index 0000000000..577b3b512e --- /dev/null +++ b/main/feathers/test/hooks/error.test.ts @@ -0,0 +1,307 @@ +// deno-lint-ignore-file require-await +import { + describe, + it, + afterEach, + assertEquals, + assertRejects, + assertStrictEquals, + assert, + beforeEach, + assertObjectMatch, +} from "../../../commons/mod.ts"; +import { feathers, Application, FeathersService } from "../../mod.ts"; + +describe("`error` hooks", () => { + describe("on direct service method errors", () => { + const errorMessage = "Something else went wrong"; + const app = feathers().use("/dummy", { + async get() { + throw new Error("Something went wrong"); + }, + }); + const service = app.service("dummy"); + + afterEach(() => { + const s = service as any; + + s.__hooks.error.get = undefined; + s.__hooks.collected.get = []; + }); + + it("basic error hook", async () => { + service.hooks({ + error: { + get(context) { + assertStrictEquals(context.type, "error"); + assertStrictEquals(context.id, "test"); + assertStrictEquals(context.method, "get"); + assertStrictEquals(context.app, app); + assertStrictEquals(context.error.message, "Something went wrong"); + }, + }, + }); + + await assertRejects(() => service.get("test"), "Something went wrong"); + }); + + it("can change the error", async () => { + service.hooks({ + error: { + get(context) { + context.error = new Error(errorMessage); + }, + }, + }); + + await assertRejects(() => service.get("test"), errorMessage); + }); + + it("throwing an error", async () => { + service.hooks({ + error: { + get() { + throw new Error(errorMessage); + }, + }, + }); + + await assertRejects(() => service.get("test"), errorMessage); + }); + + it("rejecting a promise", async () => { + service.hooks({ + error: { + async get() { + throw new Error(errorMessage); + }, + }, + }); + + await assertRejects(() => service.get("test"), errorMessage); + }); + + it("can chain multiple hooks", async () => { + service.hooks({ + error: { + get: [ + function (context) { + context.error = new Error(errorMessage); + context.error.first = true; + }, + + function (context) { + context.error.second = true; + + return Promise.resolve(context); + }, + + function (context) { + context.error.third = true; + + return context; + }, + ], + }, + }); + + const err: any = await assertRejects( + () => service.get("test"), + errorMessage + ); + + assertObjectMatch(err, { + first: true, + second: true, + third: true, + }); + }); + + it("setting `context.result` will return result", async () => { + const data = { + message: "It worked", + }; + + service.hooks({ + error: { + get(context) { + context.result = data; + }, + }, + }); + + const result = await service.get(10); + + assertEquals(result, data); + }); + + it("allows to set `context.result = null` in error hooks (#865)", async () => { + const app = feathers().use("/dummy", { + async get() { + throw new Error("Damnit"); + }, + }); + + app.service("dummy").hooks({ + error: { + get(context: any) { + context.result = null; + }, + }, + }); + + const result = await app.service("dummy").get(1); + + assertStrictEquals(result, null); + }); + + it("uses the current hook object if thrown in a service method", async () => { + const app = feathers().use("/dummy", { + async get() { + throw new Error("Something went wrong"); + }, + }); + const service = app.service("dummy"); + + service.hooks({ + before(context) { + context.id = 42; + }, + error(context) { + assertStrictEquals(context.id, 42); + }, + }); + + await assertRejects(() => service.get(1), "Something went wrong"); + }); + }); + + describe("error in hooks", () => { + const errorMessage = "before hook broke"; + + let app: Application; + let service: FeathersService; + + beforeEach(() => { + app = feathers().use("/dummy", { + async get(id: any) { + return { + id, + text: `You have to do ${id}`, + }; + }, + }); + + service = app.service("dummy"); + }); + + it("in before hook", async () => { + service + .hooks({ + before() { + throw new Error(errorMessage); + }, + }) + .hooks({ + error(context) { + assertStrictEquals( + context.original.type, + "before", + "Original hook still set" + ); + assertStrictEquals(context.id, "dishes"); + assertStrictEquals(context.error.message, errorMessage); + }, + }); + + await assertRejects(() => service.get("dishes"), errorMessage); + }); + + it("in after hook", async () => { + service.hooks({ + after() { + throw new Error(errorMessage); + }, + + error(context) { + assertStrictEquals( + context.original.type, + "after", + "Original hook still set" + ); + assertStrictEquals(context.id, "dishes"); + assertEquals(context.original.result, { + id: "dishes", + text: "You have to do dishes", + }); + assertStrictEquals(context.error.message, errorMessage); + }, + }); + + await assertRejects(() => service.get("dishes"), errorMessage); + }); + + it("uses the current hook object if thrown in a hook and sets context.original", async () => { + service.hooks({ + after(context) { + context.modified = true; + + throw new Error(errorMessage); + }, + + error(context) { + assert(context.modified); + assertStrictEquals(context.original.type, "after"); + }, + }); + + await assertRejects(() => service.get("laundry"), errorMessage); + }); + }); + + it("Error in before hook causes inter-service calls to have wrong hook context (#841)", async () => { + const app = feathers(); + + let service1Params: any; + let service2Params: any; + + app.use("/service1", { + async find() { + return { message: "service1 success" }; + }, + }); + + app.service("service1").hooks({ + before(context: any) { + service1Params = context.params; + throw new Error("Error in service1 before hook"); + }, + }); + + app.use("/service2", { + async find() { + await app.service("/service1").find({}); + + return { message: "service2 success" }; + }, + }); + + app.service("service2").hooks({ + before(context: any) { + service2Params = context.params; + context.params.foo = "bar"; + }, + error(context: any) { + assert(service1Params !== context.params); + assert(service2Params === context.params); + assertStrictEquals(context.path, "service2"); + assertStrictEquals(context.params.foo, "bar"); + }, + }); + + await assertRejects( + () => app.service("/service2").find(), + "Error in service1 before hook" + ); + }); +}); diff --git a/main/feathers/test/hooks/hooks.test.ts b/main/feathers/test/hooks/hooks.test.ts new file mode 100644 index 0000000000..1b8945b14f --- /dev/null +++ b/main/feathers/test/hooks/hooks.test.ts @@ -0,0 +1,446 @@ +// deno-lint-ignore-file require-await +import { + describe, + it, + afterEach, + assertEquals, + assertRejects, + assertStrictEquals, + assert, + beforeEach, + assertObjectMatch, +} from "../../../commons/mod.ts"; +import { + hooks, + NextFunction, +} from "https://deno.land/x/hooks@v0.7.5/src/index.ts"; +import { + HookContext, + createContext, + feathers, + Id, + Params, + ServiceInterface, +} from "../../mod.ts"; + +describe("hooks basics", () => { + it("mix @feathersjs/hooks and .hooks", async () => { + interface SimpleParams extends Params { + chain: string[]; + } + class SimpleService { + async get(id: Id, params: SimpleParams) { + return { id, chain: params.chain }; + } + } + + hooks(SimpleService.prototype, [ + async (ctx: HookContext, next: NextFunction) => { + ctx.params.chain.push("@hooks all before"); + await next(); + ctx.params.chain.push("@hooks all after"); + }, + ]); + + hooks(SimpleService, { + get: [ + async (ctx: HookContext, next: NextFunction) => { + assert(ctx.app); + assert(ctx.service); + ctx.params.chain.push("@hooks get before"); + await next(); + ctx.params.chain.push("@hooks get after"); + }, + ], + }); + + const app = feathers().use("/dummy", new SimpleService()); + const service = app.service("dummy"); + + app.hooks([ + async function appHook(ctx: HookContext, next: NextFunction) { + assert(ctx.app); + assert(ctx.service); + + ctx.params.chain = ["app.hooks before"]; + await next(); + ctx.params.chain.push("app.hooks after"); + }, + ]); + + app.hooks({ + before: [ + (ctx: HookContext) => { + ctx.params.chain.push("app.hooks regular before"); + }, + ], + after: [ + (ctx: HookContext) => { + ctx.params.chain.push("app.hooks regular after"); + }, + ], + }); + + service.hooks({ + before: { + get: (ctx: HookContext) => { + ctx.params.chain.push("service.hooks regular before"); + }, + }, + after: { + get: (ctx: HookContext) => { + ctx.params.chain.push("service.hooks regular after"); + }, + }, + }); + + service.hooks({ + get: [ + async (ctx: HookContext, next: NextFunction) => { + ctx.params.chain.push("service.hooks get before"); + await next(); + ctx.params.chain.push("service.hooks get after"); + }, + ], + }); + + service.hooks({ + before: { + get: (ctx: HookContext) => { + ctx.params.chain.push("service.hooks 2 regular before"); + }, + }, + after: { + get: (ctx: HookContext) => { + ctx.params.chain.push("service.hooks 2 regular after"); + }, + }, + }); + + const { chain } = await service.get(1, {}); + + assertEquals(chain, [ + "app.hooks before", + "app.hooks regular before", + "@hooks all before", + "@hooks get before", + "service.hooks get before", + "service.hooks regular before", + "service.hooks 2 regular before", + "service.hooks regular after", + "service.hooks 2 regular after", + "service.hooks get after", + "@hooks get after", + "@hooks all after", + "app.hooks regular after", + "app.hooks after", + ]); + }); + + // it('validates arguments', async () => { + // const app = feathers().use('/dummy', { + // async get (id: any, params: any) { + // return { id, user: params.user }; + // }, + + // async create (data: any) { + // return data; + // } + // }); + + // await assert.rejects(() => app.service('dummy').get(), { + // message: 'An id must be provided to the \'dummy.get\' method' + // }); + // await assert.rejects(() => app.service('dummy').create(), { + // message: 'A data object must be provided to the \'dummy.create\' method' + // }); + // }); + + it("works with services that return a promise (feathers-hooks#28)", async () => { + interface DummyParams extends Params { + user: string; + } + + const app = feathers<{ + dummy: ServiceInterface; + }>().use("dummy", { + async get(id: any, params: any) { + return { id, user: params.user }; + }, + }); + const service = app.service("dummy"); + + service.hooks({ + before: { + get(context) { + context.params.user = "David"; + }, + }, + after: { + get(context) { + context.result.after = true; + }, + }, + }); + + const data = await service.get(10); + + assertEquals(data, { id: 10, user: "David", after: true }); + }); + + it("has context.app, context.service and context.path", async () => { + const app = feathers().use("/dummy", { + async get(id: any) { + return { id }; + }, + }); + const service = app.service("dummy"); + + service.hooks({ + before(context) { + assertStrictEquals(this, service); + assertStrictEquals(context.service, service); + assertStrictEquals(context.app, app); + assertStrictEquals(context.path, "dummy"); + }, + }); + + await service.get("test"); + }); + + it("does not error when result is null", async () => { + const app = feathers().use("/dummy", { + async get(id: any) { + return { id }; + }, + }); + const service = app.service("dummy"); + + service.hooks({ + after: { + get: [ + function (context) { + context.result = null; + return context; + }, + ], + }, + }); + + const result = await service.get(1); + + assertStrictEquals(result, null); + }); + + it("registering an already hooked service works (#154)", () => { + const app = feathers().use("/dummy", { + async get(id: any, params: any) { + return { id, params }; + }, + }); + + app.use("/dummy2", app.service("dummy")); + }); + + describe("returns the context when passing it as last parameter", () => { + it("on normal method call", async () => { + const app = feathers().use("/dummy", { + async get(id: any, params: any) { + return { id, params }; + }, + }); + const service = app.service("dummy"); + const context = createContext(service, "get"); + const returnedContext = await app.service("dummy").get(10, {}, context); + + assertStrictEquals(returnedContext.service, app.service("dummy")); + assertStrictEquals(returnedContext.type, null); + assertStrictEquals(returnedContext.path, "dummy"); + assertEquals(returnedContext.result, { + id: 10, + params: {}, + }); + }); + + it.ignore("on error", async () => { + const app = feathers().use("/dummy", { + get() { + throw new Error("Something went wrong"); + }, + }); + + const service = app.service("dummy"); + const context = createContext(service, "get"); + + const err: any = await assertRejects(() => service.get(10, {}, context)); + + assertObjectMatch(err, { + service: app.service("dummy"), + type: null, + path: "dummy", + }); + }); + + // it('on argument validation error (https://github.com/feathersjs/express/issues/19)', async () => { + // const app = feathers().use('/dummy', { + // async get (id: string) { + // return { id }; + // } + // }); + + // await assert.rejects(() => app.service('dummy').get(undefined, {}, true), context => { + // assert.strictEqual(context.service, app.service('dummy')); + // assert.strictEqual(context.type, 'error'); + // assert.strictEqual(context.path, 'dummy'); + // assert.strictEqual(context.error.message, 'An id must be provided to the \'dummy.get\' method'); + + // return true; + // }); + // }); + + // it('on error in error hook (https://github.com/feathersjs/express/issues/21)', async () => { + // const app = feathers().use('/dummy', { + // async get () { + // throw new Error('Nope'); + // } + // }); + + // app.service('dummy').hooks({ + // error: { + // get () { + // throw new Error('Error in error hook'); + // } + // } + // }); + + // await assert.rejects(() => app.service('dummy').get(10, {}, true), context => { + // assert.strictEqual(context.service, app.service('dummy')); + // assert.strictEqual(context.type, 'error'); + // assert.strictEqual(context.path, 'dummy'); + // assert.strictEqual(context.error.message, 'Error in error hook'); + + // return true; + // }); + // }); + + it("still swallows error if context.result is set", async () => { + const result = { message: "this is a test" }; + const app = feathers().use("/dummy", { + async get() { + throw new Error("Something went wrong"); + }, + }); + + app.service("dummy").hooks({ + error(context: any) { + context.result = result; + }, + }); + + const service = app.service("dummy"); + const context = createContext(service, "get"); + const returnedContext = await service.get(10, {}, context); + + assert(returnedContext.error); + assertEquals(returnedContext.result, result); + }); + }); + + it("can register hooks on a custom method, still adds hooks to default methods", async () => { + class Dummy { + async get(id: Id) { + return { id }; + } + + async create(data: any) { + return data; + } + + async custom(data: any) { + return data; + } + } + + const app = feathers<{ + dummy: Dummy; + }>().use("dummy", new Dummy(), { + methods: ["get", "custom"], + }); + + app.service("dummy").hooks({ + custom: [ + async (context, next) => { + context.data.fromHook = true; + await next(); + }, + ], + create: [async (_context, next) => next()], + }); + + assertEquals( + await app.service("dummy").custom({ + message: "testing", + }), + { + message: "testing", + fromHook: true, + } + ); + }); + + it("normalizes params to object even when it is falsy (#1001)", async () => { + const app = feathers().use("/dummy", { + async get(id: Id, params: Params) { + return { id, params }; + }, + }); + + // @ts-ignore + const result = await app.service("dummy").get("test", null); + + assertObjectMatch(result, { + id: "test", + params: {}, + }); + }); + + it("allows to return new context in basic hooks (#2451)", async () => { + const app = feathers().use("/dummy", { + async get() { + return {}; + }, + }); + const service = app.service("dummy"); + + service.hooks({ + before: { + get: [ + (context) => { + return { + ...context, + value: "something", + }; + }, + (context) => { + assertStrictEquals(context.value, "something"); + }, + ], + }, + after: { + get: [ + (context) => { + context.result = { + value: context.value, + }; + }, + ], + }, + }); + + const data = await service.get(10); + + assertEquals(data, { + value: "something", + }); + }); +}); diff --git a/main/feathers/test/util.ts b/main/feathers/test/util.ts new file mode 100644 index 0000000000..5e9d1aa97d --- /dev/null +++ b/main/feathers/test/util.ts @@ -0,0 +1,12 @@ +import { EventEmitter } from "../../commons/mod.ts"; + +export const awaitEvent = ( + emitter: EventEmitter, + event: string | symbol +) => { + return new Promise((resolve) => { + emitter.once(event, (data: Data) => { + resolve(data); + }); + }); +}; diff --git a/main/memory/LICENSE b/main/memory/LICENSE new file mode 100644 index 0000000000..59604f46f3 --- /dev/null +++ b/main/memory/LICENSE @@ -0,0 +1,22 @@ +The MIT License (MIT) + +Copyright (c) 2022 Feathers + +Permission is hereby granted, free of charge, to any person obtaining a copy +of this software and associated documentation files (the "Software"), to deal +in the Software without restriction, including without limitation the rights +to use, copy, modify, merge, publish, distribute, sublicense, and/or sell +copies of the Software, and to permit persons to whom the Software is +furnished to do so, subject to the following conditions: + +The above copyright notice and this permission notice shall be included in all +copies or substantial portions of the Software. + +THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE +AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, +OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE +SOFTWARE. + diff --git a/main/memory/README.md b/main/memory/README.md new file mode 100644 index 0000000000..1d2e1f0b2e --- /dev/null +++ b/main/memory/README.md @@ -0,0 +1,114 @@ +# @feathersjs/memory + +[![CI](https://github.com/feathersjs/feathers/workflows/CI/badge.svg)](https://github.com/feathersjs/feathers/actions?query=workflow%3ACI) +[![Download Status](https://img.shields.io/npm/dm/@feathersjs/memory.svg?style=flat-square)](https://www.npmjs.com/package/@feathersjs/memory) +[![Discord](https://badgen.net/badge/icon/discord?icon=discord&label)](https://discord.gg/qa8kez8QBx) + +A [Feathers](https://feathersjs.com) service adapter for in-memory data storage +that works on all platforms. + +```bash +$ npm install --save @feathersjs/memory +``` + +> **Important:** `@feathersjs/memory` implements the +> [Feathers Common database adapter API](https://docs.feathersjs.com/api/databases/common.html) +> and +> [querying syntax](https://docs.feathersjs.com/api/databases/querying.html). + +## API + +### `service([options])` + +Returns a new service instance initialized with the given options. + +```js +const service = require("@feathersjs/memory"); + +app.use("/messages", service()); +app.use("/messages", service({ id, startId, store, events, paginate })); +``` + +**Options:** + +- `id` (_optional_, default: `'id'`) - The name of the id field property. +- `startId` (_optional_, default: `0`) - An id number to start with that will be + incremented for every new record (unless it is already set). +- `store` (_optional_) - An object with id to item assignments to pre-initialize + the data store +- `events` (_optional_) - A list of + [custom service events](https://docs.feathersjs.com/api/events.html#custom-events) + sent by this service +- `paginate` (_optional_) - A + [pagination object](https://docs.feathersjs.com/api/databases/common.html#pagination) + containing a `default` and `max` page size +- `whitelist` (_DEPRECATED_) - renamed to `allow` +- `allow` (_optional_) - A list of additional query parameters to allow +- `multi` (_optional_) - Allow `create` with arrays and `update` and `remove` + with `id` `null` to change multiple items. Can be `true` for all methods or an + array of allowed methods (e.g. `[ 'remove', 'create' ]`) + +## Example + +Here is an example of a Feathers server with a `messages` in-memory service that +supports pagination: + +``` +$ npm install @feathersjs/feathers @feathersjs/express @feathersjs/socketio @feathersjs/errors @feathersjs/memory +``` + +In `app.js`: + +```js +const feathers = require("@feathersjs/feathers"); +const express = require("@feathersjs/express"); +const socketio = require("@feathersjs/socketio"); + +const memory = require("@feathersjs/memory"); + +// Create an Express compatible Feathers application instance. +const app = express(feathers()); +// Turn on JSON parser for REST services +app.use(express.json()); +// Turn on URL-encoded parser for REST services +app.use(express.urlencoded({ extended: true })); +// Enable REST services +app.configure(express.rest()); +// Enable REST services +app.configure(socketio()); +// Create an in-memory Feathers service with a default page size of 2 items +// and a maximum size of 4 +app.use( + "/messages", + memory({ + paginate: { + default: 2, + max: 4, + }, + }), +); +// Set up default error handler +app.use(express.errorHandler()); + +// Create a dummy Message +app.service("messages").create({ + text: "Message created on server", +}).then((message) => console.log("Created message", message)); + +// Start the server. +const port = 3030; + +app.listen(port, () => { + console.log(`Feathers server listening on port ${port}`); +}); +``` + +Run the example with `node app` and go to +[localhost:3030/messages](http://localhost:3030/messages). + +## License + +Copyright (c) 2022 +[Feathers contributors](https://github.com/feathersjs/feathers/graphs/contributors) + +Licensed under the [MIT license](LICENSE). diff --git a/main/memory/mod.ts b/main/memory/mod.ts new file mode 100644 index 0000000000..401c73ac2a --- /dev/null +++ b/main/memory/mod.ts @@ -0,0 +1 @@ +export * from "./src/index.ts"; diff --git a/main/memory/src/index.ts b/main/memory/src/index.ts new file mode 100644 index 0000000000..ee75da540e --- /dev/null +++ b/main/memory/src/index.ts @@ -0,0 +1,266 @@ +import { NotFound } from "../../errors/mod.ts"; +import { _ } from "../../commons/mod.ts"; +import { + AdapterBase, + AdapterParams, + AdapterServiceOptions, + PaginationOptions, + select, + sorter, +} from "../../adapter-commons/mod.ts"; +import sift from "https://esm.sh/sift@15.1.0"; +import { + Id, + NullableId, + Paginated, + Params, + ServiceMethods, +} from "../../feathers/mod.ts"; + +export interface MemoryServiceStore { + [key: string]: T; +} + +export interface MemoryServiceOptions extends AdapterServiceOptions { + store?: MemoryServiceStore; + startId?: number; + matcher?: (query: any) => any; + sorter?: (sort: any) => any; +} + +const _select = (data: any, params: any, ...args: any[]) => { + const base = select(params, ...args); + + return base(JSON.parse(JSON.stringify(data))); +}; + +export class MemoryAdapter, P extends Params = Params> + extends AdapterBase< + T, + D, + P, + MemoryServiceOptions + > { + store: MemoryServiceStore; + _uId: number; + + constructor(options: MemoryServiceOptions = {}) { + super({ + id: "id", + matcher: sift, + sorter, + store: {}, + startId: 0, + ...options, + }); + this._uId = this.options.startId!; + this.store = { ...this.options.store }; + } + + async getEntries(_params?: P) { + const params = _params || ({} as P); + + return this.$find({ + ...params, + paginate: false, + }); + } + + getQuery(params: P) { + const { $skip, $sort, $limit, $select, ...query } = params.query || {}; + + return { + query, + filters: { $skip, $sort, $limit, $select }, + }; + } + + async $find( + _params?: P & { paginate?: PaginationOptions }, + ): Promise>; + async $find(_params?: P & { paginate: false }): Promise; + async $find(_params?: P): Promise | T[]>; + async $find(params: P = {} as P): Promise | T[]> { + const { paginate } = this.getOptions(params); + const { query, filters } = this.getQuery(params); + + let values = _.values(this.store).filter(this.options.matcher!(query)); + const total = values.length; + + if (filters.$sort !== undefined) { + values.sort(this.options.sorter!(filters.$sort)); + } + + if (filters.$skip !== undefined) { + values = values.slice(filters.$skip); + } + + if (filters.$limit !== undefined) { + values = values.slice(0, filters.$limit); + } + + const result: Paginated = { + total, + limit: filters.$limit, + skip: filters.$skip || 0, + data: values.map((value) => _select(value, params)), + }; + + if (!paginate) { + return result.data; + } + + return result; + } + + async $get(id: Id, params: P = {} as P): Promise { + const { query } = this.getQuery(params); + + if (id in this.store) { + const value = this.store[id]; + + if (this.options.matcher!(query)(value)) { + return _select(value, params, this.id); + } + } + + throw new NotFound(`No record found for id '${id}'`); + } + + async $create(data: Partial, params?: P): Promise; + async $create(data: Partial[], params?: P): Promise; + async $create(data: Partial | Partial[], _params?: P): Promise; + async $create( + data: Partial | Partial[], + params: P = {} as P, + ): Promise { + if (Array.isArray(data)) { + return Promise.all(data.map((current) => this.$create(current, params))); + } + + const id = (data as any)[this.id!] || this._uId++; + const current = _.extend({}, data, { [this.id!]: id }); + const result = (this.store[id] = current); + + return _select(result, params, this.id) as T; + } + + async $update(id: Id, data: D, params: P = {} as P): Promise { + const oldEntry = await this.$get(id); + // We don't want our id to change type if it can be coerced + const oldId = (oldEntry as any)[this.id!]; + + // eslint-disable-next-line eqeqeq + id = oldId == id ? oldId : id; + + this.store[id] = _.extend({}, data, { [this.id!]: id }); + + return this.$get(id, params); + } + + async $patch(id: null, data: Partial, params?: P): Promise; + async $patch(id: Id, data: Partial, params?: P): Promise; + async $patch(id: NullableId, data: Partial, _params?: P): Promise; + async $patch( + id: NullableId, + data: Partial, + params: P = {} as P, + ): Promise { + const { query } = this.getQuery(params); + const patchEntry = (entry: T) => { + const currentId = (entry as any)[this.id!]; + + this.store[currentId] = _.extend( + this.store[currentId], + _.omit(data, this.id!), + ); + + return _select(this.store[currentId], params, this.id); + }; + + if (id === null) { + const entries = await this.getEntries({ + ...params, + query, + }); + + return entries.map(patchEntry); + } + + return patchEntry(await this.$get(id, params)); // Will throw an error if not found + } + + async $remove(id: null, params?: P): Promise; + async $remove(id: Id, params?: P): Promise; + async $remove(id: NullableId, _params?: P): Promise; + async $remove(id: NullableId, params: P = {} as P): Promise { + const { query } = this.getQuery(params); + + if (id === null) { + const entries = await this.getEntries({ + ...params, + query, + }); + + return Promise.all( + entries.map((current: any) => + this.$remove(current[this.id!] as Id, params) + ), + ); + } + + const entry = await this.$get(id, params); + + delete this.store[id]; + + return entry; + } +} + +export class MemoryService< + T = any, + D = Partial, + P extends AdapterParams = AdapterParams, +> extends MemoryAdapter + implements ServiceMethods, D, P> { + async find( + params?: P & { paginate?: PaginationOptions }, + ): Promise>; + async find(params?: P & { paginate: false }): Promise; + async find(params?: P): Promise | T[]>; + async find(params?: P): Promise | T[]> { + return this._find(params) as any; + } + + async get(id: Id, params?: P): Promise { + return this._get(id, params); + } + + async create(data: D, params?: P): Promise; + async create(data: D[], params?: P): Promise; + async create(data: D | D[], params?: P): Promise { + return this._create(data, params); + } + + async update(id: Id, data: D, params?: P): Promise { + return this._update(id, data, params); + } + + async patch(id: Id, data: Partial, params?: P): Promise; + async patch(id: null, data: Partial, params?: P): Promise; + async patch(id: NullableId, data: Partial, params?: P): Promise { + return this._patch(id, data, params); + } + + async remove(id: Id, params?: P): Promise; + async remove(id: null, params?: P): Promise; + async remove(id: NullableId, params?: P): Promise { + return this._remove(id, params); + } +} + +export function memory, P extends Params = Params>( + options: Partial> = {}, +) { + return new MemoryService(options); +} diff --git a/main/memory/test/index.test.ts b/main/memory/test/index.test.ts new file mode 100644 index 0000000000..a13c477eff --- /dev/null +++ b/main/memory/test/index.test.ts @@ -0,0 +1,248 @@ +import { + assert, + assertEquals, + assertStrictEquals, + describe, + it, +} from "../../commons/mod.ts"; +import adapterTests from "../../adapter-tests/mod.ts"; +import { errors } from "../../errors/mod.ts"; +import { feathers } from "../../feathers/mod.ts"; + +import { MemoryService } from "../mod.ts"; + +const testSuite = adapterTests([ + ".options", + ".events", + "._get", + "._find", + "._create", + "._update", + "._patch", + "._remove", + ".$get", + ".$find", + ".$create", + ".$update", + ".$patch", + ".$remove", + ".get", + ".get + $select", + ".get + id + query", + ".get + NotFound", + ".get + id + query id", + ".find", + ".find + paginate + query", + ".remove", + ".remove + $select", + ".remove + id + query", + ".remove + multi", + ".remove + multi no pagination", + ".remove + id + query id", + ".update", + ".update + $select", + ".update + id + query", + ".update + NotFound", + ".update + id + query id", + ".update + query + NotFound", + ".patch", + ".patch + $select", + ".patch + id + query", + ".patch multiple", + ".patch multiple no pagination", + ".patch multi query same", + ".patch multi query changed", + ".patch + query + NotFound", + ".patch + NotFound", + ".patch + id + query id", + ".create", + ".create + $select", + ".create multi", + "internal .find", + "internal .get", + "internal .create", + "internal .update", + "internal .patch", + "internal .remove", + ".find + equal", + ".find + equal multiple", + ".find + $sort", + ".find + $sort + string", + ".find + $limit", + ".find + $limit 0", + ".find + $skip", + ".find + $select", + ".find + $or", + ".find + $in", + ".find + $nin", + ".find + $lt", + ".find + $lte", + ".find + $gt", + ".find + $gte", + ".find + $ne", + ".find + $gt + $lt + $sort", + ".find + $or nested + $sort", + ".find + paginate", + ".find + paginate + $limit + $skip", + ".find + paginate + $limit 0", + ".find + paginate + params", + "params.adapter + paginate", + "params.adapter + multi", +]); + +describe("Feathers Memory Service", () => { + type Person = { + id: number; + name: string; + age?: number; + }; + + type Animal = { + type: string; + age: number; + }; + + const events = ["testing"]; + const app = feathers<{ + people: MemoryService; + "people-customid": MemoryService; + animals: MemoryService; + matcher: MemoryService; + }>(); + + app.use("people", new MemoryService({ events })); + app.use( + "people-customid", + new MemoryService({ + id: "customid", + events, + }), + ); + + it("update with string id works", async () => { + const people = app.service("people"); + const person = await people.create({ + name: "Tester", + age: 33, + }); + + const updatedPerson: any = await people.update( + person.id.toString(), + person, + ); + + assertStrictEquals(typeof updatedPerson.id, "number"); + + await people.remove(person.id.toString()); + }); + + it("patch record with prop also in query", async () => { + app.use("animals", new MemoryService({ multi: true })); + const animals = app.service("animals"); + await animals.create([ + { + type: "cat", + age: 30, + }, + { + type: "dog", + age: 10, + }, + ]); + + const [updated] = await animals.patch(null, { age: 40 }, { + query: { age: 30 }, + }); + + assertStrictEquals(updated.age, 40); + + await animals.remove(null, {}); + }); + + it("allows to pass custom find and sort matcher", async () => { + let sorterCalled = false; + let matcherCalled = false; + + app.use( + "matcher", + new MemoryService({ + matcher() { + matcherCalled = true; + return function () { + return true; + }; + }, + + sorter() { + sorterCalled = true; + return function () { + return 0; + }; + }, + }), + ); + + await app.service("matcher").find({ + query: { $sort: { something: 1 } }, + }); + + assert(sorterCalled, "sorter called"); + assert(matcherCalled, "matcher called"); + }); + + it("does not modify the original data", async () => { + const people = app.service("people"); + + const person = await people.create({ + name: "Delete tester", + age: 33, + }); + + delete person.age; + + const otherPerson = await people.get(person.id); + + assertStrictEquals(otherPerson.age, 33); + + await people.remove(person.id); + }); + + it("does not $select the id", async () => { + const people = app.service("people"); + const person = await people.create({ + name: "Tester", + }); + const results = await people.find({ + paginate: false, + query: { + name: "Tester", + $select: ["name"], + }, + }); + + assertEquals( + results[0], + // @ts-ignore + { name: "Tester" }, + "deepEquals the same", + ); + + await people.remove(person.id); + }); + + it("update with null throws error", async () => { + try { + // @ts-ignore + await app.service("people").update(null, {}); + throw new Error("Should never get here"); + } catch (error: any) { + assertStrictEquals( + error.message, + "You can not replace multiple instances. Did you mean 'patch'?", + ); + } + }); + + testSuite(app, errors, "people"); + testSuite(app, errors, "people-customid", "customid"); +}); diff --git a/main/schema/LICENSE b/main/schema/LICENSE new file mode 100644 index 0000000000..59604f46f3 --- /dev/null +++ b/main/schema/LICENSE @@ -0,0 +1,22 @@ +The MIT License (MIT) + +Copyright (c) 2022 Feathers + +Permission is hereby granted, free of charge, to any person obtaining a copy +of this software and associated documentation files (the "Software"), to deal +in the Software without restriction, including without limitation the rights +to use, copy, modify, merge, publish, distribute, sublicense, and/or sell +copies of the Software, and to permit persons to whom the Software is +furnished to do so, subject to the following conditions: + +The above copyright notice and this permission notice shall be included in all +copies or substantial portions of the Software. + +THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE +AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, +OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE +SOFTWARE. + diff --git a/main/schema/README.md b/main/schema/README.md new file mode 100644 index 0000000000..519f0ec138 --- /dev/null +++ b/main/schema/README.md @@ -0,0 +1,25 @@ +# @feathersjs/schema + +[![CI](https://github.com/feathersjs/feathers/workflows/CI/badge.svg)](https://github.com/feathersjs/feathers/actions?query=workflow%3ACI) +[![Download Status](https://img.shields.io/npm/dm/@feathersjs/schema.svg?style=flat-square)](https://www.npmjs.com/package/@feathersjs/schema) +[![Discord](https://badgen.net/badge/icon/discord?icon=discord&label)](https://discord.gg/qa8kez8QBx) + +> A common data schema definition format + +## Installation + +``` +npm install @feathersjs/schema --save +``` + +## Documentation + +Refer to the [Feathers documentation](https://docs.feathersjs.com) for more +details. + +## License + +Copyright (c) 2022 +[Feathers contributors](https://github.com/feathersjs/feathers/graphs/contributors) + +Licensed under the [MIT license](LICENSE). diff --git a/main/schema/mod.ts b/main/schema/mod.ts new file mode 100644 index 0000000000..401c73ac2a --- /dev/null +++ b/main/schema/mod.ts @@ -0,0 +1 @@ +export * from "./src/index.ts"; diff --git a/main/schema/src/default-schemas.ts b/main/schema/src/default-schemas.ts new file mode 100644 index 0000000000..6752c4691f --- /dev/null +++ b/main/schema/src/default-schemas.ts @@ -0,0 +1,162 @@ +import { FromSchema } from "https://deno.land/x/json_schema_to_ts@v2.5.5/index.d.ts"; + +export const authenticationSettingsSchema = { + type: "object", + required: ["secret", "entity", "authStrategies"], + properties: { + secret: { + type: "string", + description: "The JWT signing secret", + }, + entity: { + oneOf: [ + { + type: "null", + }, + { + type: "string", + }, + ], + description: "The name of the authentication entity (e.g. user)", + }, + entityId: { + type: "string", + description: "The name of the authentication entity id property", + }, + service: { + type: "string", + description: "The path of the entity service", + }, + authStrategies: { + type: "array", + items: { type: "string" }, + description: + "A list of authentication strategy names that are allowed to create JWT access tokens", + }, + parseStrategies: { + type: "array", + items: { type: "string" }, + description: + "A list of authentication strategy names that should parse HTTP headers for authentication information (defaults to `authStrategies`)", + }, + jwtOptions: { + type: "object", + }, + jwt: { + type: "object", + properties: { + header: { + type: "string", + default: "Authorization", + description: "The HTTP header containing the JWT", + }, + schemes: { + type: "array", + items: { type: "string" }, + description: "An array of schemes to support", + }, + }, + }, + local: { + type: "object", + required: ["usernameField", "passwordField"], + properties: { + usernameField: { + type: "string", + description: "Name of the username field (e.g. `email`)", + }, + passwordField: { + type: "string", + description: "Name of the password field (e.g. `password`)", + }, + hashSize: { + type: "number", + description: "The BCrypt salt length", + }, + errorMessage: { + type: "string", + default: "Invalid login", + description: "The error message to return on errors", + }, + entityUsernameField: { + type: "string", + description: + "Name of the username field on the entity if authentication request data and entity field names are different", + }, + entityPasswordField: { + type: "string", + description: + "Name of the password field on the entity if authentication request data and entity field names are different", + }, + }, + }, + oauth: { + type: "object", + properties: { + redirect: { + type: "string", + }, + origins: { + type: "array", + items: { type: "string" }, + }, + defaults: { + type: "object", + properties: { + key: { type: "string" }, + secret: { type: "string" }, + }, + }, + }, + }, + }, +} as const; + +export type AuthenticationConfiguration = FromSchema< + typeof authenticationSettingsSchema +>; + +export const sqlSettingsSchema = { + type: "object", + properties: { + client: { type: "string" }, + connection: { type: "string" }, + }, +} as const; + +/** + * Schema for properties that are available in a standard Feathers application. + */ +export const defaultAppSettings = { + authentication: authenticationSettingsSchema, + origins: { + type: "array", + items: { + type: "string", + }, + }, + paginate: { + type: "object", + additionalProperties: false, + required: ["default", "max"], + properties: { + default: { type: "number" }, + max: { type: "number" }, + }, + }, + mongodb: { type: "string" }, + mysql: sqlSettingsSchema, + postgresql: sqlSettingsSchema, + sqlite: sqlSettingsSchema, + mssql: sqlSettingsSchema, +} as const; + +export const defaultAppConfiguration = { + type: "object", + additionalProperties: false, + properties: defaultAppSettings, +} as const; + +export type DefaultAppConfiguration = FromSchema< + typeof defaultAppConfiguration +>; diff --git a/main/schema/src/hooks/index.ts b/main/schema/src/hooks/index.ts new file mode 100644 index 0000000000..84068496dd --- /dev/null +++ b/main/schema/src/hooks/index.ts @@ -0,0 +1,2 @@ +export * from "./resolve.ts"; +export * from "./validate.ts"; diff --git a/main/schema/src/hooks/resolve.ts b/main/schema/src/hooks/resolve.ts new file mode 100644 index 0000000000..575c5a745b --- /dev/null +++ b/main/schema/src/hooks/resolve.ts @@ -0,0 +1,209 @@ +import { HookContext, NextFunction } from "../../../feathers/mod.ts"; +import { compose } from "https://deno.land/x/hooks@v0.7.5/src/index.ts"; +import { Resolver, ResolverStatus } from "../resolver.ts"; + +const getContext = (context: H) => { + return Object.freeze({ + ...context, + params: Object.freeze({ + ...context.params, + query: Object.freeze({}), + }), + }); +}; + +const getData = (context: H) => { + const isPaginated = context.method === "find" && context.result.data; + const data = isPaginated ? context.result.data : context.result; + + return { isPaginated, data }; +}; + +const runResolvers = async ( + resolvers: Resolver[], + data: any, + ctx: H, + status?: Partial>, +) => { + let current: any = data; + + for (const resolver of resolvers) { + if (resolver && typeof resolver.resolve === "function") { + current = await resolver.resolve(current, ctx, status); + } + } + + return current as T; +}; + +export type ResolverSetting = + | Resolver + | Resolver[]; + +export type DataResolvers = { + create: Resolver; + patch: Resolver; + update: Resolver; +}; + +export type ResolveAllSettings = { + data?: DataResolvers; + query?: Resolver; + result?: Resolver; + dispatch?: Resolver; +}; + +export const DISPATCH = Symbol("@feathersjs/schema/dispatch"); + +export const getDispatch = (value: any) => + typeof value === "object" && value !== null && value[DISPATCH] !== undefined + ? value[DISPATCH] + : value; + +export const resolveQuery = + (...resolvers: Resolver[]) => + async (context: H, next?: NextFunction) => { + const ctx = getContext(context); + const data = context?.params?.query || {}; + const query = await runResolvers(resolvers, data, ctx); + + context.params = { + ...context.params, + query, + }; + + if (typeof next === "function") { + return next(); + } + }; + +export const resolveData = + (settings: DataResolvers | Resolver) => + async (context: H, next?: NextFunction) => { + if ( + context.method === "create" || context.method === "patch" || + context.method === "update" + ) { + const resolvers = settings instanceof Resolver + ? [settings] + : [settings[context.method]]; + const ctx = getContext(context); + const data = context.data; + + const status = { + originalContext: context, + }; + + if (Array.isArray(data)) { + context.data = await Promise.all( + data.map((current) => runResolvers(resolvers, current, ctx, status)), + ); + } else { + context.data = await runResolvers(resolvers, data, ctx, status); + } + } + + if (typeof next === "function") { + return next(); + } + }; + +export const resolveResult = + (...resolvers: Resolver[]) => + async (context: H, next?: NextFunction) => { + if (typeof next === "function") { + const { $resolve: properties, ...query } = context.params?.query || {}; + const resolve = { + originalContext: context, + ...context.params.resolve, + properties, + }; + + context.params = { + ...context.params, + resolve, + query, + }; + + await next(); + } + + const ctx = getContext(context); + const status = context.params.resolve; + const { isPaginated, data } = getData(context); + + const result = Array.isArray(data) + ? await Promise.all( + data.map((current) => runResolvers(resolvers, current, ctx, status)), + ) + : await runResolvers(resolvers, data, ctx, status); + + if (isPaginated) { + context.result.data = result; + } else { + context.result = result; + } + }; + +export const resolveDispatch = + (...resolvers: Resolver[]) => + async (context: H, next?: NextFunction) => { + if (typeof next === "function") { + await next(); + } + + const ctx = getContext(context); + const status = context.params.resolve; + const { isPaginated, data } = getData(context); + const resolveAndGetDispatch = async (current: any) => { + const resolved: any = await runResolvers(resolvers, current, ctx, status); + + return Object.keys(resolved).reduce((res, key) => { + res[key] = getDispatch(resolved[key]); + + return res; + }, {} as any); + }; + + const result = + await (Array.isArray(data) + ? Promise.all(data.map(resolveAndGetDispatch)) + : resolveAndGetDispatch(data)); + const dispatch = isPaginated + ? { + ...context.result, + data: result, + } + : result; + + context.dispatch = dispatch; + Object.defineProperty(context.result, DISPATCH, { + value: dispatch, + enumerable: false, + configurable: false, + }); + }; + +export const resolveExternal = resolveDispatch; + +export const resolveAll = ( + map: ResolveAllSettings, +) => { + const middleware = []; + + middleware.push(resolveDispatch(map.dispatch!)); + + if (map.result) { + middleware.push(resolveResult(map.result)); + } + + if (map.query) { + middleware.push(resolveQuery(map.query)); + } + + if (map.data) { + middleware.push(resolveData(map.data)); + } + + return compose(middleware); +}; diff --git a/main/schema/src/hooks/validate.ts b/main/schema/src/hooks/validate.ts new file mode 100644 index 0000000000..ddc9d864d9 --- /dev/null +++ b/main/schema/src/hooks/validate.ts @@ -0,0 +1,60 @@ +import { HookContext, NextFunction } from "../../../feathers/mod.ts"; +import { BadRequest } from "../../../errors/mod.ts"; +import { Schema, Validator } from "../schema.ts"; +import { DataValidatorMap } from "../json-schema.ts"; + +export const validateQuery = ( + schema: Schema | Validator, +) => { + const validator: Validator = typeof schema === "function" + ? schema + : schema.validate.bind(schema); + + return async (context: H, next?: NextFunction) => { + const data = context?.params?.query || {}; + + try { + const query = await validator(data); + + context.params = { + ...context.params, + query, + }; + + if (typeof next === "function") { + return next(); + } + } catch (error: any) { + throw error.ajv ? new BadRequest(error.message, error.errors) : error; + } + }; +}; + +export const validateData = ( + schema: Schema | DataValidatorMap, +) => { + return async (context: H, next?: NextFunction) => { + const data = context.data; + const validator = typeof (schema as Schema).validate === "function" + ? (schema as Schema).validate.bind(schema) + : (schema as any)[context.method]; + + if (validator) { + try { + if (Array.isArray(data)) { + context.data = await Promise.all( + data.map((current) => validator(current)), + ); + } else { + context.data = await validator(data); + } + } catch (error: any) { + throw error.ajv ? new BadRequest(error.message, error.errors) : error; + } + } + + if (typeof next === "function") { + return next(); + } + }; +}; diff --git a/main/schema/src/index.ts b/main/schema/src/index.ts new file mode 100644 index 0000000000..2f632498c4 --- /dev/null +++ b/main/schema/src/index.ts @@ -0,0 +1,32 @@ +import addFormats, { + FormatName, + FormatOptions, + FormatsPluginOptions, +} from "https://esm.sh/ajv-formats@2.1.1"; +import { HookContext } from "../../feathers/mod.ts"; +import { ResolverStatus } from "./resolver.ts"; + +export type { FromSchema } from "https://deno.land/x/json_schema_to_ts@v2.5.5/index.d.ts"; +export { addFormats }; +export type { FormatName, FormatOptions, FormatsPluginOptions }; + +export * from "./schema.ts"; +export * from "./resolver.ts"; +export * from "./hooks/index.ts"; +export * from "./json-schema.ts"; +export * from "./default-schemas.ts"; + +export * as hooks from "./hooks/index.ts"; +export * as jsonSchema from "./json-schema.ts"; + +export type Infer = S["_type"]; + +export type Combine = + & Pick, Exclude, keyof U>> + & U; + +declare module "../../feathers/src/declarations.ts" { + interface Params { + resolve?: ResolverStatus; + } +} diff --git a/main/schema/src/json-schema.ts b/main/schema/src/json-schema.ts new file mode 100644 index 0000000000..05cdd94031 --- /dev/null +++ b/main/schema/src/json-schema.ts @@ -0,0 +1,190 @@ +import { _ } from "../../commons/mod.ts"; +import { JSONSchema } from "https://deno.land/x/json_schema_to_ts@v2.5.5/index.js"; +import { Ajv, JSONSchemaDefinition, Validator } from "./schema.ts"; + +export type DataSchemaMap = { + create: JSONSchemaDefinition; + update?: JSONSchemaDefinition; + patch?: JSONSchemaDefinition; +}; + +export type DataValidatorMap = { + create: Validator; + update: Validator; + patch: Validator; +}; + +/** + * Returns a compiled validation function for a schema and AJV validator instance. + * + * @param schema The JSON schema definition + * @param validator The AJV validation instance + * @returns A compiled validation function + */ +export const getValidator = ( + schema: JSONSchemaDefinition, + validator: Ajv, +): Validator => + validator.compile({ + $async: true, + ...(schema as any), + }) as any as Validator; + +/** + * Returns compiled validation functions to validate data for the `create`, `update` and `patch` + * service methods. If not passed explicitly, the `update` validator will be the same as the `create` + * and `patch` will be the `create` validator with no required fields. + * + * @param def Either general JSON schema definition or a mapping of `create`, `update` and `patch` + * to their respecitve JSON schema + * @param validator The Ajv instance to use as the validator + * @returns A map of validator functions + */ +export const getDataValidator = ( + def: JSONSchemaDefinition | DataSchemaMap, + validator: Ajv, +): DataValidatorMap => { + const schema = ((def as any).create ? def : { create: def }) as DataSchemaMap; + + return { + create: getValidator(schema.create, validator), + update: getValidator( + schema.update || { + ...(schema.create as any), + $id: `${schema.create.$id}Update`, + }, + validator, + ), + patch: getValidator( + schema.patch || { + ...(schema.create as any), + $id: `${schema.create.$id}Patch`, + required: [], + }, + validator, + ), + }; +}; + +export type PropertyQuery = { + anyOf: [ + D, + { + type: "object"; + additionalProperties: false; + properties: { + $gt: D; + $gte: D; + $lt: D; + $lte: D; + $ne: D; + $in: { + type: "array"; + items: D; + }; + $nin: { + type: "array"; + items: D; + }; + }; + }, + ]; +}; + +/** + * Create a Feathers query syntax compatible JSON schema definition for a property definition. + * + * @param def The property definition (e.g. `{ type: 'string' }`) + * @returns A JSON schema definition for the Feathers query syntax for this property. + */ +export const queryProperty = (def: T) => { + const definition = _.omit(def, "default"); + return { + anyOf: [ + definition, + { + type: "object", + additionalProperties: false, + properties: { + $gt: definition, + $gte: definition, + $lt: definition, + $lte: definition, + $ne: definition, + $in: { + type: "array", + items: definition, + }, + $nin: { + type: "array", + items: definition, + }, + }, + }, + ], + } as const; +}; + +/** + * Creates Feathers a query syntax compatible JSON schema for multiple properties. + * + * @param definitions A map of property definitions + * @returns The JSON schema definition for the Feathers query syntax for multiple properties + */ +export const queryProperties = ( + definitions: T, +) => + Object.keys(definitions).reduce((res, key) => { + const result = res as any; + const definition = definitions[key]; + + result[key] = queryProperty(definition); + + return result; + }, {} as { [K in keyof T]: PropertyQuery }); + +/** + * Creates a JSON schema for the complete Feathers query syntax including `$limit`, $skip` + * and `$sort` and `$select` for the allowed properties. + * + * @param definition The property definitions to create the query syntax schema for + * @returns A JSON schema for the complete query syntax + */ +export const querySyntax = ( + definition: T, +) => ({ + $limit: { + type: "number", + minimum: 0, + }, + $skip: { + type: "number", + minimum: 0, + }, + $sort: { + type: "object", + properties: Object.keys(definition).reduce( + (res, key) => { + const result = res as any; + + result[key] = { + type: "number", + enum: [1, -1], + }; + + return result; + }, + {} as { + [K in keyof T]: { readonly type: "number"; readonly enum: [1, -1] }; + }, + ), + }, + $select: { + type: "array", + items: { + type: "string", + enum: Object.keys(definition) as any as (keyof T)[], + }, + }, + ...queryProperties(definition), +} as const); diff --git a/main/schema/src/resolver.ts b/main/schema/src/resolver.ts new file mode 100644 index 0000000000..7fce9373f4 --- /dev/null +++ b/main/schema/src/resolver.ts @@ -0,0 +1,175 @@ +import { BadRequest } from "../../errors/mod.ts"; +import { Schema } from "./schema.ts"; + +export type PropertyResolver = ( + value: V | undefined, + obj: T, + context: C, + status: ResolverStatus, +) => Promise; + +export type PropertyResolverMap = { + [key in keyof T]?: PropertyResolver; +}; + +export type ResolverConverter = ( + obj: any, + context: C, + status: ResolverStatus, +) => Promise; + +export interface ResolverConfig { + schema?: Schema; + /** + * @deprecated Use the `validateData` and `validateQuery` hooks explicitly instead + */ + validate?: "before" | "after" | false; + /** + * The properties to resolve + */ + properties: PropertyResolverMap; + /** + * A converter function that is run before property resolvers + * to transform the initial data into a different format. + */ + converter?: ResolverConverter; +} + +export interface ResolverStatus { + path: string[]; + originalContext?: C; + properties?: string[]; + stack: PropertyResolver[]; +} + +export class Resolver { + readonly _type!: T; + + constructor(public options: ResolverConfig) {} + + /** + * Resolve a single property + * + * @param name The name of the property + * @param data The current data + * @param context The current resolver context + * @param status The current resolver status + * @returns The resolver property + */ + async resolveProperty( + name: K, + data: D, + context: C, + status: Partial> = {}, + ): Promise { + const resolver = this.options.properties[name]!; + const value = (data as any)[name]; + const { path = [], stack = [] } = status || {}; + + // This prevents circular dependencies + if (stack.includes(resolver)) { + return undefined; + } + + const resolverStatus = { + ...status, + path: [...path, name as string], + stack: [...stack, resolver], + }; + + return resolver(value, data as any, context, resolverStatus); + } + + async convert( + data: D, + context: C, + status?: Partial>, + ) { + if (this.options.converter) { + const { path = [], stack = [] } = status || {}; + + return this.options.converter(data, context, { ...status, path, stack }); + } + + return data; + } + + async resolve( + _data: D, + context: C, + status?: Partial>, + ): Promise { + const { properties: resolvers, schema, validate } = this.options; + const payload = await this.convert(_data, context, status); + const data = schema && validate === "before" + ? await schema.validate(payload) + : payload; + const propertyList = ( + Array.isArray(status?.properties) + ? status?.properties + // By default get all data and resolver keys but remove duplicates + : [...new Set(Object.keys(data ?? {}).concat(Object.keys(resolvers)))] + ) as (keyof T)[]; + + const result: any = {}; + const errors: any = {}; + let hasErrors = false; + + // Not the most elegant but better performance + await Promise.all( + propertyList.map(async (name) => { + const value = (data as any)[name]; + + if (resolvers[name]) { + try { + const resolved = await this.resolveProperty( + name, + data, + context, + status, + ); + + if (resolved !== undefined) { + result[name] = resolved; + } + } catch (error: any) { + // TODO add error stacks + const convertedError = typeof error.toJSON === "function" + ? error.toJSON() + : { message: error.message || error }; + + errors[name] = convertedError; + hasErrors = true; + } + } else if (value !== undefined) { + result[name] = value; + } + }), + ); + + if (hasErrors) { + const propertyName = status?.properties + ? ` ${status.properties.join(".")}` + : ""; + + throw new BadRequest( + "Error resolving data" + (propertyName ? ` ${propertyName}` : ""), + errors, + ); + } + + return schema && validate === "after" + ? await schema.validate(result) + : result; + } +} + +/** + * Create a new resolver with ``. + * + * @param options The configuration for the returned resolver + * @returns A new resolver instance + */ +export function resolve(options: ResolverConfig) { + return new Resolver(options); +} diff --git a/main/schema/src/schema.ts b/main/schema/src/schema.ts new file mode 100644 index 0000000000..081658170a --- /dev/null +++ b/main/schema/src/schema.ts @@ -0,0 +1,77 @@ +import Ajv, { + AsyncValidateFunction, + ValidateFunction, +} from "https://esm.sh/ajv@8.11.0"; +import { + FromSchema, + JSONSchema, +} from "https://deno.land/x/json_schema_to_ts@v2.5.5/index.js"; +import { BadRequest } from "../../errors/mod.ts"; + +export const DEFAULT_AJV = new Ajv({ + coerceTypes: true, + addUsedSchema: false, +}); + +export { Ajv }; + +/** + * A validation function that takes data and returns the (possibly coerced) + * data or throws a validation error. + */ +export type Validator = (data: T) => Promise; + +export type JSONSchemaDefinition = JSONSchema & { + $id: string; + $async?: true; + properties?: { [key: string]: JSONSchema }; + required?: readonly string[]; +}; + +export interface Schema { + validate(...args: Parameters>): Promise; +} + +export class SchemaWrapper + implements Schema> { + ajv: Ajv; + validator: AsyncValidateFunction; + readonly _type!: FromSchema; + + constructor(public definition: S, ajv: Ajv = DEFAULT_AJV) { + this.ajv = ajv; + this.validator = this.ajv.compile({ + $async: true, + ...(this.definition as any), + }) as AsyncValidateFunction; + } + + get properties() { + return this.definition.properties as S["properties"]; + } + + get required() { + return this.definition.required as S["required"]; + } + + async validate>(...args: Parameters>) { + try { + const validated = (await this.validator(...args)) as T; + + return validated; + } catch (error: any) { + throw new BadRequest(error.message, error.errors); + } + } + + toJSON() { + return this.definition; + } +} + +export function schema( + definition: S, + ajv: Ajv = DEFAULT_AJV, +) { + return new SchemaWrapper(definition, ajv); +} diff --git a/main/schema/test/fixture.ts b/main/schema/test/fixture.ts new file mode 100644 index 0000000000..233d6390be --- /dev/null +++ b/main/schema/test/fixture.ts @@ -0,0 +1,231 @@ +import { + Application as FeathersApplication, + feathers, + HookContext, +} from "../../feathers/mod.ts"; +import { memory, MemoryService } from "../../memory/mod.ts"; +import { GeneralError } from "../../errors/mod.ts"; + +import { + Ajv, + FromSchema, + getDataValidator, + getValidator, + querySyntax, + resolve, + resolveAll, + resolveData, + resolveDispatch, + resolveQuery, + resolveResult, + validateData, + validateQuery, +} from "../mod.ts"; +import { AdapterParams } from "../../adapter-commons/mod.ts"; + +const fixtureAjv = new Ajv({ + coerceTypes: true, + addUsedSchema: false, +}); + +export const userDataSchema = { + $id: "UserData", + type: "object", + additionalProperties: false, + required: ["email"], + properties: { + email: { type: "string" }, + password: { type: "string" }, + }, +} as const; + +export const userDataValidator = getDataValidator(userDataSchema, fixtureAjv); + +export type UserData = FromSchema; + +export const userDataResolver = resolve>({ + properties: { + password: async () => { + return "hashed"; + }, + }, +}); + +export const userSchema = { + $id: "User", + type: "object", + additionalProperties: false, + required: ["id", ...userDataSchema.required], + properties: { + ...userDataSchema.properties, + id: { type: "number" }, + name: { type: "string" }, + }, +} as const; + +export type User = FromSchema; + +export const userResolver = resolve>({ + properties: { + name: async (_value, user) => user.email.split("@")[0], + }, +}); + +export const userExternalResolver = resolve>({ + properties: { + password: async () => undefined, + email: async () => "[redacted]", + }, +}); + +export const secondUserResolver = resolve>({ + properties: { + name: async (value, user) => `${value} (${user.email})`, + }, +}); + +export const messageDataSchema = { + $id: "MessageData", + type: "object", + additionalProperties: false, + required: ["text", "userId"], + properties: { + text: { type: "string" }, + userId: { type: "number" }, + }, +} as const; + +export type MessageData = FromSchema; + +export const messageSchema = { + $id: "MessageResult", + type: "object", + additionalProperties: false, + required: ["id", ...messageDataSchema.required], + properties: { + ...messageDataSchema.properties, + id: { type: "number" }, + user: { $ref: "User" }, + }, +} as const; + +export type Message = FromSchema< + typeof messageSchema, + { + references: [typeof userSchema]; + } +>; + +export const messageResolver = resolve>({ + properties: { + user: async (_value, message, context) => { + const { userId } = message; + + if (context.params.error === true) { + throw new GeneralError("This is an error"); + } + + const user = await context.app.service("users").get( + userId, + context.params, + ); + + return user as Message["user"]; + }, + }, +}); + +export const messageQuerySchema = { + $id: "MessageQuery", + type: "object", + additionalProperties: false, + required: [], + properties: { + ...querySyntax(messageDataSchema.properties), + $resolve: { + type: "array", + items: { type: "string" }, + }, + }, +} as const; + +export type MessageQuery = FromSchema; + +export const messageQueryValidator = getValidator( + messageQuerySchema, + fixtureAjv, +); + +export const messageQueryResolver = resolve< + MessageQuery, + HookContext +>({ + properties: { + userId: async (value, _query, context) => { + if (context.params?.user) { + return context.params.user.id; + } + + return value; + }, + }, +}); + +interface ServiceParams extends AdapterParams { + user?: User; + error?: boolean; +} + +type ServiceTypes = { + users: MemoryService; + messages: MemoryService; + paginatedMessages: MemoryService; +}; +type Application = FeathersApplication; + +const app = feathers(); + +app.use( + "users", + memory({ + multi: ["create"], + }), +); +app.use("messages", memory()); +app.use("paginatedMessages", memory({ paginate: { default: 10 } })); + +app.service("messages").hooks([ + resolveAll({ + result: messageResolver, + query: messageQueryResolver, + }), + validateQuery(messageQueryValidator), +]); + +app + .service("paginatedMessages") + .hooks([ + validateQuery(messageQueryValidator), + resolveQuery(messageQueryResolver), + resolveResult(messageResolver), + ]); + +app + .service("users") + .hooks([ + resolveDispatch(userExternalResolver), + resolveResult(userResolver, secondUserResolver), + ]); + +app.service("users").hooks({ + create: [ + validateData(userDataValidator), + resolveData({ + create: userDataResolver, + patch: userDataResolver, + update: userDataResolver, + }), + ], +}); + +export { app }; diff --git a/main/schema/test/hooks.test.ts b/main/schema/test/hooks.test.ts new file mode 100644 index 0000000000..b85acb3080 --- /dev/null +++ b/main/schema/test/hooks.test.ts @@ -0,0 +1,253 @@ +import { createContext } from "../../feathers/mod.ts"; +import { + describe, + it, + beforeAll, + assertStrictEquals, + assertRejects, + assert, + assertEquals +} from "../../commons/mod.ts"; +import { app, Message, User } from "./fixture.ts"; +import { BadRequest } from "../../errors/mod.ts"; + +describe("@feathersjs/schema/hooks", () => { + const text = "Hi there"; + + let message: Message; + let messageOnPaginatedService: Message; + let user: User; + + beforeAll(async () => { + user = ( + await app.service("users").create([ + { + email: "hello@feathersjs.com", + password: "supersecret", + }, + ]) + )[0]; + message = await app.service("messages").create({ + text, + userId: user.id, + }); + messageOnPaginatedService = await app.service("paginatedMessages").create({ + text, + userId: user.id, + }); + }); + + it("ran resolvers in sequence", () => { + assertStrictEquals(user.name, "hello (hello@feathersjs.com)"); + }); + + it("validates data", async () => { + await assertRejects( + () => app.service("users").create({ password: "failing" } as any), + BadRequest + ); + }); + + it("resolves results and handles resolver errors (#2534)", async () => { + const payload = { + userId: user.id, + text, + }; + + assert(user); + assertStrictEquals(user.password, "hashed", "Resolved data"); + assertEquals(message, { + id: 0, + user, + ...payload, + }); + + const messages = await app.service("messages").find({ + provider: "external", + }); + + // @ts-ignore + assertEquals(messages, [ + { + id: 0, + user, + ...payload, + }, + ]); + + const error = await assertRejects( + () => + app.service("messages").find({ + provider: "external", + error: true, + }), + ); + + assertEquals(error, + { + name: "BadRequest", + message: "Error resolving data", + code: 400, + className: "bad-request", + data: { + user: { + name: "GeneralError", + message: "This is an error", + code: 500, + className: "general-error", + }, + }, + }, + ); + }); + + it("resolves get result with the object on result", async () => { + const payload = { + userId: user.id, + text, + }; + + assert(user); + assertStrictEquals(user.password, "hashed", "Resolved data"); + assertEquals(message, { + id: 0, + user, + ...payload, + }); + + const result = await app.service("messages").get(0, { + provider: "external", + }); + + assertEquals(result, { + id: 0, + user, + ...payload, + }); + }); + + it("resolves find results with paginated result object", async () => { + const payload = { + userId: user.id, + text, + }; + + assert(user); + assertStrictEquals(user.password, "hashed", "Resolved data"); + assertEquals(messageOnPaginatedService, { + id: 0, + user, + ...payload, + }); + + const messages = await app.service("paginatedMessages").find({ + provider: "external", + query: { + $limit: 1, + $skip: 0, + }, + }); + + assertEquals(messages, { + limit: 1, + skip: 0, + total: 1, + data: [ + { + id: 0, + user, + ...payload, + }, + ], + }); + }); + + it("resolves safe dispatch data recursively", async () => { + const service = app.service("messages"); + const context = await service.get( + 0, + {}, + createContext(service as any, "get"), + ); + + assertStrictEquals(context.result.user.password, "hashed"); + + assertEquals(context.dispatch, { + text: "Hi there", + userId: 0, + id: 0, + user: { + id: 0, + email: "[redacted]", + name: "hello (hello@feathersjs.com)", + }, + }); + }); + + it("validates and converts the query", async () => { + const otherUser = await app.service("users").create({ + email: "helloagain@feathersjs.com", + password: "supersecret", + }); + + await app.service("messages").create({ + text, + userId: otherUser.id, + }); + + const messages = await app.service("messages").find({ + paginate: false, + query: { + userId: `${user.id}`, + }, + }); + + assertStrictEquals(messages.length, 1); + + const userMessages = await app.service("messages").find({ + paginate: false, + user, + }); + + assertStrictEquals(userMessages.length, 1); + assertStrictEquals(userMessages[0].userId, user.id); + + const msg = await app.service("messages").get(userMessages[0].id, { + query: { + $resolve: ["user"], + }, + }); + + // @ts-ignore + assertEquals(msg, { + user, + }); + + const error = await assertRejects( + () => + app.service("messages").find({ + query: { + thing: "me", + }, + }), + + ); + + assertEquals(error, + { + name: "BadRequest", + message: "validation failed", + code: 400, + className: "bad-request", + data: [ + { + instancePath: "", + schemaPath: "#/additionalProperties", + keyword: "additionalProperties", + params: { additionalProperty: "thing" }, + message: "must NOT have additional properties", + }, + ], + },) + }); +}); diff --git a/main/schema/test/resolver.test.ts b/main/schema/test/resolver.test.ts new file mode 100644 index 0000000000..cac7edcadd --- /dev/null +++ b/main/schema/test/resolver.test.ts @@ -0,0 +1,185 @@ +// deno-lint-ignore-file require-await +import { + describe, + it, + assertStrictEquals, + assertRejects, + assertEquals +} from "../../commons/mod.ts"; +import { BadRequest } from "../../errors/mod.ts"; + +import { Infer, resolve, schema } from "../mod.ts"; + +describe("@feathersjs/schema/resolver", () => { + const userSchema = schema( + { + $id: "simple-user", + type: "object", + required: ["firstName", "lastName"], + additionalProperties: false, + properties: { + firstName: { type: "string" }, + lastName: { type: "string" }, + password: { type: "string" }, + }, + } as const, + ); + const context = { + isContext: true, + }; + + type User = Infer & { + name: string; + }; + + it("simple resolver", async () => { + const userResolver = resolve({ + properties: { + password: async (): Promise => { + return undefined; + }, + + name: async (_name, user, ctx, status) => { + assertEquals(ctx, context); + assertEquals(status.path, ["name"]); + assertStrictEquals(typeof status.stack[0], "function"); + + return `${user.firstName} ${user.lastName}`; + }, + }, + }); + + const u = await userResolver.resolve( + { + firstName: "Dave", + lastName: "L.", + }, + context, + ); + + assertEquals(u, { + firstName: "Dave", + lastName: "L.", + name: "Dave L.", + }); + + const withProps: any = await userResolver.resolve( + { + firstName: "David", + lastName: "L", + }, + context, + { + properties: ["name", "lastName"], + }, + ); + + assertEquals(withProps, { + name: "David L", + lastName: "L", + }); + }); + + it("simple resolver with schema and validation", async () => { + const userBeforeResolver = resolve({ + schema: userSchema, + validate: "before", + properties: { + name: async (_name, user) => `${user.firstName} ${user.lastName}`, + }, + }); + const userAfterResolver = resolve({ + schema: userSchema, + validate: "after", + properties: { + firstName: async () => undefined, + }, + }); + + await assertRejects(() => userBeforeResolver.resolve({}, context),"validation failed"); + await assertRejects( + () => + userAfterResolver.resolve( + { + firstName: "Test", + lastName: "Me", + }, + context, + ), + "validation failed", + ); + }); + + it("simple resolver with converter", async () => { + const userConverterResolver = resolve({ + schema: userSchema, + validate: "before", + converter: async (data) => ({ + firstName: "Default", + lastName: "Name", + ...data, + }), + properties: { + name: async (_name, user) => `${user.firstName} ${user.lastName}`, + }, + }); + + const u = await userConverterResolver.resolve({}, context); + + assertEquals(u, { + firstName: "Default", + lastName: "Name", + name: "Default Name", + }); + }); + + it("resolving with errors", async () => { + const dummyResolver = resolve<{ + name: string; age: number + }, unknown>({ + properties: { + name: async (value?: string) => { + if (value === "Dave") { + throw new Error(`No ${value}s allowed`); + } + + return value; + }, + age: async (value) => { + if (value && value < 18) { + throw new BadRequest("Invalid age"); + } + + return value; + }, + }, + }); + + const error = await assertRejects( + () => + dummyResolver.resolve( + { + name: "Dave", + age: 16, + }, + {}, + ), + ); + + assertEquals(error, { + name: "BadRequest", + message: "Error resolving data", + code: 400, + className: "bad-request", + data: { + name: { message: "No Daves allowed" }, + age: { + name: "BadRequest", + message: "Invalid age", + code: 400, + className: "bad-request", + }, + }, + },) + }); +}); diff --git a/main/schema/test/schema.test.ts b/main/schema/test/schema.test.ts new file mode 100644 index 0000000000..92639f99b5 --- /dev/null +++ b/main/schema/test/schema.test.ts @@ -0,0 +1,363 @@ +import { + describe, + it, + assertStrictEquals, + assertRejects, + assertEquals, +assert, +assertInstanceOf +} from "../../commons/mod.ts"; + +import { Infer, queryProperty, schema } from "../mod.ts"; +import Ajv, { AnySchemaObject } from "https://esm.sh/ajv@8.11.0"; +import addFormats from "https://esm.sh/ajv-formats@2.1.1"; + +const customAjv = new Ajv({ + coerceTypes: true, +}); +addFormats(customAjv); + +// Utility for converting "date" and "date-time" string formats into Dates. +customAjv.addKeyword({ + keyword: "convert", + type: "string", + compile(schemaVal: boolean, parentSchema: AnySchemaObject) { + return ["date-time", "date"].includes(parentSchema.format) && schemaVal + ? function (value: string, obj: any) { + const { parentData, parentDataProperty } = obj; + // Update date-time string to Date object + parentData[parentDataProperty] = new Date(value); + return true; + } + : () => true; + }, +}); + +describe("@feathersjs/schema/schema", () => { + it("type inference and validation", async () => { + const messageSchema = schema( + { + $id: "message-test", + type: "object", + required: ["text", "read"], + additionalProperties: false, + properties: { + text: { + type: "string", + }, + read: { + type: "boolean", + }, + upvotes: { + type: "number", + }, + }, + } as const, + ); + type Message = Infer; + + const message = await messageSchema.validate({ + text: "hi", + read: 0, + upvotes: "10", + }); + + assertEquals(messageSchema.toJSON(), messageSchema.definition); + assertEquals(message, { + text: "hi", + read: false, + upvotes: 10, + }); + + const error = await assertRejects(() => messageSchema.validate({ text: "failing" })); + + assertEquals(error, { + name: "BadRequest", + data: [ + { + instancePath: "", + keyword: "required", + message: "must have required property 'read'", + params: { + missingProperty: "read", + }, + schemaPath: "#/required", + }, + ], + }); + }); + + it("uses custom AJV with format validation", async () => { + const formatsSchema = schema( + { + $id: "formats-test", + type: "object", + required: [], + additionalProperties: false, + properties: { + dobString: { + type: "string", + format: "date", + }, + createdAt: { + type: "string", + format: "date-time", + }, + }, + } as const, + customAjv, + ); + + await formatsSchema.validate({ + createdAt: "2021-12-22T23:59:59.999Z", + }); + + try { + await formatsSchema.validate({ + createdAt: "2021-12-22T23:59:59.bbb", + }); + } catch (error: any) { + assertStrictEquals(error.data[0].message, 'must match format "date-time"'); + } + }); + + it("custom AJV can convert dates", async () => { + const formatsSchema = schema( + { + $id: "converts-formats-test", + type: "object", + required: [], + additionalProperties: false, + properties: { + dobString: queryProperty({ + type: "string", + format: "date", + convert: true, + }), + createdAt: { + type: "string", + format: "date-time", + convert: true, + }, + }, + } as const, + customAjv, + ); + + const validated = await formatsSchema.validate({ + dobString: { $gt: "2025-04-25" }, + createdAt: "2021-12-22T23:59:59.999Z", + }); + + assertInstanceOf((validated.dobString as any).$gt, Date); + assertInstanceOf((validated.createdAt as any), Date); + }); + + it("schema extension and type inference", async () => { + const messageSchema = schema( + { + $id: "message-ext", + type: "object", + required: ["text", "read"], + additionalProperties: false, + properties: { + text: { + type: "string", + }, + read: { + type: "boolean", + }, + }, + } as const, + ); + + const messageResultSchema = schema( + { + $id: "message-ext-vote", + type: "object", + required: ["upvotes", ...messageSchema.definition.required], + additionalProperties: false, + properties: { + ...messageSchema.definition.properties, + upvotes: { + type: "number", + }, + }, + } as const, + ); + + type MessageResult = Infer; + + const m = await messageResultSchema.validate({ + text: "Hi", + read: "false", + upvotes: "23", + }); + + assertEquals(m, { + text: "Hi", + read: false, + upvotes: 23, + }); + }); + + it("with references", async () => { + const userSchema = schema( + { + $id: "ref-user", + type: "object", + required: ["email"], + additionalProperties: false, + properties: { + email: { type: "string" }, + age: { type: "number" }, + }, + } as const, + customAjv, + ); + const messageSchema = schema( + { + $id: "ref-message", + type: "object", + required: ["text", "user"], + additionalProperties: false, + properties: { + text: { + type: "string", + }, + user: { + $ref: "ref-user", + }, + }, + } as const, + customAjv, + ); + + type User = Infer; + type Message = Infer & { + user: User; + }; + + const res = await messageSchema.validate({ + text: "Hello", + user: { + email: "hello@feathersjs.com", + age: "42", + }, + }); + + assert(userSchema); + assertEquals(res, { + text: "Hello", + user: { email: "hello@feathersjs.com", age: 42 }, + }); + }); + + it("works with oneOf properties (#2508)", async () => { + const oneOfSchema = schema( + { + $id: "schemaA", + oneOf: [ + { + type: "object", + additionalProperties: false, + required: ["x"], + properties: { + x: { type: "number" }, + }, + }, + { + type: "object", + additionalProperties: false, + required: ["y"], + properties: { + y: { type: "number" }, + }, + }, + ], + } as const, + ); + + const res = await oneOfSchema.validate({ + x: "3", + }); + + assertEquals(res, { x: 3 }); + }); + + it("can handle compound queryProperty", async () => { + const formatsSchema = schema( + { + $id: "compoundQueryProperty", + type: "object", + required: [], + additionalProperties: false, + properties: { + dobString: queryProperty({ + oneOf: [ + { type: "string", format: "date", convert: true }, + { type: "string", format: "date-time", convert: true }, + { type: "object" }, + ], + }), + }, + } as const, + customAjv, + ); + + const validated = await formatsSchema.validate({ + dobString: { $gt: "2025-04-25", $lte: new Date("2027-04-25") }, + }); + + assert(validated); + }); + + it("can still fail queryProperty validation", async () => { + const formatsSchema = schema( + { + $id: "compoundQueryPropertyFail", + type: "object", + required: [], + additionalProperties: false, + properties: { + dobString: queryProperty({ type: "string" }), + }, + } as const, + customAjv, + ); + + try { + const validated = await formatsSchema.validate({ + dobString: { $moose: "test" }, + }); + assert(!validated, "should not have gotten here"); + } catch (error: any) { + assert(error.data?.length > 0); + } + }); + + it("removes default from queryProperty schemas like $gt", async () => { + const validator = schema( + { + $id: "noDefault$gt", + type: "object", + required: [], + additionalProperties: false, + properties: { + someDate: queryProperty({ default: "0000-00-00", type: "string" }), + }, + } as const, + customAjv, + ); + + assertStrictEquals( + validator.definition.properties.someDate.anyOf[1].properties.$gt.type, + "string", + "type is found under $gt", + ); + assert( + !validator.definition.properties.someDate.anyOf[1].properties.$gt.default, + "no default under $gt", + ); + }); +}); diff --git a/main/transport-commons/LICENSE b/main/transport-commons/LICENSE new file mode 100644 index 0000000000..59604f46f3 --- /dev/null +++ b/main/transport-commons/LICENSE @@ -0,0 +1,22 @@ +The MIT License (MIT) + +Copyright (c) 2022 Feathers + +Permission is hereby granted, free of charge, to any person obtaining a copy +of this software and associated documentation files (the "Software"), to deal +in the Software without restriction, including without limitation the rights +to use, copy, modify, merge, publish, distribute, sublicense, and/or sell +copies of the Software, and to permit persons to whom the Software is +furnished to do so, subject to the following conditions: + +The above copyright notice and this permission notice shall be included in all +copies or substantial portions of the Software. + +THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE +AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, +OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE +SOFTWARE. + diff --git a/main/transport-commons/README.md b/main/transport-commons/README.md new file mode 100644 index 0000000000..61654ed288 --- /dev/null +++ b/main/transport-commons/README.md @@ -0,0 +1,15 @@ +# @feathersjs/transport-commons + +[![CI](https://github.com/feathersjs/feathers/workflows/CI/badge.svg)](https://github.com/feathersjs/feathers/actions?query=workflow%3ACI) +[![Download Status](https://img.shields.io/npm/dm/@feathersjs/transport-commons.svg?style=flat-square)](https://www.npmjs.com/package/@feathersjs/transport-commons) +[![Discord](https://badgen.net/badge/icon/discord?icon=discord&label)](https://discord.gg/qa8kez8QBx) + +> Shared functionality for Feathers API transports like `@feathers/socketio` and +> `@feathersjs/primus`. Only intended to be used internally. + +## License + +Copyright (c) 2022 +[Feathers contributors](https://github.com/feathersjs/feathers/graphs/contributors) + +Licensed under the [MIT license](LICENSE). diff --git a/main/transport-commons/mod.ts b/main/transport-commons/mod.ts new file mode 100644 index 0000000000..401c73ac2a --- /dev/null +++ b/main/transport-commons/mod.ts @@ -0,0 +1 @@ +export * from "./src/index.ts"; diff --git a/main/transport-commons/src/channels/channel/base.ts b/main/transport-commons/src/channels/channel/base.ts new file mode 100644 index 0000000000..69ac091a42 --- /dev/null +++ b/main/transport-commons/src/channels/channel/base.ts @@ -0,0 +1,61 @@ +import { EventEmitter } from "../../../../commons/mod.ts"; + +export interface RealTimeConnection { + [key: string]: any; +} + +export class Channel extends EventEmitter { + connections: RealTimeConnection[]; + data: any; + + constructor(connections: RealTimeConnection[] = [], data: any = null) { + super(); + + this.connections = connections; + this.data = data; + } + + get length() { + return this.connections.length; + } + + leave(...connections: RealTimeConnection[]) { + connections.forEach((current) => { + if (typeof current === "function") { + const callback = current as (connection: RealTimeConnection) => boolean; + + this.leave(...this.connections.filter(callback)); + } else { + const index = this.connections.indexOf(current); + + if (index !== -1) { + this.connections.splice(index, 1); + } + } + }); + + if (this.length === 0) { + this.emit("empty"); + } + + return this; + } + + join(...connections: RealTimeConnection[]) { + connections.forEach((connection) => { + if (connection && this.connections.indexOf(connection) === -1) { + this.connections.push(connection); + } + }); + + return this; + } + + filter(fn: (connection: RealTimeConnection) => boolean) { + return new Channel(this.connections.filter(fn), this.data); + } + + send(data: any) { + return new Channel(this.connections, data); + } +} diff --git a/main/transport-commons/src/channels/channel/combined.ts b/main/transport-commons/src/channels/channel/combined.ts new file mode 100644 index 0000000000..d6bd8fe165 --- /dev/null +++ b/main/transport-commons/src/channels/channel/combined.ts @@ -0,0 +1,56 @@ +import { Channel, RealTimeConnection } from "./base.ts"; + +function collectConnections(children: Channel[]) { + const mappings = new WeakMap(); + const connections: RealTimeConnection[] = []; + + children.forEach((channel) => { + channel.connections.forEach((connection) => { + if (!mappings.has(connection)) { + connections.push(connection); + mappings.set(connection, channel.data); + } + }); + }); + + return { connections, mappings }; +} + +export class CombinedChannel extends Channel { + children: Channel[]; + mappings: WeakMap; + + constructor(children: Channel[], data: any = null) { + const { mappings, connections } = collectConnections(children); + + super(connections, data); + + this.children = children; + this.mappings = mappings; + } + + refresh() { + const collected = collectConnections(this.children); + + return Object.assign(this, collected); + } + + leave(...connections: RealTimeConnection[]) { + return this.callChildren("leave", connections); + } + + join(...connections: RealTimeConnection[]) { + return this.callChildren("join", connections); + } + + dataFor(connection: RealTimeConnection) { + return this.mappings.get(connection); + } + + private callChildren(method: string, connections: RealTimeConnection[]) { + this.children.forEach((child: any) => child[method](...connections)); + this.refresh(); + + return this; + } +} diff --git a/main/transport-commons/src/channels/index.ts b/main/transport-commons/src/channels/index.ts new file mode 100644 index 0000000000..8bdc58872c --- /dev/null +++ b/main/transport-commons/src/channels/index.ts @@ -0,0 +1,142 @@ +import { + FeathersService, + getServiceOptions, +} from "../../../feathers/mod.ts"; +import { Application } from "../../../feathers/src/declarations.ts"; +import { createDebug } from "../../../commons/mod.ts"; +import { lodash } from "https://deno.land/x/deno_ts_lodash@0.0.1/mod.ts"; +import { Channel, RealTimeConnection } from "./channel/base.ts"; +import { CombinedChannel } from "./channel/combined.ts"; +import { + channelMixin, + Event, + keys, + Publisher, + PublishMixin, + publishMixin, +} from "./mixins.ts"; +import { EventEmitter } from "../../../commons/mod.ts"; + +const debug = createDebug("@feathersjs/transport-commons/channels"); +const { CHANNELS } = keys; + +declare module "../../../feathers/src/declarations.ts" { + interface ServiceAddons extends EventEmitter { + publish(publisher: Publisher, A, this>): this; + publish( + event: Event, + publisher: Publisher, A, this>, + ): this; + + registerPublisher( + publisher: Publisher, A, this>, + ): this; + registerPublisher( + event: Event, + publisher: Publisher, A, this>, + ): this; + } + + interface Application { + channels: string[]; + + channel(name: string | string[]): Channel; + channel(...names: string[]): Channel; + + publish(publisher: Publisher): this; + publish(event: Event, publisher: Publisher): this; + + registerPublisher(publisher: Publisher): this; + registerPublisher(event: Event, publisher: Publisher): this; + } + + interface Params { + connection?: RealTimeConnection; + } +} + +export { keys }; + +export function channels() { + return (app: Application) => { + if ( + typeof app.channel === "function" && typeof app.publish === "function" + ) { + return; + } + + Object.assign(app, channelMixin(), publishMixin()); + Object.defineProperty(app, "channels", { + get() { + return Object.keys(this[CHANNELS]); + }, + }); + + app.mixins.push((service: FeathersService, path: string) => { + const { serviceEvents } = getServiceOptions(service); + + if (typeof service.publish === "function") { + return; + } + + Object.assign(service, publishMixin()); + + serviceEvents?.forEach((event: string) => { + service.on(event, function (data: any, hook?: any) { + if (!hook) { + // Fake hook for custom events + hook = { path, service, app, result: data }; + } + + debug("Publishing event", event, hook!.path); + + const logError = (error: any) => + debug(`Error in '${hook!.path} ${event}' publisher`, error); + const servicePublishers = + (service as unknown as PublishMixin)[keys.PUBLISHERS]; + const appPublishers = + (app as unknown as PublishMixin)[keys.PUBLISHERS]; + // This will return the first publisher list that is not empty + // In the following precedence + const publisher = + // 1. Service publisher for a specific event + servicePublishers[event] || + // 2. Service publisher for all events + servicePublishers[keys.ALL_EVENTS] || + // 3. App publisher for a specific event + appPublishers[event] || + // 4. App publisher for all events + appPublishers[keys.ALL_EVENTS] || + // 5. No publisher + lodash.noop; + + try { + Promise.resolve(publisher(data, hook!)) + .then((result: any) => { + if (!result) { + return; + } + + const results = Array.isArray(result) + ? lodash.compact(result.flat()) + : ([result] as Channel[]); + const channel = new CombinedChannel(results); + + if (channel && channel.length > 0) { + app.emit("publish", event, channel, hook, data); + } else { + debug("No connections to publish to"); + } + }) + .catch(logError); + } catch (error: any) { + logError(error); + } + }); + }); + }); + }; +} + +export { Channel, CombinedChannel }; +export type { RealTimeConnection }; diff --git a/main/transport-commons/src/channels/mixins.ts b/main/transport-commons/src/channels/mixins.ts new file mode 100644 index 0000000000..583f8865ec --- /dev/null +++ b/main/transport-commons/src/channels/mixins.ts @@ -0,0 +1,111 @@ +import { + Application, + getServiceOptions, + HookContext, +} from "../../../feathers/mod.ts"; +import { createDebug } from "../../../commons/mod.ts"; +import { Channel } from "./channel/base.ts"; +import { CombinedChannel } from "./channel/combined.ts"; + +const debug = createDebug("@feathersjs/transport-commons/channels/mixins"); +const PUBLISHERS = Symbol("@feathersjs/transport-commons/publishers"); +const CHANNELS = Symbol("@feathersjs/transport-commons/channels"); +const ALL_EVENTS = Symbol("@feathersjs/transport-commons/all-events"); + +export const keys = { + PUBLISHERS: PUBLISHERS as typeof PUBLISHERS, + CHANNELS: CHANNELS as typeof CHANNELS, + ALL_EVENTS: ALL_EVENTS as typeof ALL_EVENTS, +}; + +export interface ChannelMixin { + [CHANNELS]: { [key: string]: Channel }; + channel(...names: string[]): Channel; +} + +export function channelMixin() { + const mixin: ChannelMixin = { + [CHANNELS]: {}, + + channel(...names: string[]): Channel { + debug("Returning channels", names); + + if (names.length === 0) { + throw new Error("app.channel needs at least one channel name"); + } + + if (names.length === 1) { + const [name] = names; + + if (Array.isArray(name)) { + return this.channel(...name); + } + + if (!this[CHANNELS][name]) { + const channel = new Channel(); + + channel.once("empty", () => { + channel.removeAllListeners(); + delete this[CHANNELS][name]; + }); + + this[CHANNELS][name] = channel; + } + + return this[CHANNELS][name]; + } + + const channels = names.map((name) => this.channel(name)); + + return new CombinedChannel(channels); + }, + }; + + return mixin; +} + +export type Event = string | typeof ALL_EVENTS; + +export type Publisher = ( + data: T, + context: HookContext, +) => Channel | Channel[] | void | Promise; + +export interface PublishMixin { + [PUBLISHERS]: { [ALL_EVENTS]?: Publisher; [key: string]: Publisher }; + publish(event: Event, publisher: Publisher): this; + registerPublisher(event: Event, publisher: Publisher): this; +} + +export function publishMixin() { + const result: PublishMixin = { + [PUBLISHERS]: {}, + + publish(...args) { + return this.registerPublisher(...args); + }, + + registerPublisher(event, publisher) { + debug("Registering publisher", event); + + if (!publisher && typeof event === "function") { + publisher = event; + event = ALL_EVENTS; + } + + const { serviceEvents } = getServiceOptions(this); + + if (event !== ALL_EVENTS && !serviceEvents?.includes(event)) { + throw new Error(`'${event.toString()}' is not a valid service event`); + } + + const publishers = this[PUBLISHERS]; + + publishers[event] = publisher; + + return this; + }, + }; + + return result; +} diff --git a/main/transport-commons/src/client.ts b/main/transport-commons/src/client.ts new file mode 100644 index 0000000000..97c1b74622 --- /dev/null +++ b/main/transport-commons/src/client.ts @@ -0,0 +1,161 @@ +import { convert } from "../../errors/mod.ts"; +import { createDebug } from "../../commons/mod.ts"; +import { + Id, + NullableId, + Params, + ServiceInterface, +} from "../../feathers/mod.ts"; + +const debug = createDebug("@feathersjs/transport-commons/client"); + +const namespacedEmitterMethods = [ + "addListener", + "addEventListener", + "emit", + "listenerCount", + "listeners", + "on", + "once", + "prependListener", + "prependOnceListener", + "removeAllListeners", + "removeEventListener", + "removeListener", +]; +const otherEmitterMethods = [ + "eventNames", + "getMaxListeners", + "setMaxListeners", +]; + +const addEmitterMethods = (service: any) => { + otherEmitterMethods.forEach((method) => { + service[method] = function (...args: any[]) { + if (typeof this.connection[method] !== "function") { + throw new Error( + `Can not call '${method}' on the client service connection`, + ); + } + + return this.connection[method](...args); + }; + }); + + // Methods that should add the namespace (service path) + namespacedEmitterMethods.forEach((method) => { + service[method] = function (name: string, ...args: any[]) { + if (typeof this.connection[method] !== "function") { + throw new Error( + `Can not call '${method}' on the client service connection`, + ); + } + + const eventName = `${this.path} ${name}`; + + debug( + `Calling emitter method ${method} with ` + + `namespaced event '${eventName}'`, + ); + + const result = this.connection[method](eventName, ...args); + + return result === this.connection ? this : result; + }; + }); +}; + +interface ServiceOptions { + name: string; + connection: any; + method: string; + events?: string[]; +} + +export type SocketService< + T = any, + D = Partial, + P extends Params = Params, +> = Service; + +export class Service, P extends Params = Params> + implements ServiceInterface { + events: string[]; + path: string; + connection: any; + method: string; + + constructor(options: ServiceOptions) { + this.events = options.events || []; + this.path = options.name; + this.connection = options.connection; + this.method = options.method; + + addEmitterMethods(this); + } + + send(method: string, ...args: any[]) { + return new Promise((resolve, reject) => { + args.unshift(method, this.path); + + args.push(function (error: any, data: any) { + return error ? reject(convert(error)) : resolve(data); + }); + + debug(`Sending socket.${this.method}`, args); + + this.connection[this.method](...args); + }); + } + + methods(this: any, ...names: string[]) { + names.forEach((name) => { + this[name] = function (data: any, params: Params = {}) { + return this.send(name, data, params.query || {}); + }; + }); + + return this; + } + + find(params: Params = {}) { + return this.send("find", params.query || {}); + } + + get(id: Id, params: Params = {}) { + return this.send("get", id, params.query || {}); + } + + create(data: any, params: Params = {}) { + return this.send("create", data, params.query || {}); + } + + update(id: Id, data: any, params: Params = {}) { + return this.send("update", id, data, params.query || {}); + } + + patch(id: NullableId, data: any, params: Params = {}) { + return this.send("patch", id, data, params.query || {}); + } + + remove(id: NullableId, params: Params = {}) { + return this.send("remove", id, params.query || {}); + } + + // `off` is actually not part of the Node event emitter spec + // but we are adding it since everybody is expecting it because + // of the emitter-component Socket.io is using + off(name: string, ...args: any[]) { + if (typeof this.connection.off === "function") { + const result = this.connection.off(`${this.path} ${name}`, ...args); + + return result === this.connection ? this : result; + } else if (args.length === 0) { + // @ts-ignore + return this.removeAllListeners(name); + } + + // @ts-ignore + return this.removeListener(name, ...args); + } +} diff --git a/main/transport-commons/src/http.ts b/main/transport-commons/src/http.ts new file mode 100644 index 0000000000..c62a85e7ef --- /dev/null +++ b/main/transport-commons/src/http.ts @@ -0,0 +1,104 @@ +import { MethodNotAllowed } from "../../errors/mod.ts"; +import { HookContext, NullableId, Params } from "../../feathers/mod.ts"; + +export const METHOD_HEADER = "x-service-method"; + +export interface ServiceParams { + id: NullableId; + data: any; + params: Params; +} + +export const statusCodes = { + created: 201, + noContent: 204, + methodNotAllowed: 405, + success: 200, + seeOther: 303, +}; + +export const knownMethods: { [key: string]: string } = { + post: "create", + patch: "patch", + put: "update", + delete: "remove", +}; + +export function getServiceMethod( + _httpMethod: string, + id: unknown, + headerOverride?: string, +) { + const httpMethod = _httpMethod.toLowerCase(); + + if (httpMethod === "post" && headerOverride) { + return headerOverride; + } + + const mappedMethod = knownMethods[httpMethod]; + + if (mappedMethod) { + return mappedMethod; + } + + if (httpMethod === "get") { + return id === null ? "find" : "get"; + } + + throw new MethodNotAllowed(`Method ${_httpMethod} not allowed`); +} + +export const argumentsFor = { + get: ({ id, params }: ServiceParams) => [id, params], + find: ({ params }: ServiceParams) => [params], + create: ({ data, params }: ServiceParams) => [data, params], + update: ({ id, data, params }: ServiceParams) => [id, data, params], + patch: ({ id, data, params }: ServiceParams) => [id, data, params], + remove: ({ id, params }: ServiceParams) => [id, params], + default: ({ data, params }: ServiceParams) => [data, params], +}; + +export function getStatusCode( + context: HookContext, + body: any, + location: string | string[], +) { + const { http = {} } = context; + + if (http.status) { + return http.status; + } + + if (context.method === "create") { + return statusCodes.created; + } + + if (location !== undefined) { + return statusCodes.seeOther; + } + + if (!body) { + return statusCodes.noContent; + } + + return statusCodes.success; +} + +export function getResponse(context: HookContext) { + const { http = {} } = context; + const body = context.dispatch !== undefined + ? context.dispatch + : context.result; + + let headers = http.headers || {}; + let location = headers.Location; + + if (http.location !== undefined) { + location = encodeURI(http.location); + headers = { ...headers, Location: location }; + } + + const status = getStatusCode(context, body, location); + + return { status, headers, body }; +} diff --git a/main/transport-commons/src/index.ts b/main/transport-commons/src/index.ts new file mode 100644 index 0000000000..e789daa5df --- /dev/null +++ b/main/transport-commons/src/index.ts @@ -0,0 +1,12 @@ +import { socket } from "./socket/index.ts"; +import { routing } from "./routing/index.ts"; +import { + Channel, + channels, + CombinedChannel, + RealTimeConnection, +} from "./channels/index.ts"; + +export * as http from "./http.ts"; +export { Channel, channels, CombinedChannel, routing, socket }; +export type { RealTimeConnection }; diff --git a/main/transport-commons/src/routing/index.ts b/main/transport-commons/src/routing/index.ts new file mode 100644 index 0000000000..93f9e4920b --- /dev/null +++ b/main/transport-commons/src/routing/index.ts @@ -0,0 +1,68 @@ +import { + // Application, + FeathersService, + ServiceOptions, + // type Service +} from "../../../feathers/mod.ts"; +import { Application } from "../../../feathers/src/declarations.ts"; +import { Router } from "./router.ts"; + +export * from "./router.ts"; + +declare module "../../../feathers/src/declarations.ts" { + interface RouteLookup { + service: Service; + params: { [key: string]: any }; + } + + interface Application { + routes: Router<{ + service: Service; + params?: { [key: string]: any }; + }>; + lookup(path: string): RouteLookup | null; + } +} + +const lookup = function (this: Application, path: string) { + const result = this.routes.lookup(path); + + if (result === null) { + return null; + } + + const { + params: colonParams, + data: { service, params: dataParams }, + } = result; + + const params = dataParams ? { ...dataParams, ...colonParams } : colonParams; + + return { service, params }; +}; + +export const routing = () => (app: Application) => { + if (typeof app.lookup === "function") { + return; + } + + const { unuse } = app; + + app.routes = new Router(); + app.lookup = lookup; + app.unuse = function (path: string) { + app.routes.remove(path); + app.routes.remove(`${path}/:__id`); + return unuse.call(this, path); + }; + + // Add a mixin that registers a service on the router + app.mixins.push( + (service: FeathersService, path: string, options: ServiceOptions) => { + const { routeParams: params = {} } = options; + + app.routes.insert(path, { service, params }); + app.routes.insert(`${path}/:__id`, { service, params }); + }, + ); +}; diff --git a/main/transport-commons/src/routing/router.ts b/main/transport-commons/src/routing/router.ts new file mode 100644 index 0000000000..9e7426f841 --- /dev/null +++ b/main/transport-commons/src/routing/router.ts @@ -0,0 +1,140 @@ +import { stripSlashes } from "../../../commons/mod.ts"; + +export interface LookupData { + params: { [key: string]: string }; +} + +export interface LookupResult extends LookupData { + data: T; +} + +export class RouteNode { + data?: T; + children: { [key: string]: RouteNode } = {}; + placeholders: RouteNode[] = []; + + constructor(public name: string, public depth: number) {} + + get hasChildren() { + return Object.keys(this.children).length !== 0 || + this.placeholders.length !== 0; + } + + insert(path: string[], data: T): RouteNode { + if (this.depth === path.length) { + if (this.data !== undefined) { + throw new Error(`Path ${path.join("/")} already exists`); + } + + this.data = data; + return this; + } + + const current = path[this.depth]; + const nextDepth = this.depth + 1; + + if (current.startsWith(":")) { + // Insert a placeholder node like /messages/:id + const placeholderName = current.substring(1); + let placeholder = this.placeholders.find((p) => + p.name === placeholderName + ); + + if (!placeholder) { + placeholder = new RouteNode(placeholderName, nextDepth); + this.placeholders.push(placeholder); + } + + return placeholder.insert(path, data); + } + + const child = this.children[current] || new RouteNode(current, nextDepth); + + this.children[current] = child; + + return child.insert(path, data); + } + + remove(path: string[]) { + if (path.length === this.depth) { + return; + } + + const current = path[this.depth]; + + if (current.startsWith(":")) { + const placeholderName = current.substring(1); + const placeholder = this.placeholders.find((p) => + p.name === placeholderName + ); + + placeholder?.remove(path); + + this.placeholders = this.placeholders.filter((p) => p !== placeholder); + } else if (this.children[current]) { + const child = this.children[current]; + + child.remove(path); + + if (!child.hasChildren) { + delete this.children[current]; + } + } + } + + lookup(path: string[], info: LookupData): LookupResult | null { + if (path.length === this.depth) { + return this.data === undefined ? null : { + ...info, + data: this.data, + }; + } + + const current = path[this.depth]; + const child = this.children[current]; + + if (child) { + const lookup = child.lookup(path, info); + + if (lookup !== null) { + return lookup; + } + } + + // This will return the first placeholder that matches early + for (const placeholder of this.placeholders) { + const result = placeholder.lookup(path, info); + + if (result !== null) { + result.params[placeholder.name] = current; + return result; + } + } + + return null; + } +} + +export class Router { + constructor(public root: RouteNode = new RouteNode("", 0)) {} + + getPath(path: string) { + return stripSlashes(path).split("/"); + } + + insert(path: string, data: T) { + return this.root.insert(this.getPath(path), data); + } + + remove(path: string) { + return this.root.remove(this.getPath(path)); + } + + lookup(path: string) { + if (typeof path !== "string") { + return null; + } + + return this.root.lookup(this.getPath(path), { params: {} }); + } +} diff --git a/main/transport-commons/src/socket/index.ts b/main/transport-commons/src/socket/index.ts new file mode 100644 index 0000000000..35c2f3c456 --- /dev/null +++ b/main/transport-commons/src/socket/index.ts @@ -0,0 +1,84 @@ +import { + Application, + getServiceOptions, + Params, +} from "../../../feathers/mod.ts"; +import { createDebug } from "../../../commons/mod.ts"; +import { channels } from "../channels/index.ts"; +import { routing } from "../routing/index.ts"; +import { getDispatcher, runMethod } from "./utils.ts"; +import { RealTimeConnection } from "../channels/channel/base.ts"; + +const debug = createDebug("@feathersjs/transport-commons"); + +export interface SocketOptions { + done: Promise; + emit: string; + socketMap: WeakMap; + socketKey?: any; + getParams: (socket: any) => RealTimeConnection; +} + +export function socket( + { done, emit, socketMap, socketKey, getParams }: SocketOptions, +) { + return (app: Application) => { + const leaveChannels = (connection: RealTimeConnection) => { + const { channels } = app; + + if (channels.length) { + app.channel(app.channels).leave(connection); + } + }; + + app.configure(channels()); + app.configure(routing()); + + app.on("publish", getDispatcher(emit, socketMap, socketKey)); + app.on("disconnect", leaveChannels); + app.on("logout", (_authResult: any, params: Params) => { + const { connection } = params; + + if (connection) { + leaveChannels(connection); + } + }); + + // `connection` event + done.then((provider) => + provider.on( + "connection", + (connection: any) => app.emit("connection", getParams(connection)), + ) + ); + + // `socket.emit('methodName', 'serviceName', ...args)` handlers + done.then((provider) => + provider.on("connection", (connection: any) => { + const methodHandlers = Object.keys(app.services).reduce( + (result, name) => { + const { methods } = getServiceOptions(app.service(name)); + + methods?.forEach((method) => { + if (!result[method]) { + result[method] = (...args: any[]) => { + const path = args.shift(); + + debug(`Got '${method}' call for service '${path}'`); + runMethod(app, getParams(connection), path, method, args); + }; + } + }); + + return result; + }, + {} as any, + ); + + Object.keys(methodHandlers).forEach((key) => + connection.on(key, methodHandlers[key]) + ); + }) + ); + }; +} diff --git a/main/transport-commons/src/socket/utils.ts b/main/transport-commons/src/socket/utils.ts new file mode 100644 index 0000000000..c15f4cc5fe --- /dev/null +++ b/main/transport-commons/src/socket/utils.ts @@ -0,0 +1,153 @@ +import { + Application, + createContext, + getServiceOptions, + HookContext, +} from "../../../feathers/mod.ts"; +import { BadRequest, MethodNotAllowed, NotFound } from "../../../errors/mod.ts"; +import { createDebug } from "../../../commons/mod.ts"; +import { lodash } from "https://deno.land/x/deno_ts_lodash@0.0.1/mod.ts"; +import { CombinedChannel } from "../channels/channel/combined.ts"; +import { RealTimeConnection } from "../channels/channel/base.ts"; + +const debug = createDebug("@feathersjs/transport-commons"); + +export const DEFAULT_PARAMS_POSITION = 1; + +export const paramsPositions: { [key: string]: number } = { + find: 0, + update: 2, + patch: 2, +}; + +export function normalizeError(e: any) { + const hasToJSON = typeof e.toJSON === "function"; + const result = hasToJSON ? e.toJSON() : {}; + + if (!hasToJSON) { + Object.getOwnPropertyNames(e).forEach((key) => { + result[key] = e[key]; + }); + } + + // @TODO how to tell if we are in production mode in Deno? NODE_ENV is, of course, a NODE / express way to do it + // if (process.env.NODE_ENV === "production") { + delete result.stack; + // } + + delete result.hook; + + return result; +} + +export function getDispatcher( + emit: string, + socketMap: WeakMap, + socketKey?: any, +) { + return function ( + event: string, + channel: CombinedChannel, + context: HookContext, + data?: any, + ) { + debug(`Dispatching '${event}' to ${channel.length} connections`); + + channel.connections.forEach((connection) => { + // The reference between connection and socket is set in `app.setup` + const socket = socketKey + ? connection[socketKey] + : socketMap.get(connection); + + if (socket) { + const eventName = `${context.path || ""} ${event}`.trim(); + + let result = channel.dataFor(connection) || context.dispatch || + context.result; + + // If we are getting events from an array but try to dispatch individual data + // try to get the individual item to dispatch from the correct index. + if ( + !Array.isArray(data) && Array.isArray(context.result) && + Array.isArray(result) + ) { + result = context.result.find((resultData) => + lodash.isEqual(resultData, data) + ); + } + + debug(`Dispatching '${eventName}' to Socket ${socket.id} with`, result); + + socket[emit](eventName, result); + } + }); + }; +} + +export async function runMethod( + app: Application, + connection: RealTimeConnection, + path: string, + method: string, + args: any[], +) { + const trace = `method '${method}' on service '${path}'`; + const methodArgs = args.slice(0); + const callback = + // eslint-disable-next-line @typescript-eslint/no-empty-function + typeof methodArgs[methodArgs.length - 1] === "function" + ? methodArgs.pop() + : function () {}; + + debug(`Running ${trace}`, connection, args); + + const handleError = (error: any) => { + debug(`Error in ${trace}`, error); + callback(normalizeError(error)); + }; + + try { + const lookup = app.lookup(path); + + // No valid service was found throw a NotFound error + if (lookup === null) { + throw new NotFound(`Service '${path}' not found`); + } + + const { service, params: route = {} } = lookup; + const { methods } = getServiceOptions(service); + + // Only service methods are allowed + if (!methods?.includes(method)) { + throw new MethodNotAllowed( + `Method '${method}' not allowed on service '${path}'`, + ); + } + + const position = paramsPositions[method] !== undefined + ? paramsPositions[method] + : DEFAULT_PARAMS_POSITION; + const query = Object.assign({}, methodArgs[position]); + // `params` have to be re-mapped to the query and added with the route + const params = Object.assign({ query, route, connection }, connection); + + // `params` is always the last parameter. Error if we got more arguments. + if (methodArgs.length > position + 1) { + throw new BadRequest(`Too many arguments for '${method}' method`); + } + + methodArgs[position] = params; + + const ctx = createContext(service, method); + const returnedCtx: HookContext = await (service as any)[method]( + ...methodArgs, + ctx, + ); + const result = returnedCtx.dispatch || returnedCtx.result; + + debug(`Returned successfully ${trace}`, result); + callback(null, result); + } catch (error: any) { + handleError(error); + } +} diff --git a/main/transport-commons/test/channels/channel.test.ts b/main/transport-commons/test/channels/channel.test.ts new file mode 100644 index 0000000000..6b7a3a07b5 --- /dev/null +++ b/main/transport-commons/test/channels/channel.test.ts @@ -0,0 +1,253 @@ +import { + assert, + assertEquals, + assertInstanceOf, + assertStrictEquals, + beforeEach, + describe, + it, +} from "../../../commons/mod.ts"; +import { Application, feathers } from "../../../feathers/mod.ts"; +import { channels, keys } from "../../src/channels/index.ts"; +import { + Channel, + RealTimeConnection, +} from "../../src/channels/channel/base.ts"; +import { CombinedChannel } from "../../src/channels/channel/combined.ts"; + +const { CHANNELS } = keys; + +describe("app.channel", () => { + let app: Application; + + beforeEach(() => { + app = feathers().configure(channels()); + }); + + describe("base channels", () => { + it("creates a new channel, app.channels has names", () => { + assert(app.channel("test") instanceof Channel); + assertEquals(app.channels, ["test"]); + }); + + it(".join", () => { + const test = app.channel("test"); + const c1 = { id: 1 }; + const c2 = { id: 2 }; + const c3 = { id: 3 }; + + assertStrictEquals(test.length, 0, "Initial channel is empty"); + + test.join(c1); + test.join(c1); + + assertStrictEquals(test.length, 1, "Joining twice only runs once"); + + test.join(c2, c3); + + assertStrictEquals(test.length, 3, "New connections joined"); + + test.join(c1, c2, c3); + + assertStrictEquals(test.length, 3, "Joining multiple times does nothing"); + }); + + it(".leave", () => { + const test = app.channel("test"); + const c1 = { id: 1 }; + const c2 = { id: 2 }; + + assertStrictEquals(test.length, 0); + + test.join(c1, c2); + + assertStrictEquals(test.length, 2); + + test.leave(c2); + test.leave(c2); + + assertStrictEquals(test.length, 1); + assertStrictEquals(test.connections.indexOf(c2), -1); + }); + + it(".leave conditional", () => { + const test = app.channel("test"); + const c1 = { id: 1, leave: true }; + const c2 = { id: 2 }; + const c3 = { id: 3 }; + + test.join(c1, c2, c3); + + assertStrictEquals(test.length, 3); + + test.leave((connection: RealTimeConnection) => connection.leave); + + assertStrictEquals(test.length, 2); + assertStrictEquals(test.connections.indexOf(c1), -1); + }); + + it(".filter", () => { + const test = app.channel("test"); + const c1 = { id: 1, filter: true }; + const c2 = { id: 2 }; + const c3 = { id: 3 }; + + test.join(c1, c2, c3); + + const filtered = test.filter((connection) => connection.filter); + + assert(filtered !== test, "Returns a new channel instance"); + assert(filtered instanceof Channel); + assertStrictEquals(filtered.length, 1); + }); + + it(".send", () => { + const data = { message: "Hi" }; + + const test = app.channel("test"); + const withData = test.send(data); + + assert(test !== withData); + assertStrictEquals(withData.data, data); + }); + + describe("empty channels", () => { + it("is an EventEmitter", () => { + const channel = app.channel("emitchannel"); + + return new Promise((resolve) => { + channel.once("message", (data: any) => { + assertStrictEquals(data, "hello"); + resolve(); + }); + + channel.emit("message", "hello"); + }); + }); + + it("empty", () => { + const channel = app.channel("test"); + const c1 = { id: 1 }; + const c2 = { id: 2 }; + + // channel.once("empty", done); + + channel.join(c1, c2); + channel.leave(c1); + channel.leave(c2); + }); + + it("removes an empty channel", () => { + const channel = app.channel("test"); + const appChannels = (app as any)[CHANNELS]; + const c1 = { id: 1 }; + + channel.join(c1); + + assert(appChannels.test); + assertStrictEquals(Object.keys(appChannels).length, 1); + channel.leave(c1); + + assert((app as any)[CHANNELS].test === undefined); + assertStrictEquals(Object.keys(appChannels).length, 0); + }); + + it("removes all event listeners from an empty channel", () => { + const channel = app.channel("testing"); + const connection = { id: 1 }; + + channel.on("something", () => {}); + assertStrictEquals(channel.listenerCount("something"), 1); + assertStrictEquals(channel.listenerCount("empty"), 1); + + channel.join(connection).leave(connection); + + assert((app as any)[CHANNELS].testing === undefined); + + assertStrictEquals(channel.listenerCount("something"), 0); + assertStrictEquals(channel.listenerCount("empty"), 0); + }); + }); + }); + + describe("combined channels", () => { + it("combines multiple channels", () => { + const combined = app.channel("test", "again"); + + assertEquals(app.channels, ["test", "again"]); + assertInstanceOf(combined, CombinedChannel); + assertStrictEquals(combined.length, 0); + }); + + it("de-dupes connections", () => { + const c1 = { id: 1 }; + const c2 = { id: 2 }; + + app.channel("test").join(c1, c2); + app.channel("again").join(c1); + + const combined = app.channel("test", "again"); + + assertInstanceOf(combined, CombinedChannel); + assertStrictEquals(combined.length, 2); + }); + + it("does nothing when the channel is undefined (#2207)", () => { + const channel = app.channel("test", "me"); + + // @ts-ignore + channel.join(undefined); + }); + + it(".join all child channels", () => { + const c1 = { id: 1 }; + const c2 = { id: 2 }; + + const combined = app.channel("test", "again"); + + combined.join(c1, c2); + + assertStrictEquals(combined.length, 2); + assertStrictEquals(app.channel("test").length, 2); + assertStrictEquals(app.channel("again").length, 2); + }); + + it(".leave all child channels", () => { + const c1 = { id: 1 }; + const c2 = { id: 2 }; + + app.channel("test").join(c1, c2); + app.channel("again").join(c1); + + const combined = app.channel("test", "again"); + + combined.leave(c1); + + assertStrictEquals(app.channel("test").length, 1); + assertStrictEquals(app.channel("again").length, 0); + }); + + it(".leave all child channels conditionally", () => { + const c1 = { id: 1 }; + const c2 = { id: 2, leave: true }; + const combined = app.channel("test", "again").join(c1, c2); + + combined.leave((connection: RealTimeConnection) => connection.leave); + + assertStrictEquals(app.channel("test").length, 1); + assertStrictEquals(app.channel("again").length, 1); + }); + + it("app.channel(app.channels)", () => { + const c1 = { id: 1 }; + const c2 = { id: 2 }; + + app.channel("test").join(c1, c2); + app.channel("again").join(c1); + + const combined = app.channel(app.channels); + + assertEquals(combined.connections, [c1, c2]); + }); + }); +}); diff --git a/main/transport-commons/test/channels/dispatch.test.ts b/main/transport-commons/test/channels/dispatch.test.ts new file mode 100644 index 0000000000..529653f217 --- /dev/null +++ b/main/transport-commons/test/channels/dispatch.test.ts @@ -0,0 +1,294 @@ +/* eslint-disable @typescript-eslint/no-empty-function */ +import { + assertEquals, + assertNotStrictEquals, + assertObjectMatch, + assertStrictEquals, + beforeEach, + describe, + fail, + it, + unreachable, +} from "../../../commons/mod.ts"; +import { Application, feathers, HookContext } from "../../../feathers/mod.ts"; +import { channels } from "../../src/channels/index.ts"; +import { Channel } from "../../src/channels/channel/base.ts"; +import { CombinedChannel } from "../../src/channels/channel/combined.ts"; + +class TestService { + events = ["foo"]; + + async create(payload: any) { + return payload; + } +} + +describe("app.publish", () => { + let app: Application; + + beforeEach(() => { + app = feathers().configure(channels()); + }); + + it("throws an error if service does not send the event", () => { + try { + app.use("/test", { + create(data: any) { + return Promise.resolve(data); + }, + }); + + app.service("test").registerPublisher("created", function () {}); + app.service("test").registerPublisher("bla", function () {}); + unreachable(); + } catch (e: any) { + assertStrictEquals(e.message, "'bla' is not a valid service event"); + } + }); + + describe("registration and `dispatch` event", () => { + const c1 = { id: 1, test: true }; + const c2 = { id: 2, test: true }; + const data = { message: "This is a test" }; + + beforeEach(() => { + app.use("/test", new TestService()); + }); + + it("error in publisher is handled gracefully (#1707)", async () => { + app.service("test").publish("created", () => { + throw new Error("Something went wrong"); + }); + + try { + await app.service("test").create({ message: "something" }); + } catch (error: any) { + fail(error.message); + } + }); + + it("simple event registration and dispatching", () => { + app.channel("testing").join(c1); + + app.service("test").registerPublisher( + "created", + () => app.channel("testing"), + ); + + app.once( + "publish", + (event: string, channel: Channel, hook: HookContext) => { + try { + assertStrictEquals(event, "created"); + assertStrictEquals(hook.path, "test"); + assertStrictEquals(hook.result, data); + assertEquals(channel.connections, [c1]); + } catch (error: any) { + fail(error.message); + } + }, + ); + + app.service("test").create(data).catch(fail); + }); + + it("app and global level dispatching and precedence", () => { + app.channel("testing").join(c1); + app.channel("other").join(c2); + + app.registerPublisher("created", () => app.channel("testing")); + app.registerPublisher(() => app.channel("other")); + + app.once("publish", (_event: string, channel: Channel) => { + assertNotStrictEquals(channel.connections.indexOf(c1), -1); + }); + + app.service("test").create(data).catch(fail); + }); + + it("promise event dispatching", () => new Promise((resolve) =>{ + app.channel("testing").join(c1); + app.channel("othertest").join(c2); + + app + .service("test") + .registerPublisher( + "created", + () => + new Promise((resolve) => + setTimeout( + () => resolve(app.channel("testing")), + 50, + ) + ), + ); + app + .service("test") + .registerPublisher( + "created", + () => + new Promise((resolve) => + setTimeout( + () => resolve(app.channel("testing", "othertest")), + 100, + ) + ), + ); + + app.once( + "publish", + (_event: string, channel: Channel, hook: HookContext) => { + assertStrictEquals(hook.result, data); + assertEquals(channel.connections, [c1, c2]); + resolve(); + }, + ); + + app.service("test").create(data).catch(fail); + })); + + it("custom event dispatching", () => { + const eventData = { testing: true }; + + app.channel("testing").join(c1); + app.channel("othertest").join(c2); + + app.service("test").registerPublisher( + "foo", + () => app.channel("testing"), + ); + + app.once( + "publish", + (event: string, channel: Channel, hook: HookContext) => { + assertStrictEquals(event, "foo"); + assertObjectMatch(hook, { + app, + path: "test", + service: app.service("test"), + result: eventData, + }); + assertEquals(channel.connections, [c1]); + }, + ); + + app.service("test").emit("foo", eventData); + }); + + it("does not sent `dispatch` event if there are no dispatchers", () => + new Promise((resolve) => { + app.once("publish", () => unreachable()); + + globalThis.addEventListener( + "unhandledrejection", + () => fail("Unhandled Rejection"), + ); + + app + .service("test") + .create(data) + .then(resolve) + .catch(fail); + })); + + it("does not send `dispatch` event if there are no connections", () => + new Promise((resolve) => { + app.service("test").registerPublisher( + "created", + () => app.channel("dummy"), + ); + + app.once("publish", () => fail("Should never get here")); + + app + .service("test") + .create(data) + .then(resolve) + .catch(fail); + })); + + it("dispatcher returning an array of channels", () => { + app.channel("testing").join(c1); + app.channel("othertest").join(c2); + + app + .service("test") + .registerPublisher( + "created", + () => [app.channel("testing"), app.channel("othertest")], + ); + + app.once( + "publish", + (_event: string, channel: Channel, hook: HookContext) => { + assertStrictEquals(hook.result, data); + assertEquals(channel.connections, [c1, c2]); + }, + ); + + app.service("test").create(data).catch(fail); + }); + + it("dispatcher can send data", () => { + const c1data = { channel: "testing" }; + + app.channel("testing").join(c1); + app.channel("othertest").join(c2); + + app + .service("test") + .registerPublisher( + "created", + () => [app.channel("testing").send(c1data), app.channel("othertest")], + ); + + app.once( + "publish", + (_event: string, channel: CombinedChannel, hook: HookContext) => { + assertStrictEquals(hook.result, data); + assertStrictEquals(channel.dataFor(c1), c1data); + assertStrictEquals(channel.dataFor(c2), null); + assertEquals(channel.connections, [c1, c2]); + }, + ); + + app.service("test").create(data).catch(fail); + }); + + it("publisher precedence and preventing publishing", (done) => { + app.channel("test").join(c1); + + app.registerPublisher(() => app.channel("test")); + // @ts-ignore + app.service("test").registerPublisher("created", (): null => null); + + app.once("publish", () => fail("Should never get here")); + + app + .service("test") + .create(data) + .catch(fail); + }); + + it("data of first channel has precedence", () => { + const sendData = { test: true }; + + app.channel("testing").join(c1); + app.channel("othertest").join(c1); + + app.service("test").registerPublisher("created", () => { + return [ + app.channel("testing"), + app.channel("othertest").send(sendData), + ]; + }); + + app.once("publish", (_event: string, channel: CombinedChannel) => { + assertStrictEquals(channel.dataFor(c1), null); + assertEquals(channel.connections, [c1]); + }); + + app.service("test").create(data).catch(fail); + }); + }); +}); diff --git a/main/transport-commons/test/channels/index.test.ts b/main/transport-commons/test/channels/index.test.ts new file mode 100644 index 0000000000..c35c5dff5b --- /dev/null +++ b/main/transport-commons/test/channels/index.test.ts @@ -0,0 +1,52 @@ +import { + assert, + assertStrictEquals, + describe, + it, + unreachable, +} from "../../../commons/mod.ts"; +import { feathers } from "../../../feathers/mod.ts"; +import { channels, keys } from "../../src/channels/index.ts"; + +describe("feathers-channels", () => { + it("has app.channel", () => { + const app = feathers().configure(channels()); + + assertStrictEquals(typeof app.channel, "function"); + assertStrictEquals(typeof (app as any)[keys.CHANNELS], "object"); + assertStrictEquals(app.channels.length, 0); + }); + + it("throws an error when called with nothing", () => { + const app = feathers().configure(channels()); + + try { + app.channel(); + unreachable; + } catch (e: any) { + assertStrictEquals( + e.message, + "app.channel needs at least one channel name", + ); + } + }); + + it("configuring twice does nothing", () => { + feathers().configure(channels()).configure(channels()); + }); + + it("does not add things to the service if `dispatch` exists", () => { + const app = feathers() + .configure(channels()) + .use("/test", { + async setup() {}, + publish() { + return this; + }, + } as any); + + const service: any = app.service("test"); + + assert(!service[keys.PUBLISHERS]); + }); +}); diff --git a/main/transport-commons/test/client.test.ts b/main/transport-commons/test/client.test.ts new file mode 100644 index 0000000000..67fa0d837e --- /dev/null +++ b/main/transport-commons/test/client.test.ts @@ -0,0 +1,256 @@ +import { + assert, + assertEquals, + assertObjectMatch, + assertRejects, + assertStrictEquals, + beforeEach, + describe, + it, + unreachable, +} from "../../commons/mod.ts"; +import { EventEmitter } from "../../commons/mod.ts"; +import { CustomMethods } from "../../feathers/mod.ts"; +import { NotAuthenticated } from "../../errors/mod.ts"; +import { Service, SocketService } from "../src/client.ts"; + +declare type DummyCallback = (err: any, data?: any) => void; + +describe("client", () => { + let connection: any; + let testData: any; + let service: + & SocketService + & CustomMethods<{ customMethod: any }> + & EventEmitter; + + beforeEach(() => { + connection = new EventEmitter(); + testData = { data: "testing " }; + service = new Service({ + events: ["created"], + name: "todos", + method: "emit", + connection, + }) as any; + }); + + it("sets `events` property on service", () => { + assert(service.events); + }); + + it("throws an error when the emitter does not have the method", () => { + const clientService = new Service({ + name: "todos", + method: "emit", + connection: {}, + }) as Service & EventEmitter; + + try { + clientService.eventNames(); + unreachable(); + } catch (e: any) { + assertStrictEquals( + e.message, + "Can not call 'eventNames' on the client service connection", + ); + } + + try { + clientService.on("test", () => {}); + unreachable(); + } catch (e: any) { + assertStrictEquals( + e.message, + "Can not call 'on' on the client service connection", + ); + } + }); + + it("allows chaining event listeners", () => { + assertStrictEquals( + service, + service.on("thing", () => {}), + ); + assertStrictEquals( + service, + service.once("other thing", () => {}), + ); + }); + + it("initializes and emits namespaced events", () => { + connection.once("todos test", (data: any) => { + assertStrictEquals(data, testData); + }); + service.emit("test", testData); + }); + + it("has other emitter methods", () => { + assert(service.eventNames()); + }); + + it("can receive pathed events", () => { + service.once("thing", (data: any) => { + assertStrictEquals(data, testData); + }); + + connection.emit("todos thing", testData); + }); + + it("sends all service and custom methods with acknowledgement", async () => { + const idCb = (_path: any, id: any, _params: any, callback: DummyCallback) => + callback(null, { id }); + + const idDataCb = ( + _path: any, + _id: any, + data: any, + _params: any, + callback: DummyCallback, + ) => callback(null, data); + + const dataCb = ( + _path: any, + data: any, + _params: any, + callback: DummyCallback, + ) => { + data.created = true; + callback(null, data); + }; + + connection.once("create", dataCb); + service.methods("customMethod"); + + let res = await service.create(testData); + + assert(res.created); + + connection.once("get", idCb); + res = await service.get(1); + assertEquals(res, { id: 1 }); + + connection.once("remove", idCb); + res = await service.remove(12); + assertEquals(res, { id: 12 }); + + connection.once("update", idDataCb); + res = await service.update(12, testData); + assertStrictEquals(res, testData); + + connection.once("patch", idDataCb); + res = await service.patch(12, testData); + assertStrictEquals(res, testData); + + connection.once("customMethod", dataCb); + res = await service.customMethod({ message: "test" }); + assertEquals(res, { + created: true, + message: "test", + }); + + connection.once( + "find", + (_path: any, params: any, callback: DummyCallback) => + callback(null, { params }), + ); + + res = await service.find({ query: { test: true } }); + assertEquals(res, { + params: { test: true }, + }); + }); + + it("converts to feathers-errors (#19)", async () => { + connection.once( + "create", + (_path: any, _data: any, _params: any, callback: DummyCallback) => + callback(new NotAuthenticated("Test", { hi: "me" }).toJSON()), + ); + + const error = await assertRejects( + () => service.create(testData), + NotAuthenticated, + "Test", + ); + + assertObjectMatch(error, { + name: "NotAuthenticated", + message: "Test", + code: 401, + data: { hi: "me" }, + }); + }); + + it("converts other errors (#19)", async () => { + connection.once( + "create", + ( + _path: string, + _data: any, + _params: any, + callback: (x: string) => void, + ) => { + callback("Something went wrong"); // eslint-disable-line + }, + ); + + await assertRejects(() => service.create(testData), "Something went wrong"); + }); + + it("has all EventEmitter methods", () => { + const testing = { hello: "world" }; + const callback = (data: any) => { + assertStrictEquals(data, testing); + assertStrictEquals(service.listenerCount("test"), 1); + service.removeListener("test", callback); + assertStrictEquals(service.listenerCount("test"), 0); + }; + + service.addListener("test", callback); + + connection.emit("todos test", testing); + }); + + it("properly handles on/off methods", () => { + const testing = { hello: "world" }; + + const callback1 = (data: any) => { + assertStrictEquals(data, testing); + assertStrictEquals(service.listenerCount("test"), 3); + service.off("test", callback1); + assertStrictEquals(service.listenerCount("test"), 2); + service.removeAllListeners("test"); + assertStrictEquals(service.listenerCount("test"), 0); + }; + const callback2 = () => { + // noop + }; + + service.on("test", callback1); + service.on("test", callback2); + service.on("test", callback2); + + connection.emit("todos test", testing); + }); + + it("forwards namespaced call to .off, returns service instance", () => { + // Use it's own connection and service so off method gets detected + const conn = new EventEmitter(); + + // @ts-ignore + conn.off = function (name) { + assertStrictEquals(name, "todos test"); + + return this; + }; + + const client = new Service({ + name: "todos", + method: "emit", + connection: conn, + }); + + assertStrictEquals(client.off("test"), client); + }); +}); diff --git a/main/transport-commons/test/http.test.ts b/main/transport-commons/test/http.test.ts new file mode 100644 index 0000000000..95c6f7cb69 --- /dev/null +++ b/main/transport-commons/test/http.test.ts @@ -0,0 +1,102 @@ +import { + assertEquals, + assertStrictEquals, + assertThrows, + describe, + it, +} from "../../commons/mod.ts"; +import { HookContext } from "../../feathers/mod.ts"; +import { http } from "../src/index.ts"; + +describe("@feathersjs/transport-commons HTTP helpers", () => { + it("getResponse body", () => { + const plainData = { message: "hi" }; + const dispatch = { message: "from dispatch" }; + const resultContext = { + result: plainData, + }; + const dispatchContext = { + dispatch, + }; + + assertStrictEquals( + http.getResponse(resultContext as HookContext).body, + plainData, + ); + assertStrictEquals( + http.getResponse(dispatchContext as HookContext).body, + dispatch, + ); + }); + + it("getResponse status", () => { + const statusContext = { + http: { status: 202 }, + }; + const createContext = { + method: "create", + }; + const redirectContext = { + http: { location: "/" }, + }; + + assertStrictEquals( + http.getResponse(statusContext as HookContext).status, + 202, + ); + assertStrictEquals( + http.getResponse(createContext as HookContext).status, + http.statusCodes.created, + ); + assertStrictEquals( + http.getResponse(redirectContext as HookContext).status, + http.statusCodes.seeOther, + ); + assertStrictEquals( + http.getResponse({} as HookContext).status, + http.statusCodes.noContent, + ); + assertStrictEquals( + http.getResponse({ result: true } as HookContext).status, + http.statusCodes.success, + ); + }); + + it("getResponse headers", () => { + const headers = { key: "value" } as any; + const headersContext = { + http: { headers }, + }; + const locationContext = { + http: { location: "/" }, + }; + + assertEquals(http.getResponse({} as HookContext).headers, {}); + assertEquals( + http.getResponse({ http: {} } as HookContext).headers, + {}, + ); + assertStrictEquals( + http.getResponse(headersContext as HookContext).headers, + headers, + ); + assertEquals( + http.getResponse(locationContext as HookContext).headers, + { + Location: "/", + }, + ); + }); + + it("getServiceMethod", () => { + assertStrictEquals(http.getServiceMethod("GET", 2), "get"); + assertStrictEquals(http.getServiceMethod("GET", null), "find"); + assertStrictEquals(http.getServiceMethod("PoST", null), "create"); + assertStrictEquals( + http.getServiceMethod("PoST", null, "customMethod"), + "customMethod", + ); + assertStrictEquals(http.getServiceMethod("delete", null), "remove"); + assertThrows(() => http.getServiceMethod("nonsense", null)); + }); +}); diff --git a/main/transport-commons/test/routing/index.test.ts b/main/transport-commons/test/routing/index.test.ts new file mode 100644 index 0000000000..869beb63d1 --- /dev/null +++ b/main/transport-commons/test/routing/index.test.ts @@ -0,0 +1,128 @@ +import { + assert, + assertEquals, + assertStrictEquals, + beforeEach, + describe, + it, +} from "../../../commons/mod.ts"; +import { Application, feathers } from "../../../feathers/mod.ts"; +import { routing } from "../../src/routing/index.ts"; + +describe("app.routes", () => { + let app: Application; + + beforeEach(() => { + app = feathers().configure(routing()); + + app.use("/my/service", { + get(id: string | number) { + return Promise.resolve({ id }); + }, + }); + }); + + it("does nothing when configured twice", () => { + feathers().configure(routing()).configure(routing()); + }); + + it("has app.lookup and app.routes", () => { + assertStrictEquals(typeof app.lookup, "function"); + assert(app.routes); + }); + + it("returns null when nothing is found", () => { + const result = app.lookup("me/service"); + + assertStrictEquals(result, null); + }); + + it("returns null for invalid service path", () => { + // @ts-ignore + assertStrictEquals(app.lookup(null), null); + // @ts-ignore + assertStrictEquals(app.lookup({}), null); + }); + + it("can look up and strips slashes", () => { + const result = app.lookup("my/service"); + + assertStrictEquals(result?.service, app.service("/my/service/")); + }); + + it("can look up with id", () => { + const result = app.lookup("/my/service/1234"); + + assertStrictEquals(result?.service, app.service("/my/service")); + + assertEquals(result.params, { + __id: "1234", + }); + }); + + it("can look up with params, id and special characters", () => { + const path = "/test/:first/my/:second"; + + app.use(path, { + async get(id: string | number) { + return { id }; + }, + }); + + const result = app.lookup("/test/me/my/::special/testing"); + + assertStrictEquals(result?.service, app.service(path)); + assertEquals(result.params, { + __id: "testing", + first: "me", + second: "::special", + }); + }); + + it("can register routes with preset params", () => { + app.routes.insert("/my/service/:__id/preset", { + service: app.service("/my/service"), + params: { preset: true }, + }); + + const result = app.lookup("/my/service/1234/preset"); + + assertStrictEquals(result?.service, app.service("/my/service")); + assertEquals(result.params, { + preset: true, + __id: "1234", + }); + }); + + it("can pass route params during a service registration", () => { + app.use( + "/other/service", + { + async get(id: any) { + return id; + }, + }, + { + routeParams: { used: true }, + }, + ); + + const result = app.lookup("/other/service/1234"); + + assertStrictEquals(result?.service, app.service("/other/service")); + assertEquals(result.params, { + used: true, + __id: "1234", + }); + }); + + it("can unregister a service (#2035)", async () => { + const result = app.lookup("my/service"); + + assertStrictEquals(result?.service, app.service("/my/service/")); + + await app.unuse("/my/service"); + + assertStrictEquals(app.lookup("my/service"), null); + }); +}); diff --git a/main/transport-commons/test/routing/router.test.ts b/main/transport-commons/test/routing/router.test.ts new file mode 100644 index 0000000000..8fb54a482c --- /dev/null +++ b/main/transport-commons/test/routing/router.test.ts @@ -0,0 +1,141 @@ +import { + assert, + assertEquals, + assertStrictEquals, + assertThrows, + describe, + it, +} from "../../../commons/mod.ts"; +import { Router } from "../../src/routing/index.ts"; + +describe("router", () => { + it("can lookup and insert a simple path and returns null for invalid path", () => { + const r = new Router(); + + r.insert("/hello/there/you", "test"); + + const result = r.lookup("hello/there/you/"); + + assertEquals(result, { + params: {}, + data: "test", + }); + + assertStrictEquals(r.lookup("not/there"), null); + assertStrictEquals(r.lookup("not-me"), null); + }); + + it("can insert data at the root", () => { + const r = new Router(); + + r.insert("", "hi"); + + const result = r.lookup("/"); + + assertEquals(result, { + params: {}, + data: "hi", + }); + }); + + it("can insert with placeholder and has proper specificity", () => { + const r = new Router(); + + r.insert("/hello/:id", "one"); + r.insert("/hello/:id/you", "two"); + r.insert("/hello/:id/:other", "three"); + + const first = r.lookup("hello/there/"); + + assertThrows( + () => r.insert("/hello/:id/you", "two"), + "Path hello/:id/you already exists", + ); + + assertEquals(first, { + params: { id: "there" }, + data: "one", + }); + + const second = r.lookup("hello/yes/you"); + + assertEquals(second, { + params: { id: "yes" }, + data: "two", + }); + + const third = r.lookup("hello/yes/they"); + + assertEquals(third, { + params: { + id: "yes", + other: "they", + }, + data: "three", + }); + + assertStrictEquals(r.lookup("hello/yes/they/here"), null); + }); + + it("works with different placeholders in different paths (#2327)", () => { + const r = new Router(); + + r.insert("/hello/:id", "one"); + r.insert("/hello/:test/you", "two"); + r.insert("/hello/:test/:two/hi/:three", "three"); + r.insert("/hello/:test/:two/hi", "four"); + + assertEquals(r.lookup("/hello/there"), { + params: { id: "there" }, + data: "one", + }); + assertEquals(r.lookup("/hello/there/you"), { + params: { test: "there" }, + data: "two", + }); + assertStrictEquals(r.lookup("/hello/there/bla"), null); + assertEquals(r.lookup("/hello/there/maybe/hi"), { + params: { test: "there", two: "maybe" }, + data: "four", + }); + assertEquals(r.lookup("/hello/there/maybe/hi/test"), { + params: { three: "test", two: "maybe", test: "there" }, + data: "three", + }); + }); + + it("can remove paths (#2035)", () => { + const r = new Router(); + + r.insert("/hello/:id", "one"); + r.insert("/hello/:test/you", "two"); + r.insert("/hello/here/thing", "else"); + + assertEquals(r.lookup("hello/there"), { + params: { id: "there" }, + data: "one", + }); + + r.remove("/hello/:id"); + + assertEquals(r.lookup("hello/here/you"), { + params: { test: "here" }, + data: "two", + }); + assertEquals(r.lookup("hello/here/thing"), { + params: {}, + data: "else", + }); + assertStrictEquals(r.lookup("hello/there"), null); + + r.remove("/hello/:test/you"); + assertStrictEquals(r.lookup("hello/here/you"), null); + assertEquals(r.lookup("hello/here/thing"), { + params: {}, + data: "else", + }); + + r.remove("/hello/here/thing"); + assert(!r.root.hasChildren); + }); +}); diff --git a/main/transport-commons/test/socket/index.test.ts b/main/transport-commons/test/socket/index.test.ts new file mode 100644 index 0000000000..3c00a98dc6 --- /dev/null +++ b/main/transport-commons/test/socket/index.test.ts @@ -0,0 +1,184 @@ +import { + assert, + assertEquals, + assertStrictEquals, + beforeEach, + describe, + fail, + it, +} from "../../../commons/mod.ts"; +import { EventEmitter } from "../../../commons/mod.ts"; +import { Application, feathers, Id, Params } from "../../../feathers/mod.ts"; + +import { socket as commons, SocketOptions } from "../../src/socket/index.ts"; + +class DummyService { + async get(id: Id, params: Params) { + return { id, params }; + } + + async create(data: any, params: Params) { + return { + ...data, + params, + }; + } + + async custom(data: any, params: Params) { + return { + ...data, + params, + message: "From custom method", + }; + } +} + +describe("@feathersjs/transport-commons", () => { + let provider: EventEmitter; + let options: SocketOptions; + let app: Application; + let connection: any; + + beforeEach(() => { + connection = { testing: true }; + provider = new EventEmitter(); + + options = { + emit: "emit", + done: Promise.resolve(provider), + socketMap: new WeakMap(), + getParams() { + return connection; + }, + }; + app = feathers() + .configure(commons(options)) + .use("/myservice", new DummyService(), { + methods: ["get", "create", "custom"], + }); + + return options.done; + }); + + it("`connection` event", () => { + const socket = new EventEmitter(); + + app.once("connection", (data: any) => { + assertStrictEquals(connection, data); + }); + + provider.emit("connection", socket); + }); + + describe("method name based socket events", () => { + it(".get without params", () => { + const socket = new EventEmitter(); + + provider.emit("connection", socket); + + socket.emit("get", "myservice", 10, (error: any, result: any) => { + try { + assert(!error); + assertEquals(result, { + id: 10, + params: Object.assign( + { + query: {}, + route: {}, + connection, + }, + connection, + ), + }); + } catch (e: any) { + fail(e.message); + } + }); + }); + + it(".get with invalid service name and arguments", () => { + const socket = new EventEmitter(); + + provider.emit("connection", socket); + + socket.emit("get", null, (error: any) => { + assertStrictEquals(error.name, "NotFound"); + assertStrictEquals(error.message, "Service 'null' not found"); + }); + }); + + it(".create with params", (done) => { + const socket = new EventEmitter(); + const data = { + test: "data", + }; + + provider.emit("connection", socket); + + socket.emit( + "create", + "myservice", + data, + { + fromQuery: true, + }, + (error: any, result: any) => { + try { + const params = Object.assign( + { + query: { fromQuery: true }, + route: {}, + connection, + }, + connection, + ); + + assert(!error); + assertEquals(result, Object.assign({ params }, data)); + } catch (e: any) { + fail(e.message); + } + }, + ); + }); + + it("custom method with params", () => { + const socket = new EventEmitter(); + const data = { + test: "data", + }; + + provider.emit("connection", socket); + + socket.emit( + "custom", + "myservice", + data, + { + fromQuery: true, + }, + (error: any, result: any) => { + try { + const params = Object.assign( + { + query: { fromQuery: true }, + route: {}, + connection, + }, + connection, + ); + + assert(!error); + assertEquals(result, { + ...data, + params, + message: "From custom method", + }); + } catch (e: any) { + fail(e.message); + } + }, + ); + }); + }); +}); diff --git a/main/transport-commons/test/socket/utils.test.ts b/main/transport-commons/test/socket/utils.test.ts new file mode 100644 index 0000000000..da6e1791b6 --- /dev/null +++ b/main/transport-commons/test/socket/utils.test.ts @@ -0,0 +1,384 @@ +import { + assert, + assertEquals, + assertStrictEquals, + beforeEach, + describe, + fail, + it, +} from "../../../commons/mod.ts"; +import { EventEmitter } from "../../../commons/mod.ts"; +import { Application, feathers, Params } from "../../../feathers/mod.ts"; +import { NotAuthenticated } from "../../../errors/mod.ts"; +import { lodash } from "https://deno.land/x/deno_ts_lodash@0.0.1/mod.ts"; + +import { routing } from "../../src/routing/index.ts"; +import { + getDispatcher, + normalizeError, + runMethod, +} from "../../src/socket/utils.ts"; +import { RealTimeConnection } from "../../src/channels/channel/base.ts"; + +describe("socket commons utils", () => { + describe(".normalizeError", () => { + it.ignore("simple error normalization", () => { + // const message = "Something went wrong"; + // const e = new Error(message); + + // assertEquals(normalizeError(e), { + // message, + // stack: e.stack.toString(), + // }); + }); + + it("calls .toJSON", () => { + const json = { message: "toJSON called" }; + + assertStrictEquals( + normalizeError({ + toJSON() { + return json; + }, + }), + json, + ); + }); + + it("removes `hook` property", () => { + const e = { + hook: true, + }; + + assertEquals(normalizeError(e), {}); + assert(e.hook, "Does not mutate the original object"); + }); + + it.ignore("hides stack in production", () => { + // const oldEnv = process.env.NODE_ENV; + + // process.env.NODE_ENV = "production"; + + // const message = "Something went wrong"; + // const e = new Error(message); + // const normalized = normalizeError(e); + + // assert.strictEqual(normalized.message, message); + // assert.ok(!normalized.stack); + + // process.env.NODE_ENV = oldEnv; + }); + }); + + describe(".getDispatcher", () => { + it("returns a dispatcher function", () => + assertStrictEquals( + typeof getDispatcher("test", new WeakMap()), + "function", + )); + + it("works with backwards compatible socketKey", () => { + const socketKey = Symbol("@feathersjs/test"); + + // @ts-ignore + const dispatcher = getDispatcher("emit", undefined, socketKey); + + const socket = new EventEmitter(); + + const connection = { + [socketKey]: socket, + }; + + const channel: any = { + connections: [connection], + dataFor(): null { + return null; + }, + }; + + socket.once("testing", (data: any) => { + assertStrictEquals(data, "hi"); + }); + + dispatcher("testing", channel, { result: "hi" } as any); + }); + + describe("dispatcher logic", () => { + let dispatcher: any; + let dummySocket: EventEmitter; + let dummyHook: any; + let dummyChannel: any; + let dummyConnection: RealTimeConnection; + let dummyMap: WeakMap; + + beforeEach(() => { + dummyConnection = {}; + dummyMap = new WeakMap(); + dispatcher = getDispatcher("emit", dummyMap); + dummySocket = new EventEmitter(); + dummyHook = { result: "hi" }; + dummyChannel = { + connections: [dummyConnection], + dataFor(): null { + return null; + }, + }; + dummyMap.set(dummyConnection, dummySocket); + }); + + it("dispatches a basic event", () => { + dummySocket.once("testing", (data: any) => { + assertStrictEquals(data, "hi"); + }); + + dispatcher("testing", dummyChannel, dummyHook); + }); + + it("dispatches event on a hooks path event", () => { + dummyHook.path = "myservice"; + + dummySocket.once("myservice testing", (data: any) => { + assertStrictEquals(data, "hi"); + }); + + dispatcher("testing", dummyChannel, dummyHook); + }); + + it("dispatches `hook.dispatch` instead", () => { + const message = "hi from dispatch"; + + dummyHook.dispatch = message; + + dummySocket.once("testing", (data: any) => { + assertStrictEquals(data, message); + }); + + dispatcher("testing", dummyChannel, dummyHook); + }); + + it("does nothing if there is no socket", () => { + dummyChannel.connections[0].test = null; + + dispatcher("testing", dummyChannel, dummyHook); + }); + + it("dispatches arrays properly hook events", () => { + const data1 = { message: "First message" }; + const data2 = { message: "Second message" }; + + dummyHook.result = [data1, data2]; + + dummySocket.once("testing", (data: any) => { + assertStrictEquals(data, data1); + dummySocket.once("testing", (result: any) => { + assertStrictEquals(result, data2); + }); + }); + + dispatcher("testing", dummyChannel, dummyHook, data1); + dispatcher("testing", dummyChannel, dummyHook, data2); + }); + + it("dispatches arrays properly for custom events", () => { + const result = [{ message: "First" }, { message: "Second" }]; + + dummyHook.result = result; + + dummySocket.once("otherEvent", (data: any) => { + assertStrictEquals(data, result); + }); + + dispatcher("otherEvent", dummyChannel, dummyHook, result); + }); + }); + }); + + describe(".runMethod", () => { + let app: Application; + + beforeEach(() => { + app = feathers().configure(routing()); + app.use("/myservice", { + async get(id: number | string, params: Params) { + if (params.query?.error) { + throw new NotAuthenticated("None shall pass"); + } + if (!lodash.isPlainObject(params.query)) { + throw new Error("Query is not a plain object"); + } + + return { id }; + }, + }); + }); + + describe("running methods", () => { + it("basic", () => { + const callback = (error: any, result: any) => { + if (error) { + return (error); + } + + assertEquals(result, { id: 10 }); + }; + + runMethod(app, {}, "myservice", "get", [10, {}, callback]); + }); + + it("queries are always plain objects", () => { + const callback = (error: any, result: any) => { + if (error) { + return (error); + } + + assertEquals(result, { id: 10 }); + }; + + runMethod(app, {}, "myservice", "get", [ + 10, + { + __proto__: [], + }, + callback, + ]); + }); + + it("merges params with connection and passes connection", () => { + const connection = { + testing: true, + }; + const callback = (error: any, result: any) => { + if (error) { + return (error); + } + + assertEquals(result, { + id: 10, + params: { + connection, + query: {}, + route: {}, + testing: true, + }, + }); + }; + + app.use("/otherservice", { + get(id, params) { + return Promise.resolve({ id, params }); + }, + }); + + runMethod(app, connection, "otherservice", "get", [10, {}, callback]); + }); + + it("with params missing", () => { + const callback = (error: any, result: any) => { + if (error) { + return (error); + } + + assertEquals(result, { id: 10 }); + }; + + runMethod(app, {}, "myservice", "get", [10, callback]); + }); + + it("with params but missing callback", () => { + app.use("/otherservice", { + get(id: number | string) { + assertStrictEquals(id, "dishes"); + + return Promise.resolve({ id }).then((res) => { + return res; + }); + }, + }); + + runMethod(app, {}, "otherservice", "get", ["dishes", {}]); + }); + + it("with params and callback missing", () => { + app.use("/otherservice", { + get(id: number | string) { + assertStrictEquals(id, "laundry"); + + return Promise.resolve({ id }).then((res) => { + return res; + }); + }, + }); + + runMethod(app, {}, "otherservice", "get", ["laundry"]); + }); + }); + + it("throws NotFound for invalid service", () => { + const callback = (error: any) => { + try { + assertEquals(error, { + name: "NotFound", + message: "Service 'ohmyservice' not found", + code: 404, + className: "not-found", + }); + } catch (e: any) { + fail(e.message); + } + }; + + runMethod(app, {}, "ohmyservice", "get", [10, callback]); + }); + + it("throws MethodNotAllowed undefined method", () => { + const callback = (error: any) => { + try { + assertEquals(error, { + name: "MethodNotAllowed", + message: "Method 'create' not allowed on service 'myservice'", + code: 405, + className: "method-not-allowed", + }); + } catch (e: any) { + fail(e.message); + } + }; + + runMethod(app, {}, "myservice", "create", [{}, callback]); + }); + + it("throws MethodNotAllowed for invalid service method", () => { + const callback = (error: any) => { + try { + assertEquals(error, { + name: "MethodNotAllowed", + message: "Method 'blabla' not allowed on service 'myservice'", + code: 405, + className: "method-not-allowed", + }); + } catch (e: any) { + fail(e.message); + } + }; + + runMethod(app, {}, "myservice", "blabla", [{}, callback]); + }); + + it("method error calls back with normalized error", () => { + const callback = (error: any) => { + try { + assertEquals(error, { + name: "NotAuthenticated", + message: "None shall pass", + code: 401, + className: "not-authenticated", + }); + } catch (e: any) { + fail(e.message); + } + }; + + runMethod(app, {}, "myservice", "get", [42, { error: true }, callback]); + }); + }); +}); diff --git a/package-lock.json b/package-lock.json index 61500071d2..809a692e2a 100644 --- a/package-lock.json +++ b/package-lock.json @@ -1,32709 +1,17183 @@ { - "name": "feathers", - "lockfileVersion": 2, - "requires": true, - "packages": { - "": { - "name": "feathers", - "license": "MIT", - "dependencies": { - "@babel/core": "^7.16.7", - "@babel/preset-env": "^7.16.7", - "@feathersjs/hooks": "^0.6.5", - "@types/axios": "^0.14.0", - "@types/bcryptjs": "^2.4.2", - "@types/config": "^0.0.40", - "@types/express": "^4.17.13", - "@types/express-serve-static-core": "^4.17.27", - "@types/express-session": "^1.17.4", - "@types/json-schema": "^7.0.9", - "@types/jsonwebtoken": "^8.5.6", - "@types/koa": "^2.13.4", - "@types/koa-bodyparser": "^4.3.5", - "@types/koa-qs": "^2.0.0", - "@types/lodash": "^4.14.178", - "@types/mocha": "^9.0.0", - "@types/mongodb": "^4.0.6", - "@types/node": "^17.0.5", - "@types/node-fetch": "^3.0.2", - "@types/qs": "^6.9.7", - "@types/superagent": "^4.1.14", - "@types/uuid": "^8.3.3", - "ajv": "^8.8.2", - "ajv-formats": "^2.1.1", - "axios": "^0.24.0", - "babel-loader": "^8.2.3", - "bcryptjs": "^2.4.3", - "config": "^3.3.6", - "events": "^3.3.0", - "express": "^4.17.2", - "express-session": "^1.17.2", - "grant": "^5.4.18", - "json-schema": "^0.4.0", - "json-schema-to-ts": "^1.6.4", - "jsonwebtoken": "^8.5.1", - "koa": "^2.13.4", - "koa-bodyparser": "^4.3.0", - "koa-qs": "^3.0.0", - "lodash": "^4.17.21", - "long-timeout": "^0.1.1", - "mocha": "^9.1.3", - "mocha-puppeteer": "^0.14.0", - "mongodb": "^4.2.2", - "node-fetch": "^2.6.1", - "qs": "^6.10.2", - "rxjs": "^7.5.1", - "shx": "^0.3.3", - "sift": "^15.1.3", - "socket.io": "^4.4.0", - "socket.io-client": "^4.4.0", - "superagent": "^6.1.0", - "ts-loader": "^9.2.6", - "ts-node": "^10.4.0", - "uuid": "^8.3.2", - "webpack": "^5.65.0", - "webpack-cli": "^4.9.1", - "webpack-merge": "^5.8.0" - }, - "devDependencies": { - "@typescript-eslint/eslint-plugin": "^5.8.1", - "@typescript-eslint/parser": "^5.8.1", - "eslint": "^8.6.0", - "eslint-plugin-import": "^2.25.3", - "eslint-plugin-prefer-arrow": "^1.2.3", - "lerna": "^4.0.0", - "npm-check-updates": "^12.0.5", - "nyc": "^15.1.0", - "typescript": "^4.5.4" - }, - "engines": { - "node": ">= 12" - }, - "funding": { - "type": "github", - "url": "https://github.com/sponsors/daffl" - } - }, - "node_modules/@babel/code-frame": { - "version": "7.16.7", - "resolved": "https://registry.npmjs.org/@babel/code-frame/-/code-frame-7.16.7.tgz", - "integrity": "sha512-iAXqUn8IIeBTNd72xsFlgaXHkMBMt6y4HJp1tIaK465CWLT/fG1aqB7ykr95gHHmlBdGbFeWWfyB4NJJ0nmeIg==", - "dependencies": { - "@babel/highlight": "^7.16.7" - }, - "engines": { - "node": ">=6.9.0" - } - }, - "node_modules/@babel/compat-data": { - "version": "7.16.4", - "resolved": "https://registry.npmjs.org/@babel/compat-data/-/compat-data-7.16.4.tgz", - "integrity": "sha512-1o/jo7D+kC9ZjHX5v+EHrdjl3PhxMrLSOTGsOdHJ+KL8HCaEK6ehrVL2RS6oHDZp+L7xLirLrPmQtEng769J/Q==", - "engines": { - "node": ">=6.9.0" - } - }, - "node_modules/@babel/core": { - "version": "7.16.7", - "resolved": "https://registry.npmjs.org/@babel/core/-/core-7.16.7.tgz", - "integrity": "sha512-aeLaqcqThRNZYmbMqtulsetOQZ/5gbR/dWruUCJcpas4Qoyy+QeagfDsPdMrqwsPRDNxJvBlRiZxxX7THO7qtA==", - "dependencies": { - "@babel/code-frame": "^7.16.7", - "@babel/generator": "^7.16.7", - "@babel/helper-compilation-targets": "^7.16.7", - "@babel/helper-module-transforms": "^7.16.7", - "@babel/helpers": "^7.16.7", - "@babel/parser": "^7.16.7", - "@babel/template": "^7.16.7", - "@babel/traverse": "^7.16.7", - "@babel/types": "^7.16.7", - "convert-source-map": "^1.7.0", - "debug": "^4.1.0", - "gensync": "^1.0.0-beta.2", - "json5": "^2.1.2", - "semver": "^6.3.0", - "source-map": "^0.5.0" - }, - "engines": { - "node": ">=6.9.0" - }, - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/babel" - } - }, - "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==", - "bin": { - "semver": "bin/semver.js" - } - }, - "node_modules/@babel/core/node_modules/source-map": { - "version": "0.5.7", - "resolved": "https://registry.npmjs.org/source-map/-/source-map-0.5.7.tgz", - "integrity": "sha1-igOdLRAh0i0eoUyA2OpGi6LvP8w=", - "engines": { - "node": ">=0.10.0" - } - }, - "node_modules/@babel/generator": { - "version": "7.16.7", - "resolved": "https://registry.npmjs.org/@babel/generator/-/generator-7.16.7.tgz", - "integrity": "sha512-/ST3Sg8MLGY5HVYmrjOgL60ENux/HfO/CsUh7y4MalThufhE/Ff/6EibFDHi4jiDCaWfJKoqbE6oTh21c5hrRg==", - "dependencies": { - "@babel/types": "^7.16.7", - "jsesc": "^2.5.1", - "source-map": "^0.5.0" - }, - "engines": { - "node": ">=6.9.0" - } - }, - "node_modules/@babel/generator/node_modules/source-map": { - "version": "0.5.7", - "resolved": "https://registry.npmjs.org/source-map/-/source-map-0.5.7.tgz", - "integrity": "sha1-igOdLRAh0i0eoUyA2OpGi6LvP8w=", - "engines": { - "node": ">=0.10.0" - } - }, - "node_modules/@babel/helper-annotate-as-pure": { - "version": "7.16.7", - "resolved": "https://registry.npmjs.org/@babel/helper-annotate-as-pure/-/helper-annotate-as-pure-7.16.7.tgz", - "integrity": "sha512-s6t2w/IPQVTAET1HitoowRGXooX8mCgtuP5195wD/QJPV6wYjpujCGF7JuMODVX2ZAJOf1GT6DT9MHEZvLOFSw==", - "dependencies": { - "@babel/types": "^7.16.7" - }, - "engines": { - "node": ">=6.9.0" - } - }, - "node_modules/@babel/helper-builder-binary-assignment-operator-visitor": { - "version": "7.16.7", - "resolved": "https://registry.npmjs.org/@babel/helper-builder-binary-assignment-operator-visitor/-/helper-builder-binary-assignment-operator-visitor-7.16.7.tgz", - "integrity": "sha512-C6FdbRaxYjwVu/geKW4ZeQ0Q31AftgRcdSnZ5/jsH6BzCJbtvXvhpfkbkThYSuutZA7nCXpPR6AD9zd1dprMkA==", - "dependencies": { - "@babel/helper-explode-assignable-expression": "^7.16.7", - "@babel/types": "^7.16.7" - }, - "engines": { - "node": ">=6.9.0" - } - }, - "node_modules/@babel/helper-compilation-targets": { - "version": "7.16.7", - "resolved": "https://registry.npmjs.org/@babel/helper-compilation-targets/-/helper-compilation-targets-7.16.7.tgz", - "integrity": "sha512-mGojBwIWcwGD6rfqgRXVlVYmPAv7eOpIemUG3dGnDdCY4Pae70ROij3XmfrH6Fa1h1aiDylpglbZyktfzyo/hA==", - "dependencies": { - "@babel/compat-data": "^7.16.4", - "@babel/helper-validator-option": "^7.16.7", - "browserslist": "^4.17.5", - "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==", - "bin": { - "semver": "bin/semver.js" - } - }, - "node_modules/@babel/helper-create-class-features-plugin": { - "version": "7.16.7", - "resolved": "https://registry.npmjs.org/@babel/helper-create-class-features-plugin/-/helper-create-class-features-plugin-7.16.7.tgz", - "integrity": "sha512-kIFozAvVfK05DM4EVQYKK+zteWvY85BFdGBRQBytRyY3y+6PX0DkDOn/CZ3lEuczCfrCxEzwt0YtP/87YPTWSw==", - "dependencies": { - "@babel/helper-annotate-as-pure": "^7.16.7", - "@babel/helper-environment-visitor": "^7.16.7", - "@babel/helper-function-name": "^7.16.7", - "@babel/helper-member-expression-to-functions": "^7.16.7", - "@babel/helper-optimise-call-expression": "^7.16.7", - "@babel/helper-replace-supers": "^7.16.7", - "@babel/helper-split-export-declaration": "^7.16.7" - }, - "engines": { - "node": ">=6.9.0" - }, - "peerDependencies": { - "@babel/core": "^7.0.0" - } - }, - "node_modules/@babel/helper-create-regexp-features-plugin": { - "version": "7.16.7", - "resolved": "https://registry.npmjs.org/@babel/helper-create-regexp-features-plugin/-/helper-create-regexp-features-plugin-7.16.7.tgz", - "integrity": "sha512-fk5A6ymfp+O5+p2yCkXAu5Kyj6v0xh0RBeNcAkYUMDvvAAoxvSKXn+Jb37t/yWFiQVDFK1ELpUTD8/aLhCPu+g==", - "dependencies": { - "@babel/helper-annotate-as-pure": "^7.16.7", - "regexpu-core": "^4.7.1" - }, - "engines": { - "node": ">=6.9.0" - }, - "peerDependencies": { - "@babel/core": "^7.0.0" - } - }, - "node_modules/@babel/helper-define-polyfill-provider": { - "version": "0.3.0", - "resolved": "https://registry.npmjs.org/@babel/helper-define-polyfill-provider/-/helper-define-polyfill-provider-0.3.0.tgz", - "integrity": "sha512-7hfT8lUljl/tM3h+izTX/pO3W3frz2ok6Pk+gzys8iJqDfZrZy2pXjRTZAvG2YmfHun1X4q8/UZRLatMfqc5Tg==", - "dependencies": { - "@babel/helper-compilation-targets": "^7.13.0", - "@babel/helper-module-imports": "^7.12.13", - "@babel/helper-plugin-utils": "^7.13.0", - "@babel/traverse": "^7.13.0", - "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-define-polyfill-provider/node_modules/semver": { - "version": "6.3.0", - "resolved": "https://registry.npmjs.org/semver/-/semver-6.3.0.tgz", - "integrity": "sha512-b39TBaTSfV6yBrapU89p5fKekE2m/NwnDocOVruQFS1/veMgdzuPcnOM34M6CwxW8jH/lxEa5rBoDeUwu5HHTw==", - "bin": { - "semver": "bin/semver.js" - } - }, - "node_modules/@babel/helper-environment-visitor": { - "version": "7.16.7", - "resolved": "https://registry.npmjs.org/@babel/helper-environment-visitor/-/helper-environment-visitor-7.16.7.tgz", - "integrity": "sha512-SLLb0AAn6PkUeAfKJCCOl9e1R53pQlGAfc4y4XuMRZfqeMYLE0dM1LMhqbGAlGQY0lfw5/ohoYWAe9V1yibRag==", - "dependencies": { - "@babel/types": "^7.16.7" - }, - "engines": { - "node": ">=6.9.0" - } - }, - "node_modules/@babel/helper-explode-assignable-expression": { - "version": "7.16.7", - "resolved": "https://registry.npmjs.org/@babel/helper-explode-assignable-expression/-/helper-explode-assignable-expression-7.16.7.tgz", - "integrity": "sha512-KyUenhWMC8VrxzkGP0Jizjo4/Zx+1nNZhgocs+gLzyZyB8SHidhoq9KK/8Ato4anhwsivfkBLftky7gvzbZMtQ==", - "dependencies": { - "@babel/types": "^7.16.7" - }, - "engines": { - "node": ">=6.9.0" - } - }, - "node_modules/@babel/helper-function-name": { - "version": "7.16.7", - "resolved": "https://registry.npmjs.org/@babel/helper-function-name/-/helper-function-name-7.16.7.tgz", - "integrity": "sha512-QfDfEnIUyyBSR3HtrtGECuZ6DAyCkYFp7GHl75vFtTnn6pjKeK0T1DB5lLkFvBea8MdaiUABx3osbgLyInoejA==", - "dependencies": { - "@babel/helper-get-function-arity": "^7.16.7", - "@babel/template": "^7.16.7", - "@babel/types": "^7.16.7" - }, - "engines": { - "node": ">=6.9.0" - } - }, - "node_modules/@babel/helper-get-function-arity": { - "version": "7.16.7", - "resolved": "https://registry.npmjs.org/@babel/helper-get-function-arity/-/helper-get-function-arity-7.16.7.tgz", - "integrity": "sha512-flc+RLSOBXzNzVhcLu6ujeHUrD6tANAOU5ojrRx/as+tbzf8+stUCj7+IfRRoAbEZqj/ahXEMsjhOhgeZsrnTw==", - "dependencies": { - "@babel/types": "^7.16.7" - }, - "engines": { - "node": ">=6.9.0" - } - }, - "node_modules/@babel/helper-hoist-variables": { - "version": "7.16.7", - "resolved": "https://registry.npmjs.org/@babel/helper-hoist-variables/-/helper-hoist-variables-7.16.7.tgz", - "integrity": "sha512-m04d/0Op34H5v7pbZw6pSKP7weA6lsMvfiIAMeIvkY/R4xQtBSMFEigu9QTZ2qB/9l22vsxtM8a+Q8CzD255fg==", - "dependencies": { - "@babel/types": "^7.16.7" - }, - "engines": { - "node": ">=6.9.0" - } - }, - "node_modules/@babel/helper-member-expression-to-functions": { - "version": "7.16.7", - "resolved": "https://registry.npmjs.org/@babel/helper-member-expression-to-functions/-/helper-member-expression-to-functions-7.16.7.tgz", - "integrity": "sha512-VtJ/65tYiU/6AbMTDwyoXGPKHgTsfRarivm+YbB5uAzKUyuPjgZSgAFeG87FCigc7KNHu2Pegh1XIT3lXjvz3Q==", - "dependencies": { - "@babel/types": "^7.16.7" - }, - "engines": { - "node": ">=6.9.0" - } - }, - "node_modules/@babel/helper-module-imports": { - "version": "7.16.7", - "resolved": "https://registry.npmjs.org/@babel/helper-module-imports/-/helper-module-imports-7.16.7.tgz", - "integrity": "sha512-LVtS6TqjJHFc+nYeITRo6VLXve70xmq7wPhWTqDJusJEgGmkAACWwMiTNrvfoQo6hEhFwAIixNkvB0jPXDL8Wg==", - "dependencies": { - "@babel/types": "^7.16.7" - }, - "engines": { - "node": ">=6.9.0" - } - }, - "node_modules/@babel/helper-module-transforms": { - "version": "7.16.7", - "resolved": "https://registry.npmjs.org/@babel/helper-module-transforms/-/helper-module-transforms-7.16.7.tgz", - "integrity": "sha512-gaqtLDxJEFCeQbYp9aLAefjhkKdjKcdh6DB7jniIGU3Pz52WAmP268zK0VgPz9hUNkMSYeH976K2/Y6yPadpng==", - "dependencies": { - "@babel/helper-environment-visitor": "^7.16.7", - "@babel/helper-module-imports": "^7.16.7", - "@babel/helper-simple-access": "^7.16.7", - "@babel/helper-split-export-declaration": "^7.16.7", - "@babel/helper-validator-identifier": "^7.16.7", - "@babel/template": "^7.16.7", - "@babel/traverse": "^7.16.7", - "@babel/types": "^7.16.7" - }, - "engines": { - "node": ">=6.9.0" - } - }, - "node_modules/@babel/helper-optimise-call-expression": { - "version": "7.16.7", - "resolved": "https://registry.npmjs.org/@babel/helper-optimise-call-expression/-/helper-optimise-call-expression-7.16.7.tgz", - "integrity": "sha512-EtgBhg7rd/JcnpZFXpBy0ze1YRfdm7BnBX4uKMBd3ixa3RGAE002JZB66FJyNH7g0F38U05pXmA5P8cBh7z+1w==", - "dependencies": { - "@babel/types": "^7.16.7" - }, - "engines": { - "node": ">=6.9.0" - } - }, - "node_modules/@babel/helper-plugin-utils": { - "version": "7.16.7", - "resolved": "https://registry.npmjs.org/@babel/helper-plugin-utils/-/helper-plugin-utils-7.16.7.tgz", - "integrity": "sha512-Qg3Nk7ZxpgMrsox6HreY1ZNKdBq7K72tDSliA6dCl5f007jR4ne8iD5UzuNnCJH2xBf2BEEVGr+/OL6Gdp7RxA==", - "engines": { - "node": ">=6.9.0" - } - }, - "node_modules/@babel/helper-remap-async-to-generator": { - "version": "7.16.7", - "resolved": "https://registry.npmjs.org/@babel/helper-remap-async-to-generator/-/helper-remap-async-to-generator-7.16.7.tgz", - "integrity": "sha512-C3o117GnP/j/N2OWo+oepeWbFEKRfNaay+F1Eo5Mj3A1SRjyx+qaFhm23nlipub7Cjv2azdUUiDH+VlpdwUFRg==", - "dependencies": { - "@babel/helper-annotate-as-pure": "^7.16.7", - "@babel/helper-wrap-function": "^7.16.7", - "@babel/types": "^7.16.7" - }, - "engines": { - "node": ">=6.9.0" - } - }, - "node_modules/@babel/helper-replace-supers": { - "version": "7.16.7", - "resolved": "https://registry.npmjs.org/@babel/helper-replace-supers/-/helper-replace-supers-7.16.7.tgz", - "integrity": "sha512-y9vsWilTNaVnVh6xiJfABzsNpgDPKev9HnAgz6Gb1p6UUwf9NepdlsV7VXGCftJM+jqD5f7JIEubcpLjZj5dBw==", - "dependencies": { - "@babel/helper-environment-visitor": "^7.16.7", - "@babel/helper-member-expression-to-functions": "^7.16.7", - "@babel/helper-optimise-call-expression": "^7.16.7", - "@babel/traverse": "^7.16.7", - "@babel/types": "^7.16.7" - }, - "engines": { - "node": ">=6.9.0" - } - }, - "node_modules/@babel/helper-simple-access": { - "version": "7.16.7", - "resolved": "https://registry.npmjs.org/@babel/helper-simple-access/-/helper-simple-access-7.16.7.tgz", - "integrity": "sha512-ZIzHVyoeLMvXMN/vok/a4LWRy8G2v205mNP0XOuf9XRLyX5/u9CnVulUtDgUTama3lT+bf/UqucuZjqiGuTS1g==", - "dependencies": { - "@babel/types": "^7.16.7" - }, - "engines": { - "node": ">=6.9.0" - } - }, - "node_modules/@babel/helper-skip-transparent-expression-wrappers": { - "version": "7.16.0", - "resolved": "https://registry.npmjs.org/@babel/helper-skip-transparent-expression-wrappers/-/helper-skip-transparent-expression-wrappers-7.16.0.tgz", - "integrity": "sha512-+il1gTy0oHwUsBQZyJvukbB4vPMdcYBrFHa0Uc4AizLxbq6BOYC51Rv4tWocX9BLBDLZ4kc6qUFpQ6HRgL+3zw==", - "dependencies": { - "@babel/types": "^7.16.0" - }, - "engines": { - "node": ">=6.9.0" - } - }, - "node_modules/@babel/helper-split-export-declaration": { - "version": "7.16.7", - "resolved": "https://registry.npmjs.org/@babel/helper-split-export-declaration/-/helper-split-export-declaration-7.16.7.tgz", - "integrity": "sha512-xbWoy/PFoxSWazIToT9Sif+jJTlrMcndIsaOKvTA6u7QEo7ilkRZpjew18/W3c7nm8fXdUDXh02VXTbZ0pGDNw==", - "dependencies": { - "@babel/types": "^7.16.7" - }, - "engines": { - "node": ">=6.9.0" - } - }, - "node_modules/@babel/helper-validator-identifier": { - "version": "7.16.7", - "resolved": "https://registry.npmjs.org/@babel/helper-validator-identifier/-/helper-validator-identifier-7.16.7.tgz", - "integrity": "sha512-hsEnFemeiW4D08A5gUAZxLBTXpZ39P+a+DGDsHw1yxqyQ/jzFEnxf5uTEGp+3bzAbNOxU1paTgYS4ECU/IgfDw==", - "engines": { - "node": ">=6.9.0" - } - }, - "node_modules/@babel/helper-validator-option": { - "version": "7.16.7", - "resolved": "https://registry.npmjs.org/@babel/helper-validator-option/-/helper-validator-option-7.16.7.tgz", - "integrity": "sha512-TRtenOuRUVo9oIQGPC5G9DgK4743cdxvtOw0weQNpZXaS16SCBi5MNjZF8vba3ETURjZpTbVn7Vvcf2eAwFozQ==", - "engines": { - "node": ">=6.9.0" - } - }, - "node_modules/@babel/helper-wrap-function": { - "version": "7.16.7", - "resolved": "https://registry.npmjs.org/@babel/helper-wrap-function/-/helper-wrap-function-7.16.7.tgz", - "integrity": "sha512-7a9sABeVwcunnztZZ7WTgSw6jVYLzM1wua0Z4HIXm9S3/HC96WKQTkFgGEaj5W06SHHihPJ6Le6HzS5cGOQMNw==", - "dependencies": { - "@babel/helper-function-name": "^7.16.7", - "@babel/template": "^7.16.7", - "@babel/traverse": "^7.16.7", - "@babel/types": "^7.16.7" - }, - "engines": { - "node": ">=6.9.0" - } - }, - "node_modules/@babel/helpers": { - "version": "7.16.7", - "resolved": "https://registry.npmjs.org/@babel/helpers/-/helpers-7.16.7.tgz", - "integrity": "sha512-9ZDoqtfY7AuEOt3cxchfii6C7GDyyMBffktR5B2jvWv8u2+efwvpnVKXMWzNehqy68tKgAfSwfdw/lWpthS2bw==", - "dependencies": { - "@babel/template": "^7.16.7", - "@babel/traverse": "^7.16.7", - "@babel/types": "^7.16.7" - }, - "engines": { - "node": ">=6.9.0" - } - }, - "node_modules/@babel/highlight": { - "version": "7.16.7", - "resolved": "https://registry.npmjs.org/@babel/highlight/-/highlight-7.16.7.tgz", - "integrity": "sha512-aKpPMfLvGO3Q97V0qhw/V2SWNWlwfJknuwAunU7wZLSfrM4xTBvg7E5opUVi1kJTBKihE38CPg4nBiqX83PWYw==", - "dependencies": { - "@babel/helper-validator-identifier": "^7.16.7", - "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==", - "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==", - "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==", - "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": "sha1-p9BVi9icQveV3UIyj3QIMcpTvCU=" - }, - "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": "sha1-G2HAViGQqN/2rjuyzwIAyhMLhtQ=", - "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": "sha1-tdRU3CGZriJWmfNGfloH87lVuv0=", - "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==", - "dependencies": { - "has-flag": "^3.0.0" - }, - "engines": { - "node": ">=4" - } - }, - "node_modules/@babel/parser": { - "version": "7.16.7", - "resolved": "https://registry.npmjs.org/@babel/parser/-/parser-7.16.7.tgz", - "integrity": "sha512-sR4eaSrnM7BV7QPzGfEX5paG/6wrZM3I0HDzfIAK06ESvo9oy3xBuVBxE3MbQaKNhvg8g/ixjMWo2CGpzpHsDA==", - "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.16.7", - "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.16.7.tgz", - "integrity": "sha512-anv/DObl7waiGEnC24O9zqL0pSuI9hljihqiDuFHC8d7/bjr/4RLGPWuc8rYOff/QPzbEPSkzG8wGG9aDuhHRg==", - "dependencies": { - "@babel/helper-plugin-utils": "^7.16.7" - }, - "engines": { - "node": ">=6.9.0" - }, - "peerDependencies": { - "@babel/core": "^7.0.0" - } - }, - "node_modules/@babel/plugin-bugfix-v8-spread-parameters-in-optional-chaining": { - "version": "7.16.7", - "resolved": "https://registry.npmjs.org/@babel/plugin-bugfix-v8-spread-parameters-in-optional-chaining/-/plugin-bugfix-v8-spread-parameters-in-optional-chaining-7.16.7.tgz", - "integrity": "sha512-di8vUHRdf+4aJ7ltXhaDbPoszdkh59AQtJM5soLsuHpQJdFQZOA4uGj0V2u/CZ8bJ/u8ULDL5yq6FO/bCXnKHw==", - "dependencies": { - "@babel/helper-plugin-utils": "^7.16.7", - "@babel/helper-skip-transparent-expression-wrappers": "^7.16.0", - "@babel/plugin-proposal-optional-chaining": "^7.16.7" - }, - "engines": { - "node": ">=6.9.0" - }, - "peerDependencies": { - "@babel/core": "^7.13.0" - } - }, - "node_modules/@babel/plugin-proposal-async-generator-functions": { - "version": "7.16.7", - "resolved": "https://registry.npmjs.org/@babel/plugin-proposal-async-generator-functions/-/plugin-proposal-async-generator-functions-7.16.7.tgz", - "integrity": "sha512-TTXBT3A5c11eqRzaC6beO6rlFT3Mo9C2e8eB44tTr52ESXSK2CIc2fOp1ynpAwQA8HhBMho+WXhMHWlAe3xkpw==", - "dependencies": { - "@babel/helper-plugin-utils": "^7.16.7", - "@babel/helper-remap-async-to-generator": "^7.16.7", - "@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.16.7", - "resolved": "https://registry.npmjs.org/@babel/plugin-proposal-class-properties/-/plugin-proposal-class-properties-7.16.7.tgz", - "integrity": "sha512-IobU0Xme31ewjYOShSIqd/ZGM/r/cuOz2z0MDbNrhF5FW+ZVgi0f2lyeoj9KFPDOAqsYxmLWZte1WOwlvY9aww==", - "dependencies": { - "@babel/helper-create-class-features-plugin": "^7.16.7", - "@babel/helper-plugin-utils": "^7.16.7" - }, - "engines": { - "node": ">=6.9.0" - }, - "peerDependencies": { - "@babel/core": "^7.0.0-0" - } - }, - "node_modules/@babel/plugin-proposal-class-static-block": { - "version": "7.16.7", - "resolved": "https://registry.npmjs.org/@babel/plugin-proposal-class-static-block/-/plugin-proposal-class-static-block-7.16.7.tgz", - "integrity": "sha512-dgqJJrcZoG/4CkMopzhPJjGxsIe9A8RlkQLnL/Vhhx8AA9ZuaRwGSlscSh42hazc7WSrya/IK7mTeoF0DP9tEw==", - "dependencies": { - "@babel/helper-create-class-features-plugin": "^7.16.7", - "@babel/helper-plugin-utils": "^7.16.7", - "@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.16.7", - "resolved": "https://registry.npmjs.org/@babel/plugin-proposal-dynamic-import/-/plugin-proposal-dynamic-import-7.16.7.tgz", - "integrity": "sha512-I8SW9Ho3/8DRSdmDdH3gORdyUuYnk1m4cMxUAdu5oy4n3OfN8flDEH+d60iG7dUfi0KkYwSvoalHzzdRzpWHTg==", - "dependencies": { - "@babel/helper-plugin-utils": "^7.16.7", - "@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.16.7", - "resolved": "https://registry.npmjs.org/@babel/plugin-proposal-export-namespace-from/-/plugin-proposal-export-namespace-from-7.16.7.tgz", - "integrity": "sha512-ZxdtqDXLRGBL64ocZcs7ovt71L3jhC1RGSyR996svrCi3PYqHNkb3SwPJCs8RIzD86s+WPpt2S73+EHCGO+NUA==", - "dependencies": { - "@babel/helper-plugin-utils": "^7.16.7", - "@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.16.7", - "resolved": "https://registry.npmjs.org/@babel/plugin-proposal-json-strings/-/plugin-proposal-json-strings-7.16.7.tgz", - "integrity": "sha512-lNZ3EEggsGY78JavgbHsK9u5P3pQaW7k4axlgFLYkMd7UBsiNahCITShLjNQschPyjtO6dADrL24757IdhBrsQ==", - "dependencies": { - "@babel/helper-plugin-utils": "^7.16.7", - "@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.16.7", - "resolved": "https://registry.npmjs.org/@babel/plugin-proposal-logical-assignment-operators/-/plugin-proposal-logical-assignment-operators-7.16.7.tgz", - "integrity": "sha512-K3XzyZJGQCr00+EtYtrDjmwX7o7PLK6U9bi1nCwkQioRFVUv6dJoxbQjtWVtP+bCPy82bONBKG8NPyQ4+i6yjg==", - "dependencies": { - "@babel/helper-plugin-utils": "^7.16.7", - "@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.16.7", - "resolved": "https://registry.npmjs.org/@babel/plugin-proposal-nullish-coalescing-operator/-/plugin-proposal-nullish-coalescing-operator-7.16.7.tgz", - "integrity": "sha512-aUOrYU3EVtjf62jQrCj63pYZ7k6vns2h/DQvHPWGmsJRYzWXZ6/AsfgpiRy6XiuIDADhJzP2Q9MwSMKauBQ+UQ==", - "dependencies": { - "@babel/helper-plugin-utils": "^7.16.7", - "@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.16.7", - "resolved": "https://registry.npmjs.org/@babel/plugin-proposal-numeric-separator/-/plugin-proposal-numeric-separator-7.16.7.tgz", - "integrity": "sha512-vQgPMknOIgiuVqbokToyXbkY/OmmjAzr/0lhSIbG/KmnzXPGwW/AdhdKpi+O4X/VkWiWjnkKOBiqJrTaC98VKw==", - "dependencies": { - "@babel/helper-plugin-utils": "^7.16.7", - "@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.16.7", - "resolved": "https://registry.npmjs.org/@babel/plugin-proposal-object-rest-spread/-/plugin-proposal-object-rest-spread-7.16.7.tgz", - "integrity": "sha512-3O0Y4+dw94HA86qSg9IHfyPktgR7q3gpNVAeiKQd+8jBKFaU5NQS1Yatgo4wY+UFNuLjvxcSmzcsHqrhgTyBUA==", - "dependencies": { - "@babel/compat-data": "^7.16.4", - "@babel/helper-compilation-targets": "^7.16.7", - "@babel/helper-plugin-utils": "^7.16.7", - "@babel/plugin-syntax-object-rest-spread": "^7.8.3", - "@babel/plugin-transform-parameters": "^7.16.7" - }, - "engines": { - "node": ">=6.9.0" - }, - "peerDependencies": { - "@babel/core": "^7.0.0-0" - } - }, - "node_modules/@babel/plugin-proposal-optional-catch-binding": { - "version": "7.16.7", - "resolved": "https://registry.npmjs.org/@babel/plugin-proposal-optional-catch-binding/-/plugin-proposal-optional-catch-binding-7.16.7.tgz", - "integrity": "sha512-eMOH/L4OvWSZAE1VkHbr1vckLG1WUcHGJSLqqQwl2GaUqG6QjddvrOaTUMNYiv77H5IKPMZ9U9P7EaHwvAShfA==", - "dependencies": { - "@babel/helper-plugin-utils": "^7.16.7", - "@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.16.7", - "resolved": "https://registry.npmjs.org/@babel/plugin-proposal-optional-chaining/-/plugin-proposal-optional-chaining-7.16.7.tgz", - "integrity": "sha512-eC3xy+ZrUcBtP7x+sq62Q/HYd674pPTb/77XZMb5wbDPGWIdUbSr4Agr052+zaUPSb+gGRnjxXfKFvx5iMJ+DA==", - "dependencies": { - "@babel/helper-plugin-utils": "^7.16.7", - "@babel/helper-skip-transparent-expression-wrappers": "^7.16.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.16.7", - "resolved": "https://registry.npmjs.org/@babel/plugin-proposal-private-methods/-/plugin-proposal-private-methods-7.16.7.tgz", - "integrity": "sha512-7twV3pzhrRxSwHeIvFE6coPgvo+exNDOiGUMg39o2LiLo1Y+4aKpfkcLGcg1UHonzorCt7SNXnoMyCnnIOA8Sw==", - "dependencies": { - "@babel/helper-create-class-features-plugin": "^7.16.7", - "@babel/helper-plugin-utils": "^7.16.7" - }, - "engines": { - "node": ">=6.9.0" - }, - "peerDependencies": { - "@babel/core": "^7.0.0-0" - } - }, - "node_modules/@babel/plugin-proposal-private-property-in-object": { - "version": "7.16.7", - "resolved": "https://registry.npmjs.org/@babel/plugin-proposal-private-property-in-object/-/plugin-proposal-private-property-in-object-7.16.7.tgz", - "integrity": "sha512-rMQkjcOFbm+ufe3bTZLyOfsOUOxyvLXZJCTARhJr+8UMSoZmqTe1K1BgkFcrW37rAchWg57yI69ORxiWvUINuQ==", - "dependencies": { - "@babel/helper-annotate-as-pure": "^7.16.7", - "@babel/helper-create-class-features-plugin": "^7.16.7", - "@babel/helper-plugin-utils": "^7.16.7", - "@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.16.7", - "resolved": "https://registry.npmjs.org/@babel/plugin-proposal-unicode-property-regex/-/plugin-proposal-unicode-property-regex-7.16.7.tgz", - "integrity": "sha512-QRK0YI/40VLhNVGIjRNAAQkEHws0cswSdFFjpFyt943YmJIU1da9uW63Iu6NFV6CxTZW5eTDCrwZUstBWgp/Rg==", - "dependencies": { - "@babel/helper-create-regexp-features-plugin": "^7.16.7", - "@babel/helper-plugin-utils": "^7.16.7" - }, - "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==", - "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==", - "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==", - "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==", - "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==", - "dependencies": { - "@babel/helper-plugin-utils": "^7.8.3" - }, - "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==", - "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==", - "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==", - "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==", - "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==", - "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==", - "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==", - "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==", - "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==", - "dependencies": { - "@babel/helper-plugin-utils": "^7.14.5" - }, - "engines": { - "node": ">=6.9.0" - }, - "peerDependencies": { - "@babel/core": "^7.0.0-0" - } - }, - "node_modules/@babel/plugin-transform-arrow-functions": { - "version": "7.16.7", - "resolved": "https://registry.npmjs.org/@babel/plugin-transform-arrow-functions/-/plugin-transform-arrow-functions-7.16.7.tgz", - "integrity": "sha512-9ffkFFMbvzTvv+7dTp/66xvZAWASuPD5Tl9LK3Z9vhOmANo6j94rik+5YMBt4CwHVMWLWpMsriIc2zsa3WW3xQ==", - "dependencies": { - "@babel/helper-plugin-utils": "^7.16.7" - }, - "engines": { - "node": ">=6.9.0" - }, - "peerDependencies": { - "@babel/core": "^7.0.0-0" - } - }, - "node_modules/@babel/plugin-transform-async-to-generator": { - "version": "7.16.7", - "resolved": "https://registry.npmjs.org/@babel/plugin-transform-async-to-generator/-/plugin-transform-async-to-generator-7.16.7.tgz", - "integrity": "sha512-pFEfjnK4DfXCfAlA5I98BYdDJD8NltMzx19gt6DAmfE+2lXRfPUoa0/5SUjT4+TDE1W/rcxU/1lgN55vpAjjdg==", - "dependencies": { - "@babel/helper-module-imports": "^7.16.7", - "@babel/helper-plugin-utils": "^7.16.7", - "@babel/helper-remap-async-to-generator": "^7.16.7" - }, - "engines": { - "node": ">=6.9.0" - }, - "peerDependencies": { - "@babel/core": "^7.0.0-0" - } - }, - "node_modules/@babel/plugin-transform-block-scoped-functions": { - "version": "7.16.7", - "resolved": "https://registry.npmjs.org/@babel/plugin-transform-block-scoped-functions/-/plugin-transform-block-scoped-functions-7.16.7.tgz", - "integrity": "sha512-JUuzlzmF40Z9cXyytcbZEZKckgrQzChbQJw/5PuEHYeqzCsvebDx0K0jWnIIVcmmDOAVctCgnYs0pMcrYj2zJg==", - "dependencies": { - "@babel/helper-plugin-utils": "^7.16.7" - }, - "engines": { - "node": ">=6.9.0" - }, - "peerDependencies": { - "@babel/core": "^7.0.0-0" - } - }, - "node_modules/@babel/plugin-transform-block-scoping": { - "version": "7.16.7", - "resolved": "https://registry.npmjs.org/@babel/plugin-transform-block-scoping/-/plugin-transform-block-scoping-7.16.7.tgz", - "integrity": "sha512-ObZev2nxVAYA4bhyusELdo9hb3H+A56bxH3FZMbEImZFiEDYVHXQSJ1hQKFlDnlt8G9bBrCZ5ZpURZUrV4G5qQ==", - "dependencies": { - "@babel/helper-plugin-utils": "^7.16.7" - }, - "engines": { - "node": ">=6.9.0" - }, - "peerDependencies": { - "@babel/core": "^7.0.0-0" - } - }, - "node_modules/@babel/plugin-transform-classes": { - "version": "7.16.7", - "resolved": "https://registry.npmjs.org/@babel/plugin-transform-classes/-/plugin-transform-classes-7.16.7.tgz", - "integrity": "sha512-WY7og38SFAGYRe64BrjKf8OrE6ulEHtr5jEYaZMwox9KebgqPi67Zqz8K53EKk1fFEJgm96r32rkKZ3qA2nCWQ==", - "dependencies": { - "@babel/helper-annotate-as-pure": "^7.16.7", - "@babel/helper-environment-visitor": "^7.16.7", - "@babel/helper-function-name": "^7.16.7", - "@babel/helper-optimise-call-expression": "^7.16.7", - "@babel/helper-plugin-utils": "^7.16.7", - "@babel/helper-replace-supers": "^7.16.7", - "@babel/helper-split-export-declaration": "^7.16.7", - "globals": "^11.1.0" - }, - "engines": { - "node": ">=6.9.0" - }, - "peerDependencies": { - "@babel/core": "^7.0.0-0" - } - }, - "node_modules/@babel/plugin-transform-classes/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==", - "engines": { - "node": ">=4" - } - }, - "node_modules/@babel/plugin-transform-computed-properties": { - "version": "7.16.7", - "resolved": "https://registry.npmjs.org/@babel/plugin-transform-computed-properties/-/plugin-transform-computed-properties-7.16.7.tgz", - "integrity": "sha512-gN72G9bcmenVILj//sv1zLNaPyYcOzUho2lIJBMh/iakJ9ygCo/hEF9cpGb61SCMEDxbbyBoVQxrt+bWKu5KGw==", - "dependencies": { - "@babel/helper-plugin-utils": "^7.16.7" - }, - "engines": { - "node": ">=6.9.0" - }, - "peerDependencies": { - "@babel/core": "^7.0.0-0" - } - }, - "node_modules/@babel/plugin-transform-destructuring": { - "version": "7.16.7", - "resolved": "https://registry.npmjs.org/@babel/plugin-transform-destructuring/-/plugin-transform-destructuring-7.16.7.tgz", - "integrity": "sha512-VqAwhTHBnu5xBVDCvrvqJbtLUa++qZaWC0Fgr2mqokBlulZARGyIvZDoqbPlPaKImQ9dKAcCzbv+ul//uqu70A==", - "dependencies": { - "@babel/helper-plugin-utils": "^7.16.7" - }, - "engines": { - "node": ">=6.9.0" - }, - "peerDependencies": { - "@babel/core": "^7.0.0-0" - } - }, - "node_modules/@babel/plugin-transform-dotall-regex": { - "version": "7.16.7", - "resolved": "https://registry.npmjs.org/@babel/plugin-transform-dotall-regex/-/plugin-transform-dotall-regex-7.16.7.tgz", - "integrity": "sha512-Lyttaao2SjZF6Pf4vk1dVKv8YypMpomAbygW+mU5cYP3S5cWTfCJjG8xV6CFdzGFlfWK81IjL9viiTvpb6G7gQ==", - "dependencies": { - "@babel/helper-create-regexp-features-plugin": "^7.16.7", - "@babel/helper-plugin-utils": "^7.16.7" - }, - "engines": { - "node": ">=6.9.0" - }, - "peerDependencies": { - "@babel/core": "^7.0.0-0" - } - }, - "node_modules/@babel/plugin-transform-duplicate-keys": { - "version": "7.16.7", - "resolved": "https://registry.npmjs.org/@babel/plugin-transform-duplicate-keys/-/plugin-transform-duplicate-keys-7.16.7.tgz", - "integrity": "sha512-03DvpbRfvWIXyK0/6QiR1KMTWeT6OcQ7tbhjrXyFS02kjuX/mu5Bvnh5SDSWHxyawit2g5aWhKwI86EE7GUnTw==", - "dependencies": { - "@babel/helper-plugin-utils": "^7.16.7" - }, - "engines": { - "node": ">=6.9.0" - }, - "peerDependencies": { - "@babel/core": "^7.0.0-0" - } - }, - "node_modules/@babel/plugin-transform-exponentiation-operator": { - "version": "7.16.7", - "resolved": "https://registry.npmjs.org/@babel/plugin-transform-exponentiation-operator/-/plugin-transform-exponentiation-operator-7.16.7.tgz", - "integrity": "sha512-8UYLSlyLgRixQvlYH3J2ekXFHDFLQutdy7FfFAMm3CPZ6q9wHCwnUyiXpQCe3gVVnQlHc5nsuiEVziteRNTXEA==", - "dependencies": { - "@babel/helper-builder-binary-assignment-operator-visitor": "^7.16.7", - "@babel/helper-plugin-utils": "^7.16.7" - }, - "engines": { - "node": ">=6.9.0" - }, - "peerDependencies": { - "@babel/core": "^7.0.0-0" - } - }, - "node_modules/@babel/plugin-transform-for-of": { - "version": "7.16.7", - "resolved": "https://registry.npmjs.org/@babel/plugin-transform-for-of/-/plugin-transform-for-of-7.16.7.tgz", - "integrity": "sha512-/QZm9W92Ptpw7sjI9Nx1mbcsWz33+l8kuMIQnDwgQBG5s3fAfQvkRjQ7NqXhtNcKOnPkdICmUHyCaWW06HCsqg==", - "dependencies": { - "@babel/helper-plugin-utils": "^7.16.7" - }, - "engines": { - "node": ">=6.9.0" - }, - "peerDependencies": { - "@babel/core": "^7.0.0-0" - } - }, - "node_modules/@babel/plugin-transform-function-name": { - "version": "7.16.7", - "resolved": "https://registry.npmjs.org/@babel/plugin-transform-function-name/-/plugin-transform-function-name-7.16.7.tgz", - "integrity": "sha512-SU/C68YVwTRxqWj5kgsbKINakGag0KTgq9f2iZEXdStoAbOzLHEBRYzImmA6yFo8YZhJVflvXmIHUO7GWHmxxA==", - "dependencies": { - "@babel/helper-compilation-targets": "^7.16.7", - "@babel/helper-function-name": "^7.16.7", - "@babel/helper-plugin-utils": "^7.16.7" - }, - "engines": { - "node": ">=6.9.0" - }, - "peerDependencies": { - "@babel/core": "^7.0.0-0" - } - }, - "node_modules/@babel/plugin-transform-literals": { - "version": "7.16.7", - "resolved": "https://registry.npmjs.org/@babel/plugin-transform-literals/-/plugin-transform-literals-7.16.7.tgz", - "integrity": "sha512-6tH8RTpTWI0s2sV6uq3e/C9wPo4PTqqZps4uF0kzQ9/xPLFQtipynvmT1g/dOfEJ+0EQsHhkQ/zyRId8J2b8zQ==", - "dependencies": { - "@babel/helper-plugin-utils": "^7.16.7" - }, - "engines": { - "node": ">=6.9.0" - }, - "peerDependencies": { - "@babel/core": "^7.0.0-0" - } - }, - "node_modules/@babel/plugin-transform-member-expression-literals": { - "version": "7.16.7", - "resolved": "https://registry.npmjs.org/@babel/plugin-transform-member-expression-literals/-/plugin-transform-member-expression-literals-7.16.7.tgz", - "integrity": "sha512-mBruRMbktKQwbxaJof32LT9KLy2f3gH+27a5XSuXo6h7R3vqltl0PgZ80C8ZMKw98Bf8bqt6BEVi3svOh2PzMw==", - "dependencies": { - "@babel/helper-plugin-utils": "^7.16.7" - }, - "engines": { - "node": ">=6.9.0" - }, - "peerDependencies": { - "@babel/core": "^7.0.0-0" - } - }, - "node_modules/@babel/plugin-transform-modules-amd": { - "version": "7.16.7", - "resolved": "https://registry.npmjs.org/@babel/plugin-transform-modules-amd/-/plugin-transform-modules-amd-7.16.7.tgz", - "integrity": "sha512-KaaEtgBL7FKYwjJ/teH63oAmE3lP34N3kshz8mm4VMAw7U3PxjVwwUmxEFksbgsNUaO3wId9R2AVQYSEGRa2+g==", - "dependencies": { - "@babel/helper-module-transforms": "^7.16.7", - "@babel/helper-plugin-utils": "^7.16.7", - "babel-plugin-dynamic-import-node": "^2.3.3" - }, - "engines": { - "node": ">=6.9.0" - }, - "peerDependencies": { - "@babel/core": "^7.0.0-0" - } - }, - "node_modules/@babel/plugin-transform-modules-commonjs": { - "version": "7.16.7", - "resolved": "https://registry.npmjs.org/@babel/plugin-transform-modules-commonjs/-/plugin-transform-modules-commonjs-7.16.7.tgz", - "integrity": "sha512-h2RP2kE7He1ZWKyAlanMZrAbdv+Acw1pA8dQZhE025WJZE2z0xzFADAinXA9fxd5bn7JnM+SdOGcndGx1ARs9w==", - "dependencies": { - "@babel/helper-module-transforms": "^7.16.7", - "@babel/helper-plugin-utils": "^7.16.7", - "@babel/helper-simple-access": "^7.16.7", - "babel-plugin-dynamic-import-node": "^2.3.3" - }, - "engines": { - "node": ">=6.9.0" - }, - "peerDependencies": { - "@babel/core": "^7.0.0-0" - } - }, - "node_modules/@babel/plugin-transform-modules-systemjs": { - "version": "7.16.7", - "resolved": "https://registry.npmjs.org/@babel/plugin-transform-modules-systemjs/-/plugin-transform-modules-systemjs-7.16.7.tgz", - "integrity": "sha512-DuK5E3k+QQmnOqBR9UkusByy5WZWGRxfzV529s9nPra1GE7olmxfqO2FHobEOYSPIjPBTr4p66YDcjQnt8cBmw==", - "dependencies": { - "@babel/helper-hoist-variables": "^7.16.7", - "@babel/helper-module-transforms": "^7.16.7", - "@babel/helper-plugin-utils": "^7.16.7", - "@babel/helper-validator-identifier": "^7.16.7", - "babel-plugin-dynamic-import-node": "^2.3.3" - }, - "engines": { - "node": ">=6.9.0" - }, - "peerDependencies": { - "@babel/core": "^7.0.0-0" - } - }, - "node_modules/@babel/plugin-transform-modules-umd": { - "version": "7.16.7", - "resolved": "https://registry.npmjs.org/@babel/plugin-transform-modules-umd/-/plugin-transform-modules-umd-7.16.7.tgz", - "integrity": "sha512-EMh7uolsC8O4xhudF2F6wedbSHm1HHZ0C6aJ7K67zcDNidMzVcxWdGr+htW9n21klm+bOn+Rx4CBsAntZd3rEQ==", - "dependencies": { - "@babel/helper-module-transforms": "^7.16.7", - "@babel/helper-plugin-utils": "^7.16.7" - }, - "engines": { - "node": ">=6.9.0" - }, - "peerDependencies": { - "@babel/core": "^7.0.0-0" - } - }, - "node_modules/@babel/plugin-transform-named-capturing-groups-regex": { - "version": "7.16.7", - "resolved": "https://registry.npmjs.org/@babel/plugin-transform-named-capturing-groups-regex/-/plugin-transform-named-capturing-groups-regex-7.16.7.tgz", - "integrity": "sha512-kFy35VwmwIQwCjwrAQhl3+c/kr292i4KdLPKp5lPH03Ltc51qnFlIADoyPxc/6Naz3ok3WdYKg+KK6AH+D4utg==", - "dependencies": { - "@babel/helper-create-regexp-features-plugin": "^7.16.7" - }, - "engines": { - "node": ">=6.9.0" - }, - "peerDependencies": { - "@babel/core": "^7.0.0" - } - }, - "node_modules/@babel/plugin-transform-new-target": { - "version": "7.16.7", - "resolved": "https://registry.npmjs.org/@babel/plugin-transform-new-target/-/plugin-transform-new-target-7.16.7.tgz", - "integrity": "sha512-xiLDzWNMfKoGOpc6t3U+etCE2yRnn3SM09BXqWPIZOBpL2gvVrBWUKnsJx0K/ADi5F5YC5f8APFfWrz25TdlGg==", - "dependencies": { - "@babel/helper-plugin-utils": "^7.16.7" - }, - "engines": { - "node": ">=6.9.0" - }, - "peerDependencies": { - "@babel/core": "^7.0.0-0" - } - }, - "node_modules/@babel/plugin-transform-object-super": { - "version": "7.16.7", - "resolved": "https://registry.npmjs.org/@babel/plugin-transform-object-super/-/plugin-transform-object-super-7.16.7.tgz", - "integrity": "sha512-14J1feiQVWaGvRxj2WjyMuXS2jsBkgB3MdSN5HuC2G5nRspa5RK9COcs82Pwy5BuGcjb+fYaUj94mYcOj7rCvw==", - "dependencies": { - "@babel/helper-plugin-utils": "^7.16.7", - "@babel/helper-replace-supers": "^7.16.7" - }, - "engines": { - "node": ">=6.9.0" - }, - "peerDependencies": { - "@babel/core": "^7.0.0-0" - } - }, - "node_modules/@babel/plugin-transform-parameters": { - "version": "7.16.7", - "resolved": "https://registry.npmjs.org/@babel/plugin-transform-parameters/-/plugin-transform-parameters-7.16.7.tgz", - "integrity": "sha512-AT3MufQ7zZEhU2hwOA11axBnExW0Lszu4RL/tAlUJBuNoRak+wehQW8h6KcXOcgjY42fHtDxswuMhMjFEuv/aw==", - "dependencies": { - "@babel/helper-plugin-utils": "^7.16.7" - }, - "engines": { - "node": ">=6.9.0" - }, - "peerDependencies": { - "@babel/core": "^7.0.0-0" - } - }, - "node_modules/@babel/plugin-transform-property-literals": { - "version": "7.16.7", - "resolved": "https://registry.npmjs.org/@babel/plugin-transform-property-literals/-/plugin-transform-property-literals-7.16.7.tgz", - "integrity": "sha512-z4FGr9NMGdoIl1RqavCqGG+ZuYjfZ/hkCIeuH6Do7tXmSm0ls11nYVSJqFEUOSJbDab5wC6lRE/w6YjVcr6Hqw==", - "dependencies": { - "@babel/helper-plugin-utils": "^7.16.7" - }, - "engines": { - "node": ">=6.9.0" - }, - "peerDependencies": { - "@babel/core": "^7.0.0-0" - } - }, - "node_modules/@babel/plugin-transform-regenerator": { - "version": "7.16.7", - "resolved": "https://registry.npmjs.org/@babel/plugin-transform-regenerator/-/plugin-transform-regenerator-7.16.7.tgz", - "integrity": "sha512-mF7jOgGYCkSJagJ6XCujSQg+6xC1M77/03K2oBmVJWoFGNUtnVJO4WHKJk3dnPC8HCcj4xBQP1Egm8DWh3Pb3Q==", - "dependencies": { - "regenerator-transform": "^0.14.2" - }, - "engines": { - "node": ">=6.9.0" - }, - "peerDependencies": { - "@babel/core": "^7.0.0-0" - } - }, - "node_modules/@babel/plugin-transform-reserved-words": { - "version": "7.16.7", - "resolved": "https://registry.npmjs.org/@babel/plugin-transform-reserved-words/-/plugin-transform-reserved-words-7.16.7.tgz", - "integrity": "sha512-KQzzDnZ9hWQBjwi5lpY5v9shmm6IVG0U9pB18zvMu2i4H90xpT4gmqwPYsn8rObiadYe2M0gmgsiOIF5A/2rtg==", - "dependencies": { - "@babel/helper-plugin-utils": "^7.16.7" - }, - "engines": { - "node": ">=6.9.0" - }, - "peerDependencies": { - "@babel/core": "^7.0.0-0" - } - }, - "node_modules/@babel/plugin-transform-shorthand-properties": { - "version": "7.16.7", - "resolved": "https://registry.npmjs.org/@babel/plugin-transform-shorthand-properties/-/plugin-transform-shorthand-properties-7.16.7.tgz", - "integrity": "sha512-hah2+FEnoRoATdIb05IOXf+4GzXYTq75TVhIn1PewihbpyrNWUt2JbudKQOETWw6QpLe+AIUpJ5MVLYTQbeeUg==", - "dependencies": { - "@babel/helper-plugin-utils": "^7.16.7" - }, - "engines": { - "node": ">=6.9.0" - }, - "peerDependencies": { - "@babel/core": "^7.0.0-0" - } - }, - "node_modules/@babel/plugin-transform-spread": { - "version": "7.16.7", - "resolved": "https://registry.npmjs.org/@babel/plugin-transform-spread/-/plugin-transform-spread-7.16.7.tgz", - "integrity": "sha512-+pjJpgAngb53L0iaA5gU/1MLXJIfXcYepLgXB3esVRf4fqmj8f2cxM3/FKaHsZms08hFQJkFccEWuIpm429TXg==", - "dependencies": { - "@babel/helper-plugin-utils": "^7.16.7", - "@babel/helper-skip-transparent-expression-wrappers": "^7.16.0" - }, - "engines": { - "node": ">=6.9.0" - }, - "peerDependencies": { - "@babel/core": "^7.0.0-0" - } - }, - "node_modules/@babel/plugin-transform-sticky-regex": { - "version": "7.16.7", - "resolved": "https://registry.npmjs.org/@babel/plugin-transform-sticky-regex/-/plugin-transform-sticky-regex-7.16.7.tgz", - "integrity": "sha512-NJa0Bd/87QV5NZZzTuZG5BPJjLYadeSZ9fO6oOUoL4iQx+9EEuw/eEM92SrsT19Yc2jgB1u1hsjqDtH02c3Drw==", - "dependencies": { - "@babel/helper-plugin-utils": "^7.16.7" - }, - "engines": { - "node": ">=6.9.0" - }, - "peerDependencies": { - "@babel/core": "^7.0.0-0" - } - }, - "node_modules/@babel/plugin-transform-template-literals": { - "version": "7.16.7", - "resolved": "https://registry.npmjs.org/@babel/plugin-transform-template-literals/-/plugin-transform-template-literals-7.16.7.tgz", - "integrity": "sha512-VwbkDDUeenlIjmfNeDX/V0aWrQH2QiVyJtwymVQSzItFDTpxfyJh3EVaQiS0rIN/CqbLGr0VcGmuwyTdZtdIsA==", - "dependencies": { - "@babel/helper-plugin-utils": "^7.16.7" - }, - "engines": { - "node": ">=6.9.0" - }, - "peerDependencies": { - "@babel/core": "^7.0.0-0" - } - }, - "node_modules/@babel/plugin-transform-typeof-symbol": { - "version": "7.16.7", - "resolved": "https://registry.npmjs.org/@babel/plugin-transform-typeof-symbol/-/plugin-transform-typeof-symbol-7.16.7.tgz", - "integrity": "sha512-p2rOixCKRJzpg9JB4gjnG4gjWkWa89ZoYUnl9snJ1cWIcTH/hvxZqfO+WjG6T8DRBpctEol5jw1O5rA8gkCokQ==", - "dependencies": { - "@babel/helper-plugin-utils": "^7.16.7" - }, - "engines": { - "node": ">=6.9.0" - }, - "peerDependencies": { - "@babel/core": "^7.0.0-0" - } - }, - "node_modules/@babel/plugin-transform-unicode-escapes": { - "version": "7.16.7", - "resolved": "https://registry.npmjs.org/@babel/plugin-transform-unicode-escapes/-/plugin-transform-unicode-escapes-7.16.7.tgz", - "integrity": "sha512-TAV5IGahIz3yZ9/Hfv35TV2xEm+kaBDaZQCn2S/hG9/CZ0DktxJv9eKfPc7yYCvOYR4JGx1h8C+jcSOvgaaI/Q==", - "dependencies": { - "@babel/helper-plugin-utils": "^7.16.7" - }, - "engines": { - "node": ">=6.9.0" - }, - "peerDependencies": { - "@babel/core": "^7.0.0-0" - } - }, - "node_modules/@babel/plugin-transform-unicode-regex": { - "version": "7.16.7", - "resolved": "https://registry.npmjs.org/@babel/plugin-transform-unicode-regex/-/plugin-transform-unicode-regex-7.16.7.tgz", - "integrity": "sha512-oC5tYYKw56HO75KZVLQ+R/Nl3Hro9kf8iG0hXoaHP7tjAyCpvqBiSNe6vGrZni1Z6MggmUOC6A7VP7AVmw225Q==", - "dependencies": { - "@babel/helper-create-regexp-features-plugin": "^7.16.7", - "@babel/helper-plugin-utils": "^7.16.7" - }, - "engines": { - "node": ">=6.9.0" - }, - "peerDependencies": { - "@babel/core": "^7.0.0-0" - } - }, - "node_modules/@babel/preset-env": { - "version": "7.16.7", - "resolved": "https://registry.npmjs.org/@babel/preset-env/-/preset-env-7.16.7.tgz", - "integrity": "sha512-urX3Cee4aOZbRWOSa3mKPk0aqDikfILuo+C7qq7HY0InylGNZ1fekq9jmlr3pLWwZHF4yD7heQooc2Pow2KMyQ==", - "dependencies": { - "@babel/compat-data": "^7.16.4", - "@babel/helper-compilation-targets": "^7.16.7", - "@babel/helper-plugin-utils": "^7.16.7", - "@babel/helper-validator-option": "^7.16.7", - "@babel/plugin-bugfix-safari-id-destructuring-collision-in-function-expression": "^7.16.7", - "@babel/plugin-bugfix-v8-spread-parameters-in-optional-chaining": "^7.16.7", - "@babel/plugin-proposal-async-generator-functions": "^7.16.7", - "@babel/plugin-proposal-class-properties": "^7.16.7", - "@babel/plugin-proposal-class-static-block": "^7.16.7", - "@babel/plugin-proposal-dynamic-import": "^7.16.7", - "@babel/plugin-proposal-export-namespace-from": "^7.16.7", - "@babel/plugin-proposal-json-strings": "^7.16.7", - "@babel/plugin-proposal-logical-assignment-operators": "^7.16.7", - "@babel/plugin-proposal-nullish-coalescing-operator": "^7.16.7", - "@babel/plugin-proposal-numeric-separator": "^7.16.7", - "@babel/plugin-proposal-object-rest-spread": "^7.16.7", - "@babel/plugin-proposal-optional-catch-binding": "^7.16.7", - "@babel/plugin-proposal-optional-chaining": "^7.16.7", - "@babel/plugin-proposal-private-methods": "^7.16.7", - "@babel/plugin-proposal-private-property-in-object": "^7.16.7", - "@babel/plugin-proposal-unicode-property-regex": "^7.16.7", - "@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-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.16.7", - "@babel/plugin-transform-async-to-generator": "^7.16.7", - "@babel/plugin-transform-block-scoped-functions": "^7.16.7", - "@babel/plugin-transform-block-scoping": "^7.16.7", - "@babel/plugin-transform-classes": "^7.16.7", - "@babel/plugin-transform-computed-properties": "^7.16.7", - "@babel/plugin-transform-destructuring": "^7.16.7", - "@babel/plugin-transform-dotall-regex": "^7.16.7", - "@babel/plugin-transform-duplicate-keys": "^7.16.7", - "@babel/plugin-transform-exponentiation-operator": "^7.16.7", - "@babel/plugin-transform-for-of": "^7.16.7", - "@babel/plugin-transform-function-name": "^7.16.7", - "@babel/plugin-transform-literals": "^7.16.7", - "@babel/plugin-transform-member-expression-literals": "^7.16.7", - "@babel/plugin-transform-modules-amd": "^7.16.7", - "@babel/plugin-transform-modules-commonjs": "^7.16.7", - "@babel/plugin-transform-modules-systemjs": "^7.16.7", - "@babel/plugin-transform-modules-umd": "^7.16.7", - "@babel/plugin-transform-named-capturing-groups-regex": "^7.16.7", - "@babel/plugin-transform-new-target": "^7.16.7", - "@babel/plugin-transform-object-super": "^7.16.7", - "@babel/plugin-transform-parameters": "^7.16.7", - "@babel/plugin-transform-property-literals": "^7.16.7", - "@babel/plugin-transform-regenerator": "^7.16.7", - "@babel/plugin-transform-reserved-words": "^7.16.7", - "@babel/plugin-transform-shorthand-properties": "^7.16.7", - "@babel/plugin-transform-spread": "^7.16.7", - "@babel/plugin-transform-sticky-regex": "^7.16.7", - "@babel/plugin-transform-template-literals": "^7.16.7", - "@babel/plugin-transform-typeof-symbol": "^7.16.7", - "@babel/plugin-transform-unicode-escapes": "^7.16.7", - "@babel/plugin-transform-unicode-regex": "^7.16.7", - "@babel/preset-modules": "^0.1.5", - "@babel/types": "^7.16.7", - "babel-plugin-polyfill-corejs2": "^0.3.0", - "babel-plugin-polyfill-corejs3": "^0.4.0", - "babel-plugin-polyfill-regenerator": "^0.3.0", - "core-js-compat": "^3.19.1", - "semver": "^6.3.0" - }, - "engines": { - "node": ">=6.9.0" - }, - "peerDependencies": { - "@babel/core": "^7.0.0-0" - } - }, - "node_modules/@babel/preset-env/node_modules/semver": { - "version": "6.3.0", - "resolved": "https://registry.npmjs.org/semver/-/semver-6.3.0.tgz", - "integrity": "sha512-b39TBaTSfV6yBrapU89p5fKekE2m/NwnDocOVruQFS1/veMgdzuPcnOM34M6CwxW8jH/lxEa5rBoDeUwu5HHTw==", - "bin": { - "semver": "bin/semver.js" - } - }, - "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==", - "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/runtime": { - "version": "7.16.7", - "resolved": "https://registry.npmjs.org/@babel/runtime/-/runtime-7.16.7.tgz", - "integrity": "sha512-9E9FJowqAsytyOY6LG+1KuueckRL+aQW+mKvXRXnuFGyRAyepJPmEo9vgMfXUA6O9u3IeEdv9MAkppFcaQwogQ==", - "dependencies": { - "regenerator-runtime": "^0.13.4" - }, - "engines": { - "node": ">=6.9.0" - } - }, - "node_modules/@babel/runtime/node_modules/regenerator-runtime": { - "version": "0.13.9", - "resolved": "https://registry.npmjs.org/regenerator-runtime/-/regenerator-runtime-0.13.9.tgz", - "integrity": "sha512-p3VT+cOEgxFsRRA9X4lkI1E+k2/CtnKtU4gcxyaCUreilL/vqI6CdZ3wxVUx3UOUg+gnUOQQcRI7BmSI656MYA==" - }, - "node_modules/@babel/template": { - "version": "7.16.7", - "resolved": "https://registry.npmjs.org/@babel/template/-/template-7.16.7.tgz", - "integrity": "sha512-I8j/x8kHUrbYRTUxXrrMbfCa7jxkE7tZre39x3kjr9hvI82cK1FfqLygotcWN5kdPGWcLdWMHpSBavse5tWw3w==", - "dependencies": { - "@babel/code-frame": "^7.16.7", - "@babel/parser": "^7.16.7", - "@babel/types": "^7.16.7" - }, - "engines": { - "node": ">=6.9.0" - } - }, - "node_modules/@babel/traverse": { - "version": "7.16.7", - "resolved": "https://registry.npmjs.org/@babel/traverse/-/traverse-7.16.7.tgz", - "integrity": "sha512-8KWJPIb8c2VvY8AJrydh6+fVRo2ODx1wYBU2398xJVq0JomuLBZmVQzLPBblJgHIGYG4znCpUZUZ0Pt2vdmVYQ==", - "dependencies": { - "@babel/code-frame": "^7.16.7", - "@babel/generator": "^7.16.7", - "@babel/helper-environment-visitor": "^7.16.7", - "@babel/helper-function-name": "^7.16.7", - "@babel/helper-hoist-variables": "^7.16.7", - "@babel/helper-split-export-declaration": "^7.16.7", - "@babel/parser": "^7.16.7", - "@babel/types": "^7.16.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==", - "engines": { - "node": ">=4" - } - }, - "node_modules/@babel/types": { - "version": "7.16.7", - "resolved": "https://registry.npmjs.org/@babel/types/-/types-7.16.7.tgz", - "integrity": "sha512-E8HuV7FO9qLpx6OtoGfUQ2cjIYnbFwvZWYBS+87EwtdMvmUPJSwykpovFB+8insbpF0uJcpr8KMUi64XZntZcg==", - "dependencies": { - "@babel/helper-validator-identifier": "^7.16.7", - "to-fast-properties": "^2.0.0" - }, - "engines": { - "node": ">=6.9.0" - } - }, - "node_modules/@cspotcode/source-map-consumer": { - "version": "0.8.0", - "resolved": "https://registry.npmjs.org/@cspotcode/source-map-consumer/-/source-map-consumer-0.8.0.tgz", - "integrity": "sha512-41qniHzTU8yAGbCp04ohlmSrZf8bkf/iJsl3V0dRGsQN/5GFfx+LbCSsCpp2gqrqjTVg/K6O8ycoV35JIwAzAg==", - "engines": { - "node": ">= 12" - } - }, - "node_modules/@cspotcode/source-map-support": { - "version": "0.7.0", - "resolved": "https://registry.npmjs.org/@cspotcode/source-map-support/-/source-map-support-0.7.0.tgz", - "integrity": "sha512-X4xqRHqN8ACt2aHVe51OxeA2HjbcL4MqFqXkrmQszJ1NOUuUu5u6Vqx/0lZSVNku7velL5FC/s5uEAj1lsBMhA==", - "dependencies": { - "@cspotcode/source-map-consumer": "0.8.0" - }, - "engines": { - "node": ">=12" - } - }, - "node_modules/@discoveryjs/json-ext": { - "version": "0.5.6", - "resolved": "https://registry.npmjs.org/@discoveryjs/json-ext/-/json-ext-0.5.6.tgz", - "integrity": "sha512-ws57AidsDvREKrZKYffXddNkyaF14iHNHm8VQnZH6t99E8gczjNN0GpvcGny0imC80yQ0tHz1xVUKk/KFQSUyA==", - "engines": { - "node": ">=10.0.0" - } - }, - "node_modules/@eslint/eslintrc": { - "version": "1.0.5", - "resolved": "https://registry.npmjs.org/@eslint/eslintrc/-/eslintrc-1.0.5.tgz", - "integrity": "sha512-BLxsnmK3KyPunz5wmCCpqy0YelEoxxGmH73Is+Z74oOTMtExcjkr3dDR6quwrjh1YspA8DH9gnX1o069KiS9AQ==", - "dev": true, - "dependencies": { - "ajv": "^6.12.4", - "debug": "^4.3.2", - "espree": "^9.2.0", - "globals": "^13.9.0", - "ignore": "^4.0.6", - "import-fresh": "^3.2.1", - "js-yaml": "^4.1.0", - "minimatch": "^3.0.4", - "strip-json-comments": "^3.1.1" - }, - "engines": { - "node": "^12.22.0 || ^14.17.0 || >=16.0.0" - } - }, - "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/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/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/@feathersjs/hooks": { - "version": "0.6.5", - "resolved": "https://registry.npmjs.org/@feathersjs/hooks/-/hooks-0.6.5.tgz", - "integrity": "sha512-WtcEoG/imdHRvC3vofGi/OcgH+cjHHhO0AfEeTlsnrKLjVKKBXV6aoIrB2nHZPpE7iW5sA7AZMR6bPD8ytxN+w==", - "engines": { - "node": ">= 10" - } - }, - "node_modules/@gar/promisify": { - "version": "1.1.2", - "resolved": "https://registry.npmjs.org/@gar/promisify/-/promisify-1.1.2.tgz", - "integrity": "sha512-82cpyJyKRoQoRi+14ibCeGPu0CwypgtBAdBhq1WfvagpCZNKqwXbKwXllYSMG91DhmG4jt9gN8eP6lGOtozuaw==", - "dev": true - }, - "node_modules/@humanwhocodes/config-array": { - "version": "0.9.2", - "resolved": "https://registry.npmjs.org/@humanwhocodes/config-array/-/config-array-0.9.2.tgz", - "integrity": "sha512-UXOuFCGcwciWckOpmfKDq/GyhlTf9pN/BzG//x8p8zTOFEcGuA68ANXheFS0AGvy3qgZqLBUkMs7hqzqCKOVwA==", - "dev": true, - "dependencies": { - "@humanwhocodes/object-schema": "^1.2.1", - "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/@hutson/parse-repository-url": { - "version": "3.0.2", - "resolved": "https://registry.npmjs.org/@hutson/parse-repository-url/-/parse-repository-url-3.0.2.tgz", - "integrity": "sha512-H9XAx3hc0BQHY6l+IFSWHDySypcXsvsuLhgYLUGywmJ5pswRVQJUHpOsobnLYp2ZUaUlKiKDrgWWhosOwAEM8Q==", - "dev": true, - "engines": { - "node": ">=6.9.0" - } - }, - "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/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/@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/@lerna/add": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/@lerna/add/-/add-4.0.0.tgz", - "integrity": "sha512-cpmAH1iS3k8JBxNvnMqrGTTjbY/ZAiKa1ChJzFevMYY3eeqbvhsBKnBcxjRXtdrJ6bd3dCQM+ZtK+0i682Fhng==", - "dev": true, - "dependencies": { - "@lerna/bootstrap": "4.0.0", - "@lerna/command": "4.0.0", - "@lerna/filter-options": "4.0.0", - "@lerna/npm-conf": "4.0.0", - "@lerna/validation-error": "4.0.0", - "dedent": "^0.7.0", - "npm-package-arg": "^8.1.0", - "p-map": "^4.0.0", - "pacote": "^11.2.6", - "semver": "^7.3.4" - }, - "engines": { - "node": ">= 10.18.0" - } - }, - "node_modules/@lerna/bootstrap": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/@lerna/bootstrap/-/bootstrap-4.0.0.tgz", - "integrity": "sha512-RkS7UbeM2vu+kJnHzxNRCLvoOP9yGNgkzRdy4UV2hNalD7EP41bLvRVOwRYQ7fhc2QcbhnKNdOBihYRL0LcKtw==", - "dev": true, - "dependencies": { - "@lerna/command": "4.0.0", - "@lerna/filter-options": "4.0.0", - "@lerna/has-npm-version": "4.0.0", - "@lerna/npm-install": "4.0.0", - "@lerna/package-graph": "4.0.0", - "@lerna/pulse-till-done": "4.0.0", - "@lerna/rimraf-dir": "4.0.0", - "@lerna/run-lifecycle": "4.0.0", - "@lerna/run-topologically": "4.0.0", - "@lerna/symlink-binary": "4.0.0", - "@lerna/symlink-dependencies": "4.0.0", - "@lerna/validation-error": "4.0.0", - "dedent": "^0.7.0", - "get-port": "^5.1.1", - "multimatch": "^5.0.0", - "npm-package-arg": "^8.1.0", - "npmlog": "^4.1.2", - "p-map": "^4.0.0", - "p-map-series": "^2.1.0", - "p-waterfall": "^2.1.1", - "read-package-tree": "^5.3.1", - "semver": "^7.3.4" - }, - "engines": { - "node": ">= 10.18.0" - } - }, - "node_modules/@lerna/changed": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/@lerna/changed/-/changed-4.0.0.tgz", - "integrity": "sha512-cD+KuPRp6qiPOD+BO6S6SN5cARspIaWSOqGBpGnYzLb4uWT8Vk4JzKyYtc8ym1DIwyoFXHosXt8+GDAgR8QrgQ==", - "dev": true, - "dependencies": { - "@lerna/collect-updates": "4.0.0", - "@lerna/command": "4.0.0", - "@lerna/listable": "4.0.0", - "@lerna/output": "4.0.0" - }, - "engines": { - "node": ">= 10.18.0" - } - }, - "node_modules/@lerna/check-working-tree": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/@lerna/check-working-tree/-/check-working-tree-4.0.0.tgz", - "integrity": "sha512-/++bxM43jYJCshBiKP5cRlCTwSJdRSxVmcDAXM+1oUewlZJVSVlnks5eO0uLxokVFvLhHlC5kHMc7gbVFPHv6Q==", - "dev": true, - "dependencies": { - "@lerna/collect-uncommitted": "4.0.0", - "@lerna/describe-ref": "4.0.0", - "@lerna/validation-error": "4.0.0" - }, - "engines": { - "node": ">= 10.18.0" - } - }, - "node_modules/@lerna/child-process": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/@lerna/child-process/-/child-process-4.0.0.tgz", - "integrity": "sha512-XtCnmCT9eyVsUUHx6y/CTBYdV9g2Cr/VxyseTWBgfIur92/YKClfEtJTbOh94jRT62hlKLqSvux/UhxXVh613Q==", - "dev": true, - "dependencies": { - "chalk": "^4.1.0", - "execa": "^5.0.0", - "strong-log-transformer": "^2.1.0" - }, - "engines": { - "node": ">= 10.18.0" - } - }, - "node_modules/@lerna/clean": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/@lerna/clean/-/clean-4.0.0.tgz", - "integrity": "sha512-uugG2iN9k45ITx2jtd8nEOoAtca8hNlDCUM0N3lFgU/b1mEQYAPRkqr1qs4FLRl/Y50ZJ41wUz1eazS+d/0osA==", - "dev": true, - "dependencies": { - "@lerna/command": "4.0.0", - "@lerna/filter-options": "4.0.0", - "@lerna/prompt": "4.0.0", - "@lerna/pulse-till-done": "4.0.0", - "@lerna/rimraf-dir": "4.0.0", - "p-map": "^4.0.0", - "p-map-series": "^2.1.0", - "p-waterfall": "^2.1.1" - }, - "engines": { - "node": ">= 10.18.0" - } - }, - "node_modules/@lerna/cli": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/@lerna/cli/-/cli-4.0.0.tgz", - "integrity": "sha512-Neaw3GzFrwZiRZv2g7g6NwFjs3er1vhraIniEs0jjVLPMNC4eata0na3GfE5yibkM/9d3gZdmihhZdZ3EBdvYA==", - "dev": true, - "dependencies": { - "@lerna/global-options": "4.0.0", - "dedent": "^0.7.0", - "npmlog": "^4.1.2", - "yargs": "^16.2.0" - }, - "engines": { - "node": ">= 10.18.0" - } - }, - "node_modules/@lerna/collect-uncommitted": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/@lerna/collect-uncommitted/-/collect-uncommitted-4.0.0.tgz", - "integrity": "sha512-ufSTfHZzbx69YNj7KXQ3o66V4RC76ffOjwLX0q/ab//61bObJ41n03SiQEhSlmpP+gmFbTJ3/7pTe04AHX9m/g==", - "dev": true, - "dependencies": { - "@lerna/child-process": "4.0.0", - "chalk": "^4.1.0", - "npmlog": "^4.1.2" - }, - "engines": { - "node": ">= 10.18.0" - } - }, - "node_modules/@lerna/collect-updates": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/@lerna/collect-updates/-/collect-updates-4.0.0.tgz", - "integrity": "sha512-bnNGpaj4zuxsEkyaCZLka9s7nMs58uZoxrRIPJ+nrmrZYp1V5rrd+7/NYTuunOhY2ug1sTBvTAxj3NZQ+JKnOw==", - "dev": true, - "dependencies": { - "@lerna/child-process": "4.0.0", - "@lerna/describe-ref": "4.0.0", - "minimatch": "^3.0.4", - "npmlog": "^4.1.2", - "slash": "^3.0.0" - }, - "engines": { - "node": ">= 10.18.0" - } - }, - "node_modules/@lerna/command": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/@lerna/command/-/command-4.0.0.tgz", - "integrity": "sha512-LM9g3rt5FsPNFqIHUeRwWXLNHJ5NKzOwmVKZ8anSp4e1SPrv2HNc1V02/9QyDDZK/w+5POXH5lxZUI1CHaOK/A==", - "dev": true, - "dependencies": { - "@lerna/child-process": "4.0.0", - "@lerna/package-graph": "4.0.0", - "@lerna/project": "4.0.0", - "@lerna/validation-error": "4.0.0", - "@lerna/write-log-file": "4.0.0", - "clone-deep": "^4.0.1", - "dedent": "^0.7.0", - "execa": "^5.0.0", - "is-ci": "^2.0.0", - "npmlog": "^4.1.2" - }, - "engines": { - "node": ">= 10.18.0" - } - }, - "node_modules/@lerna/conventional-commits": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/@lerna/conventional-commits/-/conventional-commits-4.0.0.tgz", - "integrity": "sha512-CSUQRjJHFrH8eBn7+wegZLV3OrNc0Y1FehYfYGhjLE2SIfpCL4bmfu/ViYuHh9YjwHaA+4SX6d3hR+xkeseKmw==", - "dev": true, - "dependencies": { - "@lerna/validation-error": "4.0.0", - "conventional-changelog-angular": "^5.0.12", - "conventional-changelog-core": "^4.2.2", - "conventional-recommended-bump": "^6.1.0", - "fs-extra": "^9.1.0", - "get-stream": "^6.0.0", - "lodash.template": "^4.5.0", - "npm-package-arg": "^8.1.0", - "npmlog": "^4.1.2", - "pify": "^5.0.0", - "semver": "^7.3.4" - }, - "engines": { - "node": ">= 10.18.0" - } - }, - "node_modules/@lerna/create": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/@lerna/create/-/create-4.0.0.tgz", - "integrity": "sha512-mVOB1niKByEUfxlbKTM1UNECWAjwUdiioIbRQZEeEabtjCL69r9rscIsjlGyhGWCfsdAG5wfq4t47nlDXdLLag==", - "dev": true, - "dependencies": { - "@lerna/child-process": "4.0.0", - "@lerna/command": "4.0.0", - "@lerna/npm-conf": "4.0.0", - "@lerna/validation-error": "4.0.0", - "dedent": "^0.7.0", - "fs-extra": "^9.1.0", - "globby": "^11.0.2", - "init-package-json": "^2.0.2", - "npm-package-arg": "^8.1.0", - "p-reduce": "^2.1.0", - "pacote": "^11.2.6", - "pify": "^5.0.0", - "semver": "^7.3.4", - "slash": "^3.0.0", - "validate-npm-package-license": "^3.0.4", - "validate-npm-package-name": "^3.0.0", - "whatwg-url": "^8.4.0", - "yargs-parser": "20.2.4" - }, - "engines": { - "node": ">= 10.18.0" - } - }, - "node_modules/@lerna/create-symlink": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/@lerna/create-symlink/-/create-symlink-4.0.0.tgz", - "integrity": "sha512-I0phtKJJdafUiDwm7BBlEUOtogmu8+taxq6PtIrxZbllV9hWg59qkpuIsiFp+no7nfRVuaasNYHwNUhDAVQBig==", - "dev": true, - "dependencies": { - "cmd-shim": "^4.1.0", - "fs-extra": "^9.1.0", - "npmlog": "^4.1.2" - }, - "engines": { - "node": ">= 10.18.0" - } - }, - "node_modules/@lerna/describe-ref": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/@lerna/describe-ref/-/describe-ref-4.0.0.tgz", - "integrity": "sha512-eTU5+xC4C5Gcgz+Ey4Qiw9nV2B4JJbMulsYJMW8QjGcGh8zudib7Sduj6urgZXUYNyhYpRs+teci9M2J8u+UvQ==", - "dev": true, - "dependencies": { - "@lerna/child-process": "4.0.0", - "npmlog": "^4.1.2" - }, - "engines": { - "node": ">= 10.18.0" - } - }, - "node_modules/@lerna/diff": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/@lerna/diff/-/diff-4.0.0.tgz", - "integrity": "sha512-jYPKprQVg41+MUMxx6cwtqsNm0Yxx9GDEwdiPLwcUTFx+/qKCEwifKNJ1oGIPBxyEHX2PFCOjkK39lHoj2qiag==", - "dev": true, - "dependencies": { - "@lerna/child-process": "4.0.0", - "@lerna/command": "4.0.0", - "@lerna/validation-error": "4.0.0", - "npmlog": "^4.1.2" - }, - "engines": { - "node": ">= 10.18.0" - } - }, - "node_modules/@lerna/exec": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/@lerna/exec/-/exec-4.0.0.tgz", - "integrity": "sha512-VGXtL/b/JfY84NB98VWZpIExfhLOzy0ozm/0XaS4a2SmkAJc5CeUfrhvHxxkxiTBLkU+iVQUyYEoAT0ulQ8PCw==", - "dev": true, - "dependencies": { - "@lerna/child-process": "4.0.0", - "@lerna/command": "4.0.0", - "@lerna/filter-options": "4.0.0", - "@lerna/profiler": "4.0.0", - "@lerna/run-topologically": "4.0.0", - "@lerna/validation-error": "4.0.0", - "p-map": "^4.0.0" - }, - "engines": { - "node": ">= 10.18.0" - } - }, - "node_modules/@lerna/filter-options": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/@lerna/filter-options/-/filter-options-4.0.0.tgz", - "integrity": "sha512-vV2ANOeZhOqM0rzXnYcFFCJ/kBWy/3OA58irXih9AMTAlQLymWAK0akWybl++sUJ4HB9Hx12TOqaXbYS2NM5uw==", - "dev": true, - "dependencies": { - "@lerna/collect-updates": "4.0.0", - "@lerna/filter-packages": "4.0.0", - "dedent": "^0.7.0", - "npmlog": "^4.1.2" - }, - "engines": { - "node": ">= 10.18.0" - } - }, - "node_modules/@lerna/filter-packages": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/@lerna/filter-packages/-/filter-packages-4.0.0.tgz", - "integrity": "sha512-+4AJIkK7iIiOaqCiVTYJxh/I9qikk4XjNQLhE3kixaqgMuHl1NQ99qXRR0OZqAWB9mh8Z1HA9bM5K1HZLBTOqA==", - "dev": true, - "dependencies": { - "@lerna/validation-error": "4.0.0", - "multimatch": "^5.0.0", - "npmlog": "^4.1.2" - }, - "engines": { - "node": ">= 10.18.0" - } - }, - "node_modules/@lerna/get-npm-exec-opts": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/@lerna/get-npm-exec-opts/-/get-npm-exec-opts-4.0.0.tgz", - "integrity": "sha512-yvmkerU31CTWS2c7DvmAWmZVeclPBqI7gPVr5VATUKNWJ/zmVcU4PqbYoLu92I9Qc4gY1TuUplMNdNuZTSL7IQ==", - "dev": true, - "dependencies": { - "npmlog": "^4.1.2" - }, - "engines": { - "node": ">= 10.18.0" - } - }, - "node_modules/@lerna/get-packed": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/@lerna/get-packed/-/get-packed-4.0.0.tgz", - "integrity": "sha512-rfWONRsEIGyPJTxFzC8ECb3ZbsDXJbfqWYyeeQQDrJRPnEJErlltRLPLgC2QWbxFgFPsoDLeQmFHJnf0iDfd8w==", - "dev": true, - "dependencies": { - "fs-extra": "^9.1.0", - "ssri": "^8.0.1", - "tar": "^6.1.0" - }, - "engines": { - "node": ">= 10.18.0" - } - }, - "node_modules/@lerna/github-client": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/@lerna/github-client/-/github-client-4.0.0.tgz", - "integrity": "sha512-2jhsldZtTKXYUBnOm23Lb0Fx8G4qfSXF9y7UpyUgWUj+YZYd+cFxSuorwQIgk5P4XXrtVhsUesIsli+BYSThiw==", - "dev": true, - "dependencies": { - "@lerna/child-process": "4.0.0", - "@octokit/plugin-enterprise-rest": "^6.0.1", - "@octokit/rest": "^18.1.0", - "git-url-parse": "^11.4.4", - "npmlog": "^4.1.2" - }, - "engines": { - "node": ">= 10.18.0" - } - }, - "node_modules/@lerna/gitlab-client": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/@lerna/gitlab-client/-/gitlab-client-4.0.0.tgz", - "integrity": "sha512-OMUpGSkeDWFf7BxGHlkbb35T7YHqVFCwBPSIR6wRsszY8PAzCYahtH3IaJzEJyUg6vmZsNl0FSr3pdA2skhxqA==", - "dev": true, - "dependencies": { - "node-fetch": "^2.6.1", - "npmlog": "^4.1.2", - "whatwg-url": "^8.4.0" - }, - "engines": { - "node": ">= 10.18.0" - } - }, - "node_modules/@lerna/global-options": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/@lerna/global-options/-/global-options-4.0.0.tgz", - "integrity": "sha512-TRMR8afAHxuYBHK7F++Ogop2a82xQjoGna1dvPOY6ltj/pEx59pdgcJfYcynYqMkFIk8bhLJJN9/ndIfX29FTQ==", - "dev": true, - "engines": { - "node": ">= 10.18.0" - } - }, - "node_modules/@lerna/has-npm-version": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/@lerna/has-npm-version/-/has-npm-version-4.0.0.tgz", - "integrity": "sha512-LQ3U6XFH8ZmLCsvsgq1zNDqka0Xzjq5ibVN+igAI5ccRWNaUsE/OcmsyMr50xAtNQMYMzmpw5GVLAivT2/YzCg==", - "dev": true, - "dependencies": { - "@lerna/child-process": "4.0.0", - "semver": "^7.3.4" - }, - "engines": { - "node": ">= 10.18.0" - } - }, - "node_modules/@lerna/import": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/@lerna/import/-/import-4.0.0.tgz", - "integrity": "sha512-FaIhd+4aiBousKNqC7TX1Uhe97eNKf5/SC7c5WZANVWtC7aBWdmswwDt3usrzCNpj6/Wwr9EtEbYROzxKH8ffg==", - "dev": true, - "dependencies": { - "@lerna/child-process": "4.0.0", - "@lerna/command": "4.0.0", - "@lerna/prompt": "4.0.0", - "@lerna/pulse-till-done": "4.0.0", - "@lerna/validation-error": "4.0.0", - "dedent": "^0.7.0", - "fs-extra": "^9.1.0", - "p-map-series": "^2.1.0" - }, - "engines": { - "node": ">= 10.18.0" - } - }, - "node_modules/@lerna/info": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/@lerna/info/-/info-4.0.0.tgz", - "integrity": "sha512-8Uboa12kaCSZEn4XRfPz5KU9XXoexSPS4oeYGj76s2UQb1O1GdnEyfjyNWoUl1KlJ2i/8nxUskpXIftoFYH0/Q==", - "dev": true, - "dependencies": { - "@lerna/command": "4.0.0", - "@lerna/output": "4.0.0", - "envinfo": "^7.7.4" - }, - "engines": { - "node": ">= 10.18.0" - } - }, - "node_modules/@lerna/init": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/@lerna/init/-/init-4.0.0.tgz", - "integrity": "sha512-wY6kygop0BCXupzWj5eLvTUqdR7vIAm0OgyV9WHpMYQGfs1V22jhztt8mtjCloD/O0nEe4tJhdG62XU5aYmPNQ==", - "dev": true, - "dependencies": { - "@lerna/child-process": "4.0.0", - "@lerna/command": "4.0.0", - "fs-extra": "^9.1.0", - "p-map": "^4.0.0", - "write-json-file": "^4.3.0" - }, - "engines": { - "node": ">= 10.18.0" - } - }, - "node_modules/@lerna/link": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/@lerna/link/-/link-4.0.0.tgz", - "integrity": "sha512-KlvPi7XTAcVOByfaLlOeYOfkkDcd+bejpHMCd1KcArcFTwijOwXOVi24DYomIeHvy6HsX/IUquJ4PPUJIeB4+w==", - "dev": true, - "dependencies": { - "@lerna/command": "4.0.0", - "@lerna/package-graph": "4.0.0", - "@lerna/symlink-dependencies": "4.0.0", - "p-map": "^4.0.0", - "slash": "^3.0.0" - }, - "engines": { - "node": ">= 10.18.0" - } - }, - "node_modules/@lerna/list": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/@lerna/list/-/list-4.0.0.tgz", - "integrity": "sha512-L2B5m3P+U4Bif5PultR4TI+KtW+SArwq1i75QZ78mRYxPc0U/piau1DbLOmwrdqr99wzM49t0Dlvl6twd7GHFg==", - "dev": true, - "dependencies": { - "@lerna/command": "4.0.0", - "@lerna/filter-options": "4.0.0", - "@lerna/listable": "4.0.0", - "@lerna/output": "4.0.0" - }, - "engines": { - "node": ">= 10.18.0" - } - }, - "node_modules/@lerna/listable": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/@lerna/listable/-/listable-4.0.0.tgz", - "integrity": "sha512-/rPOSDKsOHs5/PBLINZOkRIX1joOXUXEtyUs5DHLM8q6/RP668x/1lFhw6Dx7/U+L0+tbkpGtZ1Yt0LewCLgeQ==", - "dev": true, - "dependencies": { - "@lerna/query-graph": "4.0.0", - "chalk": "^4.1.0", - "columnify": "^1.5.4" - }, - "engines": { - "node": ">= 10.18.0" - } - }, - "node_modules/@lerna/log-packed": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/@lerna/log-packed/-/log-packed-4.0.0.tgz", - "integrity": "sha512-+dpCiWbdzgMAtpajLToy9PO713IHoE6GV/aizXycAyA07QlqnkpaBNZ8DW84gHdM1j79TWockGJo9PybVhrrZQ==", - "dev": true, - "dependencies": { - "byte-size": "^7.0.0", - "columnify": "^1.5.4", - "has-unicode": "^2.0.1", - "npmlog": "^4.1.2" - }, - "engines": { - "node": ">= 10.18.0" - } - }, - "node_modules/@lerna/npm-conf": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/@lerna/npm-conf/-/npm-conf-4.0.0.tgz", - "integrity": "sha512-uS7H02yQNq3oejgjxAxqq/jhwGEE0W0ntr8vM3EfpCW1F/wZruwQw+7bleJQ9vUBjmdXST//tk8mXzr5+JXCfw==", - "dev": true, - "dependencies": { - "config-chain": "^1.1.12", - "pify": "^5.0.0" - }, - "engines": { - "node": ">= 10.18.0" - } - }, - "node_modules/@lerna/npm-dist-tag": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/@lerna/npm-dist-tag/-/npm-dist-tag-4.0.0.tgz", - "integrity": "sha512-F20sg28FMYTgXqEQihgoqSfwmq+Id3zT23CnOwD+XQMPSy9IzyLf1fFVH319vXIw6NF6Pgs4JZN2Qty6/CQXGw==", - "dev": true, - "dependencies": { - "@lerna/otplease": "4.0.0", - "npm-package-arg": "^8.1.0", - "npm-registry-fetch": "^9.0.0", - "npmlog": "^4.1.2" - }, - "engines": { - "node": ">= 10.18.0" - } - }, - "node_modules/@lerna/npm-install": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/@lerna/npm-install/-/npm-install-4.0.0.tgz", - "integrity": "sha512-aKNxq2j3bCH3eXl3Fmu4D54s/YLL9WSwV8W7X2O25r98wzrO38AUN6AB9EtmAx+LV/SP15et7Yueg9vSaanRWg==", - "dev": true, - "dependencies": { - "@lerna/child-process": "4.0.0", - "@lerna/get-npm-exec-opts": "4.0.0", - "fs-extra": "^9.1.0", - "npm-package-arg": "^8.1.0", - "npmlog": "^4.1.2", - "signal-exit": "^3.0.3", - "write-pkg": "^4.0.0" - }, - "engines": { - "node": ">= 10.18.0" - } - }, - "node_modules/@lerna/npm-publish": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/@lerna/npm-publish/-/npm-publish-4.0.0.tgz", - "integrity": "sha512-vQb7yAPRo5G5r77DRjHITc9piR9gvEKWrmfCH7wkfBnGWEqu7n8/4bFQ7lhnkujvc8RXOsYpvbMQkNfkYibD/w==", - "dev": true, - "dependencies": { - "@lerna/otplease": "4.0.0", - "@lerna/run-lifecycle": "4.0.0", - "fs-extra": "^9.1.0", - "libnpmpublish": "^4.0.0", - "npm-package-arg": "^8.1.0", - "npmlog": "^4.1.2", - "pify": "^5.0.0", - "read-package-json": "^3.0.0" - }, - "engines": { - "node": ">= 10.18.0" - } - }, - "node_modules/@lerna/npm-run-script": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/@lerna/npm-run-script/-/npm-run-script-4.0.0.tgz", - "integrity": "sha512-Jmyh9/IwXJjOXqKfIgtxi0bxi1pUeKe5bD3S81tkcy+kyng/GNj9WSqD5ZggoNP2NP//s4CLDAtUYLdP7CU9rA==", - "dev": true, - "dependencies": { - "@lerna/child-process": "4.0.0", - "@lerna/get-npm-exec-opts": "4.0.0", - "npmlog": "^4.1.2" - }, - "engines": { - "node": ">= 10.18.0" - } - }, - "node_modules/@lerna/otplease": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/@lerna/otplease/-/otplease-4.0.0.tgz", - "integrity": "sha512-Sgzbqdk1GH4psNiT6hk+BhjOfIr/5KhGBk86CEfHNJTk9BK4aZYyJD4lpDbDdMjIV4g03G7pYoqHzH765T4fxw==", - "dev": true, - "dependencies": { - "@lerna/prompt": "4.0.0" - }, - "engines": { - "node": ">= 10.18.0" - } - }, - "node_modules/@lerna/output": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/@lerna/output/-/output-4.0.0.tgz", - "integrity": "sha512-Un1sHtO1AD7buDQrpnaYTi2EG6sLF+KOPEAMxeUYG5qG3khTs2Zgzq5WE3dt2N/bKh7naESt20JjIW6tBELP0w==", - "dev": true, - "dependencies": { - "npmlog": "^4.1.2" - }, - "engines": { - "node": ">= 10.18.0" - } - }, - "node_modules/@lerna/pack-directory": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/@lerna/pack-directory/-/pack-directory-4.0.0.tgz", - "integrity": "sha512-NJrmZNmBHS+5aM+T8N6FVbaKFScVqKlQFJNY2k7nsJ/uklNKsLLl6VhTQBPwMTbf6Tf7l6bcKzpy7aePuq9UiQ==", - "dev": true, - "dependencies": { - "@lerna/get-packed": "4.0.0", - "@lerna/package": "4.0.0", - "@lerna/run-lifecycle": "4.0.0", - "npm-packlist": "^2.1.4", - "npmlog": "^4.1.2", - "tar": "^6.1.0", - "temp-write": "^4.0.0" - }, - "engines": { - "node": ">= 10.18.0" - } - }, - "node_modules/@lerna/package": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/@lerna/package/-/package-4.0.0.tgz", - "integrity": "sha512-l0M/izok6FlyyitxiQKr+gZLVFnvxRQdNhzmQ6nRnN9dvBJWn+IxxpM+cLqGACatTnyo9LDzNTOj2Db3+s0s8Q==", - "dev": true, - "dependencies": { - "load-json-file": "^6.2.0", - "npm-package-arg": "^8.1.0", - "write-pkg": "^4.0.0" - }, - "engines": { - "node": ">= 10.18.0" - } - }, - "node_modules/@lerna/package-graph": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/@lerna/package-graph/-/package-graph-4.0.0.tgz", - "integrity": "sha512-QED2ZCTkfXMKFoTGoccwUzjHtZMSf3UKX14A4/kYyBms9xfFsesCZ6SLI5YeySEgcul8iuIWfQFZqRw+Qrjraw==", - "dev": true, - "dependencies": { - "@lerna/prerelease-id-from-version": "4.0.0", - "@lerna/validation-error": "4.0.0", - "npm-package-arg": "^8.1.0", - "npmlog": "^4.1.2", - "semver": "^7.3.4" - }, - "engines": { - "node": ">= 10.18.0" - } - }, - "node_modules/@lerna/prerelease-id-from-version": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/@lerna/prerelease-id-from-version/-/prerelease-id-from-version-4.0.0.tgz", - "integrity": "sha512-GQqguzETdsYRxOSmdFZ6zDBXDErIETWOqomLERRY54f4p+tk4aJjoVdd9xKwehC9TBfIFvlRbL1V9uQGHh1opg==", - "dev": true, - "dependencies": { - "semver": "^7.3.4" - }, - "engines": { - "node": ">= 10.18.0" - } - }, - "node_modules/@lerna/profiler": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/@lerna/profiler/-/profiler-4.0.0.tgz", - "integrity": "sha512-/BaEbqnVh1LgW/+qz8wCuI+obzi5/vRE8nlhjPzdEzdmWmZXuCKyWSEzAyHOJWw1ntwMiww5dZHhFQABuoFz9Q==", - "dev": true, - "dependencies": { - "fs-extra": "^9.1.0", - "npmlog": "^4.1.2", - "upath": "^2.0.1" - }, - "engines": { - "node": ">= 10.18.0" - } - }, - "node_modules/@lerna/project": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/@lerna/project/-/project-4.0.0.tgz", - "integrity": "sha512-o0MlVbDkD5qRPkFKlBZsXZjoNTWPyuL58564nSfZJ6JYNmgAptnWPB2dQlAc7HWRZkmnC2fCkEdoU+jioPavbg==", - "dev": true, - "dependencies": { - "@lerna/package": "4.0.0", - "@lerna/validation-error": "4.0.0", - "cosmiconfig": "^7.0.0", - "dedent": "^0.7.0", - "dot-prop": "^6.0.1", - "glob-parent": "^5.1.1", - "globby": "^11.0.2", - "load-json-file": "^6.2.0", - "npmlog": "^4.1.2", - "p-map": "^4.0.0", - "resolve-from": "^5.0.0", - "write-json-file": "^4.3.0" - }, - "engines": { - "node": ">= 10.18.0" - } - }, - "node_modules/@lerna/project/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/@lerna/project/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/@lerna/prompt": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/@lerna/prompt/-/prompt-4.0.0.tgz", - "integrity": "sha512-4Ig46oCH1TH5M7YyTt53fT6TuaKMgqUUaqdgxvp6HP6jtdak6+amcsqB8YGz2eQnw/sdxunx84DfI9XpoLj4bQ==", - "dev": true, - "dependencies": { - "inquirer": "^7.3.3", - "npmlog": "^4.1.2" - }, - "engines": { - "node": ">= 10.18.0" - } - }, - "node_modules/@lerna/publish": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/@lerna/publish/-/publish-4.0.0.tgz", - "integrity": "sha512-K8jpqjHrChH22qtkytA5GRKIVFEtqBF6JWj1I8dWZtHs4Jywn8yB1jQ3BAMLhqmDJjWJtRck0KXhQQKzDK2UPg==", - "dev": true, - "dependencies": { - "@lerna/check-working-tree": "4.0.0", - "@lerna/child-process": "4.0.0", - "@lerna/collect-updates": "4.0.0", - "@lerna/command": "4.0.0", - "@lerna/describe-ref": "4.0.0", - "@lerna/log-packed": "4.0.0", - "@lerna/npm-conf": "4.0.0", - "@lerna/npm-dist-tag": "4.0.0", - "@lerna/npm-publish": "4.0.0", - "@lerna/otplease": "4.0.0", - "@lerna/output": "4.0.0", - "@lerna/pack-directory": "4.0.0", - "@lerna/prerelease-id-from-version": "4.0.0", - "@lerna/prompt": "4.0.0", - "@lerna/pulse-till-done": "4.0.0", - "@lerna/run-lifecycle": "4.0.0", - "@lerna/run-topologically": "4.0.0", - "@lerna/validation-error": "4.0.0", - "@lerna/version": "4.0.0", - "fs-extra": "^9.1.0", - "libnpmaccess": "^4.0.1", - "npm-package-arg": "^8.1.0", - "npm-registry-fetch": "^9.0.0", - "npmlog": "^4.1.2", - "p-map": "^4.0.0", - "p-pipe": "^3.1.0", - "pacote": "^11.2.6", - "semver": "^7.3.4" - }, - "engines": { - "node": ">= 10.18.0" - } - }, - "node_modules/@lerna/pulse-till-done": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/@lerna/pulse-till-done/-/pulse-till-done-4.0.0.tgz", - "integrity": "sha512-Frb4F7QGckaybRhbF7aosLsJ5e9WuH7h0KUkjlzSByVycxY91UZgaEIVjS2oN9wQLrheLMHl6SiFY0/Pvo0Cxg==", - "dev": true, - "dependencies": { - "npmlog": "^4.1.2" - }, - "engines": { - "node": ">= 10.18.0" - } - }, - "node_modules/@lerna/query-graph": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/@lerna/query-graph/-/query-graph-4.0.0.tgz", - "integrity": "sha512-YlP6yI3tM4WbBmL9GCmNDoeQyzcyg1e4W96y/PKMZa5GbyUvkS2+Jc2kwPD+5KcXou3wQZxSPzR3Te5OenaDdg==", - "dev": true, - "dependencies": { - "@lerna/package-graph": "4.0.0" - }, - "engines": { - "node": ">= 10.18.0" - } - }, - "node_modules/@lerna/resolve-symlink": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/@lerna/resolve-symlink/-/resolve-symlink-4.0.0.tgz", - "integrity": "sha512-RtX8VEUzqT+uLSCohx8zgmjc6zjyRlh6i/helxtZTMmc4+6O4FS9q5LJas2uGO2wKvBlhcD6siibGt7dIC3xZA==", - "dev": true, - "dependencies": { - "fs-extra": "^9.1.0", - "npmlog": "^4.1.2", - "read-cmd-shim": "^2.0.0" - }, - "engines": { - "node": ">= 10.18.0" - } - }, - "node_modules/@lerna/rimraf-dir": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/@lerna/rimraf-dir/-/rimraf-dir-4.0.0.tgz", - "integrity": "sha512-QNH9ABWk9mcMJh2/muD9iYWBk1oQd40y6oH+f3wwmVGKYU5YJD//+zMiBI13jxZRtwBx0vmBZzkBkK1dR11cBg==", - "dev": true, - "dependencies": { - "@lerna/child-process": "4.0.0", - "npmlog": "^4.1.2", - "path-exists": "^4.0.0", - "rimraf": "^3.0.2" - }, - "engines": { - "node": ">= 10.18.0" - } - }, - "node_modules/@lerna/run": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/@lerna/run/-/run-4.0.0.tgz", - "integrity": "sha512-9giulCOzlMPzcZS/6Eov6pxE9gNTyaXk0Man+iCIdGJNMrCnW7Dme0Z229WWP/UoxDKg71F2tMsVVGDiRd8fFQ==", - "dev": true, - "dependencies": { - "@lerna/command": "4.0.0", - "@lerna/filter-options": "4.0.0", - "@lerna/npm-run-script": "4.0.0", - "@lerna/output": "4.0.0", - "@lerna/profiler": "4.0.0", - "@lerna/run-topologically": "4.0.0", - "@lerna/timer": "4.0.0", - "@lerna/validation-error": "4.0.0", - "p-map": "^4.0.0" - }, - "engines": { - "node": ">= 10.18.0" - } - }, - "node_modules/@lerna/run-lifecycle": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/@lerna/run-lifecycle/-/run-lifecycle-4.0.0.tgz", - "integrity": "sha512-IwxxsajjCQQEJAeAaxF8QdEixfI7eLKNm4GHhXHrgBu185JcwScFZrj9Bs+PFKxwb+gNLR4iI5rpUdY8Y0UdGQ==", - "dev": true, - "dependencies": { - "@lerna/npm-conf": "4.0.0", - "npm-lifecycle": "^3.1.5", - "npmlog": "^4.1.2" - }, - "engines": { - "node": ">= 10.18.0" - } - }, - "node_modules/@lerna/run-topologically": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/@lerna/run-topologically/-/run-topologically-4.0.0.tgz", - "integrity": "sha512-EVZw9hGwo+5yp+VL94+NXRYisqgAlj0jWKWtAIynDCpghRxCE5GMO3xrQLmQgqkpUl9ZxQFpICgYv5DW4DksQA==", - "dev": true, - "dependencies": { - "@lerna/query-graph": "4.0.0", - "p-queue": "^6.6.2" - }, - "engines": { - "node": ">= 10.18.0" - } - }, - "node_modules/@lerna/symlink-binary": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/@lerna/symlink-binary/-/symlink-binary-4.0.0.tgz", - "integrity": "sha512-zualodWC4q1QQc1pkz969hcFeWXOsVYZC5AWVtAPTDfLl+TwM7eG/O6oP+Rr3fFowspxo6b1TQ6sYfDV6HXNWA==", - "dev": true, - "dependencies": { - "@lerna/create-symlink": "4.0.0", - "@lerna/package": "4.0.0", - "fs-extra": "^9.1.0", - "p-map": "^4.0.0" - }, - "engines": { - "node": ">= 10.18.0" - } - }, - "node_modules/@lerna/symlink-dependencies": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/@lerna/symlink-dependencies/-/symlink-dependencies-4.0.0.tgz", - "integrity": "sha512-BABo0MjeUHNAe2FNGty1eantWp8u83BHSeIMPDxNq0MuW2K3CiQRaeWT3EGPAzXpGt0+hVzBrA6+OT0GPn7Yuw==", - "dev": true, - "dependencies": { - "@lerna/create-symlink": "4.0.0", - "@lerna/resolve-symlink": "4.0.0", - "@lerna/symlink-binary": "4.0.0", - "fs-extra": "^9.1.0", - "p-map": "^4.0.0", - "p-map-series": "^2.1.0" - }, - "engines": { - "node": ">= 10.18.0" - } - }, - "node_modules/@lerna/timer": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/@lerna/timer/-/timer-4.0.0.tgz", - "integrity": "sha512-WFsnlaE7SdOvjuyd05oKt8Leg3ENHICnvX3uYKKdByA+S3g+TCz38JsNs7OUZVt+ba63nC2nbXDlUnuT2Xbsfg==", - "dev": true, - "engines": { - "node": ">= 10.18.0" - } - }, - "node_modules/@lerna/validation-error": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/@lerna/validation-error/-/validation-error-4.0.0.tgz", - "integrity": "sha512-1rBOM5/koiVWlRi3V6dB863E1YzJS8v41UtsHgMr6gB2ncJ2LsQtMKlJpi3voqcgh41H8UsPXR58RrrpPpufyw==", - "dev": true, - "dependencies": { - "npmlog": "^4.1.2" - }, - "engines": { - "node": ">= 10.18.0" - } - }, - "node_modules/@lerna/version": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/@lerna/version/-/version-4.0.0.tgz", - "integrity": "sha512-otUgiqs5W9zGWJZSCCMRV/2Zm2A9q9JwSDS7s/tlKq4mWCYriWo7+wsHEA/nPTMDyYyBO5oyZDj+3X50KDUzeA==", - "dev": true, - "dependencies": { - "@lerna/check-working-tree": "4.0.0", - "@lerna/child-process": "4.0.0", - "@lerna/collect-updates": "4.0.0", - "@lerna/command": "4.0.0", - "@lerna/conventional-commits": "4.0.0", - "@lerna/github-client": "4.0.0", - "@lerna/gitlab-client": "4.0.0", - "@lerna/output": "4.0.0", - "@lerna/prerelease-id-from-version": "4.0.0", - "@lerna/prompt": "4.0.0", - "@lerna/run-lifecycle": "4.0.0", - "@lerna/run-topologically": "4.0.0", - "@lerna/validation-error": "4.0.0", - "chalk": "^4.1.0", - "dedent": "^0.7.0", - "load-json-file": "^6.2.0", - "minimatch": "^3.0.4", - "npmlog": "^4.1.2", - "p-map": "^4.0.0", - "p-pipe": "^3.1.0", - "p-reduce": "^2.1.0", - "p-waterfall": "^2.1.1", - "semver": "^7.3.4", - "slash": "^3.0.0", - "temp-write": "^4.0.0", - "write-json-file": "^4.3.0" - }, - "engines": { - "node": ">= 10.18.0" - } - }, - "node_modules/@lerna/write-log-file": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/@lerna/write-log-file/-/write-log-file-4.0.0.tgz", - "integrity": "sha512-XRG5BloiArpXRakcnPHmEHJp+4AtnhRtpDIHSghmXD5EichI1uD73J7FgPp30mm2pDRq3FdqB0NbwSEsJ9xFQg==", - "dev": true, - "dependencies": { - "npmlog": "^4.1.2", - "write-file-atomic": "^3.0.3" - }, - "engines": { - "node": ">= 10.18.0" - } - }, - "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/@npmcli/ci-detect": { - "version": "1.4.0", - "resolved": "https://registry.npmjs.org/@npmcli/ci-detect/-/ci-detect-1.4.0.tgz", - "integrity": "sha512-3BGrt6FLjqM6br5AhWRKTr3u5GIVkjRYeAFrMp3HjnfICrg4xOrVRwFavKT6tsp++bq5dluL5t8ME/Nha/6c1Q==", - "dev": true - }, - "node_modules/@npmcli/fs": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/@npmcli/fs/-/fs-1.1.0.tgz", - "integrity": "sha512-VhP1qZLXcrXRIaPoqb4YA55JQxLNF3jNR4T55IdOJa3+IFJKNYHtPvtXx8slmeMavj37vCzCfrqQM1vWLsYKLA==", - "dev": true, - "dependencies": { - "@gar/promisify": "^1.0.1", - "semver": "^7.3.5" - }, - "engines": { - "node": "^12.13.0 || ^14.15.0 || >=16" - } - }, - "node_modules/@npmcli/git": { - "version": "2.1.0", - "resolved": "https://registry.npmjs.org/@npmcli/git/-/git-2.1.0.tgz", - "integrity": "sha512-/hBFX/QG1b+N7PZBFs0bi+evgRZcK9nWBxQKZkGoXUT5hJSwl5c4d7y8/hm+NQZRPhQ67RzFaj5UM9YeyKoryw==", - "dev": true, - "dependencies": { - "@npmcli/promise-spawn": "^1.3.2", - "lru-cache": "^6.0.0", - "mkdirp": "^1.0.4", - "npm-pick-manifest": "^6.1.1", - "promise-inflight": "^1.0.1", - "promise-retry": "^2.0.1", - "semver": "^7.3.5", - "which": "^2.0.2" - } - }, - "node_modules/@npmcli/installed-package-contents": { - "version": "1.0.7", - "resolved": "https://registry.npmjs.org/@npmcli/installed-package-contents/-/installed-package-contents-1.0.7.tgz", - "integrity": "sha512-9rufe0wnJusCQoLpV9ZPKIVP55itrM5BxOXs10DmdbRfgWtHy1LDyskbwRnBghuB0PrF7pNPOqREVtpz4HqzKw==", - "dev": true, - "dependencies": { - "npm-bundled": "^1.1.1", - "npm-normalize-package-bin": "^1.0.1" - }, - "bin": { - "installed-package-contents": "index.js" - }, - "engines": { - "node": ">= 10" - } - }, - "node_modules/@npmcli/move-file": { - "version": "1.1.2", - "resolved": "https://registry.npmjs.org/@npmcli/move-file/-/move-file-1.1.2.tgz", - "integrity": "sha512-1SUf/Cg2GzGDyaf15aR9St9TWlb+XvbZXWpDx8YKs7MLzMH/BCeopv+y9vzrzgkfykCGuWOlSu3mZhj2+FQcrg==", - "dev": true, - "dependencies": { - "mkdirp": "^1.0.4", - "rimraf": "^3.0.2" - }, - "engines": { - "node": ">=10" - } - }, - "node_modules/@npmcli/node-gyp": { - "version": "1.0.3", - "resolved": "https://registry.npmjs.org/@npmcli/node-gyp/-/node-gyp-1.0.3.tgz", - "integrity": "sha512-fnkhw+fmX65kiLqk6E3BFLXNC26rUhK90zVwe2yncPliVT/Qos3xjhTLE59Df8KnPlcwIERXKVlU1bXoUQ+liA==", - "dev": true - }, - "node_modules/@npmcli/promise-spawn": { - "version": "1.3.2", - "resolved": "https://registry.npmjs.org/@npmcli/promise-spawn/-/promise-spawn-1.3.2.tgz", - "integrity": "sha512-QyAGYo/Fbj4MXeGdJcFzZ+FkDkomfRBrPM+9QYJSg+PxgAUL+LU3FneQk37rKR2/zjqkCV1BLHccX98wRXG3Sg==", - "dev": true, - "dependencies": { - "infer-owner": "^1.0.4" - } - }, - "node_modules/@npmcli/run-script": { - "version": "1.8.6", - "resolved": "https://registry.npmjs.org/@npmcli/run-script/-/run-script-1.8.6.tgz", - "integrity": "sha512-e42bVZnC6VluBZBAFEr3YrdqSspG3bgilyg4nSLBJ7TRGNCzxHa92XAHxQBLYg0BmgwO4b2mf3h/l5EkEWRn3g==", - "dev": true, - "dependencies": { - "@npmcli/node-gyp": "^1.0.2", - "@npmcli/promise-spawn": "^1.3.2", - "node-gyp": "^7.1.0", - "read-package-json-fast": "^2.0.1" - } - }, - "node_modules/@npmcli/run-script/node_modules/node-gyp": { - "version": "7.1.2", - "resolved": "https://registry.npmjs.org/node-gyp/-/node-gyp-7.1.2.tgz", - "integrity": "sha512-CbpcIo7C3eMu3dL1c3d0xw449fHIGALIJsRP4DDPHpyiW8vcriNY7ubh9TE4zEKfSxscY7PjeFnshE7h75ynjQ==", - "dev": true, - "dependencies": { - "env-paths": "^2.2.0", - "glob": "^7.1.4", - "graceful-fs": "^4.2.3", - "nopt": "^5.0.0", - "npmlog": "^4.1.2", - "request": "^2.88.2", - "rimraf": "^3.0.2", - "semver": "^7.3.2", - "tar": "^6.0.2", - "which": "^2.0.2" - }, - "bin": { - "node-gyp": "bin/node-gyp.js" - }, - "engines": { - "node": ">= 10.12.0" - } - }, - "node_modules/@npmcli/run-script/node_modules/nopt": { - "version": "5.0.0", - "resolved": "https://registry.npmjs.org/nopt/-/nopt-5.0.0.tgz", - "integrity": "sha512-Tbj67rffqceeLpcRXrT7vKAN8CwfPeIBgM7E6iBkmKLV7bEMwpGgYLGv0jACUsECaa/vuxP0IjEont6umdMgtQ==", - "dev": true, - "dependencies": { - "abbrev": "1" - }, - "bin": { - "nopt": "bin/nopt.js" - }, - "engines": { - "node": ">=6" - } - }, - "node_modules/@octokit/auth-token": { - "version": "2.5.0", - "resolved": "https://registry.npmjs.org/@octokit/auth-token/-/auth-token-2.5.0.tgz", - "integrity": "sha512-r5FVUJCOLl19AxiuZD2VRZ/ORjp/4IN98Of6YJoJOkY75CIBuYfmiNHGrDwXr+aLGG55igl9QrxX3hbiXlLb+g==", - "dev": true, - "dependencies": { - "@octokit/types": "^6.0.3" - } - }, - "node_modules/@octokit/core": { - "version": "3.5.1", - "resolved": "https://registry.npmjs.org/@octokit/core/-/core-3.5.1.tgz", - "integrity": "sha512-omncwpLVxMP+GLpLPgeGJBF6IWJFjXDS5flY5VbppePYX9XehevbDykRH9PdCdvqt9TS5AOTiDide7h0qrkHjw==", - "dev": true, - "dependencies": { - "@octokit/auth-token": "^2.4.4", - "@octokit/graphql": "^4.5.8", - "@octokit/request": "^5.6.0", - "@octokit/request-error": "^2.0.5", - "@octokit/types": "^6.0.3", - "before-after-hook": "^2.2.0", - "universal-user-agent": "^6.0.0" - } - }, - "node_modules/@octokit/endpoint": { - "version": "6.0.12", - "resolved": "https://registry.npmjs.org/@octokit/endpoint/-/endpoint-6.0.12.tgz", - "integrity": "sha512-lF3puPwkQWGfkMClXb4k/eUT/nZKQfxinRWJrdZaJO85Dqwo/G0yOC434Jr2ojwafWJMYqFGFa5ms4jJUgujdA==", - "dev": true, - "dependencies": { - "@octokit/types": "^6.0.3", - "is-plain-object": "^5.0.0", - "universal-user-agent": "^6.0.0" - } - }, - "node_modules/@octokit/graphql": { - "version": "4.8.0", - "resolved": "https://registry.npmjs.org/@octokit/graphql/-/graphql-4.8.0.tgz", - "integrity": "sha512-0gv+qLSBLKF0z8TKaSKTsS39scVKF9dbMxJpj3U0vC7wjNWFuIpL/z76Qe2fiuCbDRcJSavkXsVtMS6/dtQQsg==", - "dev": true, - "dependencies": { - "@octokit/request": "^5.6.0", - "@octokit/types": "^6.0.3", - "universal-user-agent": "^6.0.0" - } - }, - "node_modules/@octokit/openapi-types": { - "version": "11.2.0", - "resolved": "https://registry.npmjs.org/@octokit/openapi-types/-/openapi-types-11.2.0.tgz", - "integrity": "sha512-PBsVO+15KSlGmiI8QAzaqvsNlZlrDlyAJYcrXBCvVUxCp7VnXjkwPoFHgjEJXx3WF9BAwkA6nfCUA7i9sODzKA==", - "dev": true - }, - "node_modules/@octokit/plugin-enterprise-rest": { - "version": "6.0.1", - "resolved": "https://registry.npmjs.org/@octokit/plugin-enterprise-rest/-/plugin-enterprise-rest-6.0.1.tgz", - "integrity": "sha512-93uGjlhUD+iNg1iWhUENAtJata6w5nE+V4urXOAlIXdco6xNZtUSfYY8dzp3Udy74aqO/B5UZL80x/YMa5PKRw==", - "dev": true - }, - "node_modules/@octokit/plugin-paginate-rest": { - "version": "2.17.0", - "resolved": "https://registry.npmjs.org/@octokit/plugin-paginate-rest/-/plugin-paginate-rest-2.17.0.tgz", - "integrity": "sha512-tzMbrbnam2Mt4AhuyCHvpRkS0oZ5MvwwcQPYGtMv4tUa5kkzG58SVB0fcsLulOZQeRnOgdkZWkRUiyBlh0Bkyw==", - "dev": true, - "dependencies": { - "@octokit/types": "^6.34.0" - }, - "peerDependencies": { - "@octokit/core": ">=2" - } - }, - "node_modules/@octokit/plugin-request-log": { - "version": "1.0.4", - "resolved": "https://registry.npmjs.org/@octokit/plugin-request-log/-/plugin-request-log-1.0.4.tgz", - "integrity": "sha512-mLUsMkgP7K/cnFEw07kWqXGF5LKrOkD+lhCrKvPHXWDywAwuDUeDwWBpc69XK3pNX0uKiVt8g5z96PJ6z9xCFA==", - "dev": true, - "peerDependencies": { - "@octokit/core": ">=3" - } - }, - "node_modules/@octokit/plugin-rest-endpoint-methods": { - "version": "5.13.0", - "resolved": "https://registry.npmjs.org/@octokit/plugin-rest-endpoint-methods/-/plugin-rest-endpoint-methods-5.13.0.tgz", - "integrity": "sha512-uJjMTkN1KaOIgNtUPMtIXDOjx6dGYysdIFhgA52x4xSadQCz3b/zJexvITDVpANnfKPW/+E0xkOvLntqMYpviA==", - "dev": true, - "dependencies": { - "@octokit/types": "^6.34.0", - "deprecation": "^2.3.1" - }, - "peerDependencies": { - "@octokit/core": ">=3" - } - }, - "node_modules/@octokit/request": { - "version": "5.6.2", - "resolved": "https://registry.npmjs.org/@octokit/request/-/request-5.6.2.tgz", - "integrity": "sha512-je66CvSEVf0jCpRISxkUcCa0UkxmFs6eGDRSbfJtAVwbLH5ceqF+YEyC8lj8ystKyZTy8adWr0qmkY52EfOeLA==", - "dev": true, - "dependencies": { - "@octokit/endpoint": "^6.0.1", - "@octokit/request-error": "^2.1.0", - "@octokit/types": "^6.16.1", - "is-plain-object": "^5.0.0", - "node-fetch": "^2.6.1", - "universal-user-agent": "^6.0.0" - } - }, - "node_modules/@octokit/request-error": { - "version": "2.1.0", - "resolved": "https://registry.npmjs.org/@octokit/request-error/-/request-error-2.1.0.tgz", - "integrity": "sha512-1VIvgXxs9WHSjicsRwq8PlR2LR2x6DwsJAaFgzdi0JfJoGSO8mYI/cHJQ+9FbN21aa+DrgNLnwObmyeSC8Rmpg==", - "dev": true, - "dependencies": { - "@octokit/types": "^6.0.3", - "deprecation": "^2.0.0", - "once": "^1.4.0" - } - }, - "node_modules/@octokit/rest": { - "version": "18.12.0", - "resolved": "https://registry.npmjs.org/@octokit/rest/-/rest-18.12.0.tgz", - "integrity": "sha512-gDPiOHlyGavxr72y0guQEhLsemgVjwRePayJ+FcKc2SJqKUbxbkvf5kAZEWA/MKvsfYlQAMVzNJE3ezQcxMJ2Q==", - "dev": true, - "dependencies": { - "@octokit/core": "^3.5.1", - "@octokit/plugin-paginate-rest": "^2.16.8", - "@octokit/plugin-request-log": "^1.0.4", - "@octokit/plugin-rest-endpoint-methods": "^5.12.0" - } - }, - "node_modules/@octokit/types": { - "version": "6.34.0", - "resolved": "https://registry.npmjs.org/@octokit/types/-/types-6.34.0.tgz", - "integrity": "sha512-s1zLBjWhdEI2zwaoSgyOFoKSl109CUcVBCc7biPJ3aAf6LGLU6szDvi31JPU7bxfla2lqfhjbbg/5DdFNxOwHw==", - "dev": true, - "dependencies": { - "@octokit/openapi-types": "^11.2.0" - } - }, - "node_modules/@sindresorhus/is": { - "version": "0.14.0", - "resolved": "https://registry.npmjs.org/@sindresorhus/is/-/is-0.14.0.tgz", - "integrity": "sha512-9NET910DNaIPngYnLLPeg+Ogzqsi9uM4mSboU5y6p8S5DzMTVEsJZrawi+BoDNUVBa2DhJqQYUFvMDfgU062LQ==", - "dev": true, - "engines": { - "node": ">=6" - } - }, - "node_modules/@socket.io/component-emitter": { - "version": "3.0.0", - "resolved": "https://registry.npmjs.org/@socket.io/component-emitter/-/component-emitter-3.0.0.tgz", - "integrity": "sha512-2pTGuibAXJswAPJjaKisthqS/NOK5ypG4LYT6tEAV0S/mxW0zOIvYvGK0V8w8+SHxAm6vRMSjqSalFXeBAqs+Q==" - }, - "node_modules/@szmarczak/http-timer": { - "version": "1.1.2", - "resolved": "https://registry.npmjs.org/@szmarczak/http-timer/-/http-timer-1.1.2.tgz", - "integrity": "sha512-XIB2XbzHTN6ieIjfIMV9hlVcfPU26s2vafYWQcZHWXHOxiaRZYEDKEwdl129Zyg50+foYV2jCgtrqSA6qNuNSA==", - "dev": true, - "dependencies": { - "defer-to-connect": "^1.0.1" - }, - "engines": { - "node": ">=6" - } - }, - "node_modules/@tootallnate/once": { - "version": "1.1.2", - "resolved": "https://registry.npmjs.org/@tootallnate/once/-/once-1.1.2.tgz", - "integrity": "sha512-RbzJvlNzmRq5c3O09UipeuXno4tA1FE6ikOjxZK0tuxVv3412l64l5t1W5pj4+rJq9vpkm/kwiR07aZXnsKPxw==", - "dev": true, - "engines": { - "node": ">= 6" - } - }, - "node_modules/@tsconfig/node10": { - "version": "1.0.8", - "resolved": "https://registry.npmjs.org/@tsconfig/node10/-/node10-1.0.8.tgz", - "integrity": "sha512-6XFfSQmMgq0CFLY1MslA/CPUfhIL919M1rMsa5lP2P097N2Wd1sSX0tx1u4olM16fLNhtHZpRhedZJphNJqmZg==" - }, - "node_modules/@tsconfig/node12": { - "version": "1.0.9", - "resolved": "https://registry.npmjs.org/@tsconfig/node12/-/node12-1.0.9.tgz", - "integrity": "sha512-/yBMcem+fbvhSREH+s14YJi18sp7J9jpuhYByADT2rypfajMZZN4WQ6zBGgBKp53NKmqI36wFYDb3yaMPurITw==" - }, - "node_modules/@tsconfig/node14": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/@tsconfig/node14/-/node14-1.0.1.tgz", - "integrity": "sha512-509r2+yARFfHHE7T6Puu2jjkoycftovhXRqW328PDXTVGKihlb1P8Z9mMZH04ebyajfRY7dedfGynlrFHJUQCg==" - }, - "node_modules/@tsconfig/node16": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/@tsconfig/node16/-/node16-1.0.2.tgz", - "integrity": "sha512-eZxlbI8GZscaGS7kkc/trHTT5xgrjH3/1n2JDwusC9iahPKWMRvRjJSAN5mCXviuTGQ/lHnhvv8Q1YTpnfz9gA==" - }, - "node_modules/@types/accepts": { - "version": "1.3.5", - "resolved": "https://registry.npmjs.org/@types/accepts/-/accepts-1.3.5.tgz", - "integrity": "sha512-jOdnI/3qTpHABjM5cx1Hc0sKsPoYCp+DP/GJRGtDlPd7fiV9oXGGIcjW/ZOxLIvjGz8MA+uMZI9metHlgqbgwQ==", - "dependencies": { - "@types/node": "*" - } - }, - "node_modules/@types/axios": { - "version": "0.14.0", - "resolved": "https://registry.npmjs.org/@types/axios/-/axios-0.14.0.tgz", - "integrity": "sha1-7CMA++fX3d1+udOr+HmZlkyvzkY=", - "deprecated": "This is a stub types definition for axios (https://github.com/mzabriskie/axios). axios provides its own type definitions, so you don't need @types/axios installed!", - "dependencies": { - "axios": "*" - } - }, - "node_modules/@types/bcryptjs": { - "version": "2.4.2", - "resolved": "https://registry.npmjs.org/@types/bcryptjs/-/bcryptjs-2.4.2.tgz", - "integrity": "sha512-LiMQ6EOPob/4yUL66SZzu6Yh77cbzJFYll+ZfaPiPPFswtIlA/Fs1MzdKYA7JApHU49zQTbJGX3PDmCpIdDBRQ==" - }, - "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==", - "dependencies": { - "@types/connect": "*", - "@types/node": "*" - } - }, - "node_modules/@types/component-emitter": { - "version": "1.2.11", - "resolved": "https://registry.npmjs.org/@types/component-emitter/-/component-emitter-1.2.11.tgz", - "integrity": "sha512-SRXjM+tfsSlA9VuG8hGO2nft2p8zjXCK1VcC6N4NXbBbYbSia9kzCChYQajIjzIqOOOuh5Ock6MmV2oux4jDZQ==" - }, - "node_modules/@types/config": { - "version": "0.0.40", - "resolved": "https://registry.npmjs.org/@types/config/-/config-0.0.40.tgz", - "integrity": "sha512-4s7JAciBzCJVy0fp7LPsMj0v3F+IeTdjpwMQ6owOx67UjcyurjP+8DO556u5/8PUhifAYp7H5b7D88RKFDBGEg==" - }, - "node_modules/@types/connect": { - "version": "3.4.35", - "resolved": "https://registry.npmjs.org/@types/connect/-/connect-3.4.35.tgz", - "integrity": "sha512-cdeYyv4KWoEgpBISTxWvqYsVy444DOqehiF3fM3ne10AmJ62RSyNkUnxMJXHQWRQQX2eR94m5y1IZyDwBjV9FQ==", - "dependencies": { - "@types/node": "*" - } - }, - "node_modules/@types/content-disposition": { - "version": "0.5.4", - "resolved": "https://registry.npmjs.org/@types/content-disposition/-/content-disposition-0.5.4.tgz", - "integrity": "sha512-0mPF08jn9zYI0n0Q/Pnz7C4kThdSt+6LD4amsrYDDpgBfrVWa3TcCOxKX1zkGgYniGagRv8heN2cbh+CAn+uuQ==" - }, - "node_modules/@types/cookie": { - "version": "0.4.1", - "resolved": "https://registry.npmjs.org/@types/cookie/-/cookie-0.4.1.tgz", - "integrity": "sha512-XW/Aa8APYr6jSVVA1y/DEIZX0/GMKLEVekNG727R8cs56ahETkRAy/3DR7+fJyh7oUgGwNQaRfXCun0+KbWY7Q==" - }, - "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==" - }, - "node_modules/@types/cookies": { - "version": "0.7.7", - "resolved": "https://registry.npmjs.org/@types/cookies/-/cookies-0.7.7.tgz", - "integrity": "sha512-h7BcvPUogWbKCzBR2lY4oqaZbO3jXZksexYJVFvkrFeLgbZjQkU4x8pRq6eg2MHXQhY0McQdqmmsxRWlVAHooA==", - "dependencies": { - "@types/connect": "*", - "@types/express": "*", - "@types/keygrip": "*", - "@types/node": "*" - } - }, - "node_modules/@types/cors": { - "version": "2.8.12", - "resolved": "https://registry.npmjs.org/@types/cors/-/cors-2.8.12.tgz", - "integrity": "sha512-vt+kDhq/M2ayberEtJcIN/hxXy1Pk+59g2FV/ZQceeaTyCtCucjL2Q7FXlFjtWn4n15KCr1NE2lNNFhp0lEThw==" - }, - "node_modules/@types/eslint": { - "version": "8.2.1", - "resolved": "https://registry.npmjs.org/@types/eslint/-/eslint-8.2.1.tgz", - "integrity": "sha512-UP9rzNn/XyGwb5RQ2fok+DzcIRIYwc16qTXse5+Smsy8MOIccCChT15KAwnsgQx4PzJkaMq4myFyZ4CL5TjhIQ==", - "dependencies": { - "@types/estree": "*", - "@types/json-schema": "*" - } - }, - "node_modules/@types/eslint-scope": { - "version": "3.7.2", - "resolved": "https://registry.npmjs.org/@types/eslint-scope/-/eslint-scope-3.7.2.tgz", - "integrity": "sha512-TzgYCWoPiTeRg6RQYgtuW7iODtVoKu3RVL72k3WohqhjfaOLK5Mg2T4Tg1o2bSfu0vPkoI48wdQFv5b/Xe04wQ==", - "dependencies": { - "@types/eslint": "*", - "@types/estree": "*" - } - }, - "node_modules/@types/estree": { - "version": "0.0.50", - "resolved": "https://registry.npmjs.org/@types/estree/-/estree-0.0.50.tgz", - "integrity": "sha512-C6N5s2ZFtuZRj54k2/zyRhNDjJwwcViAM3Nbm8zjBpbqAdZ00mr0CFxvSKeO8Y/e03WVFLpQMdHYVfUd6SB+Hw==" - }, - "node_modules/@types/express": { - "version": "4.17.13", - "resolved": "https://registry.npmjs.org/@types/express/-/express-4.17.13.tgz", - "integrity": "sha512-6bSZTPaTIACxn48l50SR+axgrqm6qXFIxrdAKaG6PaJk3+zuUr35hBlgT7vOmJcum+OEaIBLtHV/qloEAFITeA==", - "dependencies": { - "@types/body-parser": "*", - "@types/express-serve-static-core": "^4.17.18", - "@types/qs": "*", - "@types/serve-static": "*" - } - }, - "node_modules/@types/express-serve-static-core": { - "version": "4.17.27", - "resolved": "https://registry.npmjs.org/@types/express-serve-static-core/-/express-serve-static-core-4.17.27.tgz", - "integrity": "sha512-e/sVallzUTPdyOTiqi8O8pMdBBphscvI6E4JYaKlja4Lm+zh7UFSSdW5VMkRbhDtmrONqOUHOXRguPsDckzxNA==", - "dependencies": { - "@types/node": "*", - "@types/qs": "*", - "@types/range-parser": "*" - } - }, - "node_modules/@types/express-session": { - "version": "1.17.4", - "resolved": "https://registry.npmjs.org/@types/express-session/-/express-session-1.17.4.tgz", - "integrity": "sha512-7cNlSI8+oOBUHTfPXMwDxF/Lchx5aJ3ho7+p9jJZYVg9dVDJFh3qdMXmJtRsysnvS+C6x46k9DRYmrmCkE+MVg==", - "dependencies": { - "@types/express": "*" - } - }, - "node_modules/@types/http-assert": { - "version": "1.5.3", - "resolved": "https://registry.npmjs.org/@types/http-assert/-/http-assert-1.5.3.tgz", - "integrity": "sha512-FyAOrDuQmBi8/or3ns4rwPno7/9tJTijVW6aQQjK02+kOQ8zmoNg2XJtAuQhvQcy1ASJq38wirX5//9J1EqoUA==" - }, - "node_modules/@types/http-errors": { - "version": "1.8.1", - "resolved": "https://registry.npmjs.org/@types/http-errors/-/http-errors-1.8.1.tgz", - "integrity": "sha512-e+2rjEwK6KDaNOm5Aa9wNGgyS9oSZU/4pfSMMPYNOfjvFI0WVXm29+ITRFr6aKDvvKo7uU1jV68MW4ScsfDi7Q==" - }, - "node_modules/@types/json-schema": { - "version": "7.0.9", - "resolved": "https://registry.npmjs.org/@types/json-schema/-/json-schema-7.0.9.tgz", - "integrity": "sha512-qcUXuemtEu+E5wZSJHNxUXeCZhAfXKQ41D+duX+VYPde7xyEVZci+/oXKJL13tnRs9lR2pr4fod59GT6/X1/yQ==" - }, - "node_modules/@types/json5": { - "version": "0.0.29", - "resolved": "https://registry.npmjs.org/@types/json5/-/json5-0.0.29.tgz", - "integrity": "sha1-7ihweulOEdK4J7y+UnC86n8+ce4=", - "dev": true - }, - "node_modules/@types/jsonwebtoken": { - "version": "8.5.6", - "resolved": "https://registry.npmjs.org/@types/jsonwebtoken/-/jsonwebtoken-8.5.6.tgz", - "integrity": "sha512-+P3O/xC7nzVizIi5VbF34YtqSonFsdnbXBnWUCYRiKOi1f9gA4sEFvXkrGr/QVV23IbMYvcoerI7nnhDUiWXRQ==", - "dependencies": { - "@types/node": "*" - } - }, - "node_modules/@types/keygrip": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/@types/keygrip/-/keygrip-1.0.2.tgz", - "integrity": "sha512-GJhpTepz2udxGexqos8wgaBx4I/zWIDPh/KOGEwAqtuGDkOUJu5eFvwmdBX4AmB8Odsr+9pHCQqiAqDL/yKMKw==" - }, - "node_modules/@types/koa": { - "version": "2.13.4", - "resolved": "https://registry.npmjs.org/@types/koa/-/koa-2.13.4.tgz", - "integrity": "sha512-dfHYMfU+z/vKtQB7NUrthdAEiSvnLebvBjwHtfFmpZmB7em2N3WVQdHgnFq+xvyVgxW5jKDmjWfLD3lw4g4uTw==", - "dependencies": { - "@types/accepts": "*", - "@types/content-disposition": "*", - "@types/cookies": "*", - "@types/http-assert": "*", - "@types/http-errors": "*", - "@types/keygrip": "*", - "@types/koa-compose": "*", - "@types/node": "*" - } - }, - "node_modules/@types/koa-bodyparser": { - "version": "4.3.5", - "resolved": "https://registry.npmjs.org/@types/koa-bodyparser/-/koa-bodyparser-4.3.5.tgz", - "integrity": "sha512-NRqqoTtt7cfdDk/KNo+EwCIKRuzPAu/wsaZ7tgIvSIBtNfxuZHYueaLoWdxX3ZftWavQv07NE46TcpyoZGqpgQ==", - "dependencies": { - "@types/koa": "*" - } - }, - "node_modules/@types/koa-compose": { - "version": "3.2.5", - "resolved": "https://registry.npmjs.org/@types/koa-compose/-/koa-compose-3.2.5.tgz", - "integrity": "sha512-B8nG/OoE1ORZqCkBVsup/AKcvjdgoHnfi4pZMn5UwAPCbhk/96xyv284eBYW8JlQbQ7zDmnpFr68I/40mFoIBQ==", - "dependencies": { - "@types/koa": "*" - } - }, - "node_modules/@types/koa-qs": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/@types/koa-qs/-/koa-qs-2.0.0.tgz", - "integrity": "sha512-cBfbUvW70JsU2FCgUCFOoretdvayGzRJ2vEyNQbnZ7vb2pZ/QA+gcNzE6nVxxCcrcnRtGB7tXIRHqHPXS51utA==", - "dependencies": { - "@types/koa": "*" - } - }, - "node_modules/@types/lodash": { - "version": "4.14.178", - "resolved": "https://registry.npmjs.org/@types/lodash/-/lodash-4.14.178.tgz", - "integrity": "sha512-0d5Wd09ItQWH1qFbEyQ7oTQ3GZrMfth5JkbN3EvTKLXcHLRDSXeLnlvlOn0wvxVIwK5o2M8JzP/OWz7T3NRsbw==" - }, - "node_modules/@types/mime": { - "version": "1.3.2", - "resolved": "https://registry.npmjs.org/@types/mime/-/mime-1.3.2.tgz", - "integrity": "sha512-YATxVxgRqNH6nHEIsvg6k2Boc1JHI9ZbH5iWFFv/MTkchz3b1ieGDa5T0a9RznNdI0KhVbdbWSN+KWWrQZRxTw==" - }, - "node_modules/@types/minimatch": { - "version": "3.0.5", - "resolved": "https://registry.npmjs.org/@types/minimatch/-/minimatch-3.0.5.tgz", - "integrity": "sha512-Klz949h02Gz2uZCMGwDUSDS1YBlTdDDgbWHi+81l29tQALUtvz4rAYi5uoVhE5Lagoq6DeqAUlbrHvW/mXDgdQ==", - "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/mocha": { - "version": "9.0.0", - "resolved": "https://registry.npmjs.org/@types/mocha/-/mocha-9.0.0.tgz", - "integrity": "sha512-scN0hAWyLVAvLR9AyW7HoFF5sJZglyBsbPuHO4fv7JRvfmPBMfp1ozWqOf/e4wwPNxezBZXRfWzMb6iFLgEVRA==" - }, - "node_modules/@types/mongodb": { - "version": "4.0.7", - "resolved": "https://registry.npmjs.org/@types/mongodb/-/mongodb-4.0.7.tgz", - "integrity": "sha512-lPUYPpzA43baXqnd36cZ9xxorprybxXDzteVKCPAdp14ppHtFJHnXYvNpmBvtMUTb5fKXVv6sVbzo1LHkWhJlw==", - "deprecated": "mongodb provides its own types. @types/mongodb is no longer needed.", - "dependencies": { - "mongodb": "*" - } - }, - "node_modules/@types/node": { - "version": "17.0.7", - "resolved": "https://registry.npmjs.org/@types/node/-/node-17.0.7.tgz", - "integrity": "sha512-1QUk+WAUD4t8iR+Oj+UgI8oJa6yyxaB8a8pHaC8uqM6RrS1qbL7bf3Pwl5rHv0psm2CuDErgho6v5N+G+5fwtQ==" - }, - "node_modules/@types/node-fetch": { - "version": "3.0.3", - "resolved": "https://registry.npmjs.org/@types/node-fetch/-/node-fetch-3.0.3.tgz", - "integrity": "sha512-HhggYPH5N+AQe/OmN6fmhKmRRt2XuNJow+R3pQwJxOOF9GuwM7O2mheyGeIrs5MOIeNjDEdgdoyHBOrFeJBR3g==", - "deprecated": "This is a stub types definition. node-fetch provides its own type definitions, so you do not need this installed.", - "dependencies": { - "node-fetch": "*" - } - }, - "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", - "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==" - }, - "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==" - }, - "node_modules/@types/serve-static": { - "version": "1.13.10", - "resolved": "https://registry.npmjs.org/@types/serve-static/-/serve-static-1.13.10.tgz", - "integrity": "sha512-nCkHGI4w7ZgAdNkrEu0bv+4xNV/XDqW+DydknebMOQwkpDGx8G+HTlj7R7ABI8i8nKxVw0wtKPi1D+lPOkh4YQ==", - "dependencies": { - "@types/mime": "^1", - "@types/node": "*" - } - }, - "node_modules/@types/superagent": { - "version": "4.1.14", - "resolved": "https://registry.npmjs.org/@types/superagent/-/superagent-4.1.14.tgz", - "integrity": "sha512-iiXaOL2wSbnSY4qg0mFPWJHL9iwyEsoNYwaHF2w58/fsVAQJlj+KUfFAFZu+nzbz+b7dUprJEAc+O9vhHHhQTA==", - "dependencies": { - "@types/cookiejar": "*", - "@types/node": "*" - } - }, - "node_modules/@types/uuid": { - "version": "8.3.3", - "resolved": "https://registry.npmjs.org/@types/uuid/-/uuid-8.3.3.tgz", - "integrity": "sha512-0LbEEx1zxrYB3pgpd1M5lEhLcXjKJnYghvhTRgaBeUivLHMDM1TzF3IJ6hXU2+8uA4Xz+5BA63mtZo5DjVT8iA==" - }, - "node_modules/@types/webidl-conversions": { - "version": "6.1.1", - "resolved": "https://registry.npmjs.org/@types/webidl-conversions/-/webidl-conversions-6.1.1.tgz", - "integrity": "sha512-XAahCdThVuCFDQLT7R7Pk/vqeObFNL3YqRyFZg+AqAP/W1/w3xHaIxuW7WszQqTbIBOPRcItYJIou3i/mppu3Q==" - }, - "node_modules/@types/whatwg-url": { - "version": "8.2.1", - "resolved": "https://registry.npmjs.org/@types/whatwg-url/-/whatwg-url-8.2.1.tgz", - "integrity": "sha512-2YubE1sjj5ifxievI5Ge1sckb9k/Er66HyR2c+3+I6VDUUg1TLPdYYTEbQ+DjRkS4nTxMJhgWfSfMRD2sl2EYQ==", - "dependencies": { - "@types/node": "*", - "@types/webidl-conversions": "*" - } - }, - "node_modules/@typescript-eslint/eslint-plugin": { - "version": "5.9.0", - "resolved": "https://registry.npmjs.org/@typescript-eslint/eslint-plugin/-/eslint-plugin-5.9.0.tgz", - "integrity": "sha512-qT4lr2jysDQBQOPsCCvpPUZHjbABoTJW8V9ZzIYKHMfppJtpdtzszDYsldwhFxlhvrp7aCHeXD1Lb9M1zhwWwQ==", - "dev": true, - "dependencies": { - "@typescript-eslint/experimental-utils": "5.9.0", - "@typescript-eslint/scope-manager": "5.9.0", - "@typescript-eslint/type-utils": "5.9.0", - "debug": "^4.3.2", - "functional-red-black-tree": "^1.0.1", - "ignore": "^5.1.8", - "regexpp": "^3.2.0", - "semver": "^7.3.5", - "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/experimental-utils": { - "version": "5.9.0", - "resolved": "https://registry.npmjs.org/@typescript-eslint/experimental-utils/-/experimental-utils-5.9.0.tgz", - "integrity": "sha512-ZnLVjBrf26dn7ElyaSKa6uDhqwvAi4jBBmHK1VxuFGPRAxhdi18ubQYSGA7SRiFiES3q9JiBOBHEBStOFkwD2g==", - "dev": true, - "dependencies": { - "@types/json-schema": "^7.0.9", - "@typescript-eslint/scope-manager": "5.9.0", - "@typescript-eslint/types": "5.9.0", - "@typescript-eslint/typescript-estree": "5.9.0", - "eslint-scope": "^5.1.1", - "eslint-utils": "^3.0.0" - }, - "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/parser": { - "version": "5.9.0", - "resolved": "https://registry.npmjs.org/@typescript-eslint/parser/-/parser-5.9.0.tgz", - "integrity": "sha512-/6pOPz8yAxEt4PLzgbFRDpZmHnXCeZgPDrh/1DaVKOjvn/UPMlWhbx/gA96xRi2JxY1kBl2AmwVbyROUqys5xQ==", - "dev": true, - "dependencies": { - "@typescript-eslint/scope-manager": "5.9.0", - "@typescript-eslint/types": "5.9.0", - "@typescript-eslint/typescript-estree": "5.9.0", - "debug": "^4.3.2" - }, - "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.9.0", - "resolved": "https://registry.npmjs.org/@typescript-eslint/scope-manager/-/scope-manager-5.9.0.tgz", - "integrity": "sha512-DKtdIL49Qxk2a8icF6whRk7uThuVz4A6TCXfjdJSwOsf+9ree7vgQWcx0KOyCdk0i9ETX666p4aMhrRhxhUkyg==", - "dev": true, - "dependencies": { - "@typescript-eslint/types": "5.9.0", - "@typescript-eslint/visitor-keys": "5.9.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.9.0", - "resolved": "https://registry.npmjs.org/@typescript-eslint/type-utils/-/type-utils-5.9.0.tgz", - "integrity": "sha512-uVCb9dJXpBrK1071ri5aEW7ZHdDHAiqEjYznF3HSSvAJXyrkxGOw2Ejibz/q6BXdT8lea8CMI0CzKNFTNI6TEQ==", - "dev": true, - "dependencies": { - "@typescript-eslint/experimental-utils": "5.9.0", - "debug": "^4.3.2", - "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.9.0", - "resolved": "https://registry.npmjs.org/@typescript-eslint/types/-/types-5.9.0.tgz", - "integrity": "sha512-mWp6/b56Umo1rwyGCk8fPIzb9Migo8YOniBGPAQDNC6C52SeyNGN4gsVwQTAR+RS2L5xyajON4hOLwAGwPtUwg==", - "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.9.0", - "resolved": "https://registry.npmjs.org/@typescript-eslint/typescript-estree/-/typescript-estree-5.9.0.tgz", - "integrity": "sha512-kxo3xL2mB7XmiVZcECbaDwYCt3qFXz99tBSuVJR4L/sR7CJ+UNAPrYILILktGj1ppfZ/jNt/cWYbziJUlHl1Pw==", - "dev": true, - "dependencies": { - "@typescript-eslint/types": "5.9.0", - "@typescript-eslint/visitor-keys": "5.9.0", - "debug": "^4.3.2", - "globby": "^11.0.4", - "is-glob": "^4.0.3", - "semver": "^7.3.5", - "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/visitor-keys": { - "version": "5.9.0", - "resolved": "https://registry.npmjs.org/@typescript-eslint/visitor-keys/-/visitor-keys-5.9.0.tgz", - "integrity": "sha512-6zq0mb7LV0ThExKlecvpfepiB+XEtFv/bzx7/jKSgyXTFD7qjmSu1FoiS0x3OZaiS+UIXpH2vd9O89f02RCtgw==", - "dev": true, - "dependencies": { - "@typescript-eslint/types": "5.9.0", - "eslint-visitor-keys": "^3.0.0" - }, - "engines": { - "node": "^12.22.0 || ^14.17.0 || >=16.0.0" - }, - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/typescript-eslint" - } - }, - "node_modules/@ungap/promise-all-settled": { - "version": "1.1.2", - "resolved": "https://registry.npmjs.org/@ungap/promise-all-settled/-/promise-all-settled-1.1.2.tgz", - "integrity": "sha512-sL/cEvJWAnClXw0wHk85/2L0G6Sj8UB0Ctc1TEMbKSsmpRosqhwj9gWgFRZSrBr2f9tiXISwNhCPmlfqUqyb9Q==" - }, - "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==", - "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==" - }, - "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==" - }, - "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==" - }, - "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==", - "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==" - }, - "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==", - "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==", - "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==", - "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==" - }, - "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==", - "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==", - "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==", - "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==", - "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==", - "dependencies": { - "@webassemblyjs/ast": "1.11.1", - "@xtuc/long": "4.2.2" - } - }, - "node_modules/@webpack-cli/configtest": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/@webpack-cli/configtest/-/configtest-1.1.0.tgz", - "integrity": "sha512-ttOkEkoalEHa7RaFYpM0ErK1xc4twg3Am9hfHhL7MVqlHebnkYd2wuI/ZqTDj0cVzZho6PdinY0phFZV3O0Mzg==", - "peerDependencies": { - "webpack": "4.x.x || 5.x.x", - "webpack-cli": "4.x.x" - } - }, - "node_modules/@webpack-cli/info": { - "version": "1.4.0", - "resolved": "https://registry.npmjs.org/@webpack-cli/info/-/info-1.4.0.tgz", - "integrity": "sha512-F6b+Man0rwE4n0409FyAJHStYA5OIZERxmnUfLVwv0mc0V1wLad3V7jqRlMkgKBeAq07jUvglacNaa6g9lOpuw==", - "dependencies": { - "envinfo": "^7.7.3" - }, - "peerDependencies": { - "webpack-cli": "4.x.x" - } - }, - "node_modules/@webpack-cli/serve": { - "version": "1.6.0", - "resolved": "https://registry.npmjs.org/@webpack-cli/serve/-/serve-1.6.0.tgz", - "integrity": "sha512-ZkVeqEmRpBV2GHvjjUZqEai2PpUbuq8Bqd//vEYsp63J8WyexI8ppCqVS3Zs0QADf6aWuPdU+0XsPI647PVlQA==", - "peerDependencies": { - "webpack-cli": "4.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==" - }, - "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==" - }, - "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==", - "dev": true - }, - "node_modules/accepts": { - "version": "1.3.7", - "resolved": "https://registry.npmjs.org/accepts/-/accepts-1.3.7.tgz", - "integrity": "sha512-Il80Qs2WjYlJIBNzNkK6KYqlVMTbZLXgHx2oT0pU/fjRHyEp+PEfEPY0R3WCwAGVOtauxh1hOxNgIf5bv7dQpA==", - "dependencies": { - "mime-types": "~2.1.24", - "negotiator": "0.6.2" - }, - "engines": { - "node": ">= 0.6" - } - }, - "node_modules/acorn": { - "version": "8.7.0", - "resolved": "https://registry.npmjs.org/acorn/-/acorn-8.7.0.tgz", - "integrity": "sha512-V/LGr1APy+PXIwKebEWrkZPwoeoF+w1jiOBUmuxuiUIaOHtob8Qc9BTrYo7VuI5fR8tqsy+buA2WFooR5olqvQ==", - "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==", - "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==", - "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==", - "engines": { - "node": ">=0.4.0" - } - }, - "node_modules/add-stream": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/add-stream/-/add-stream-1.0.0.tgz", - "integrity": "sha1-anmQQ3ynNtXhKI25K9MmbV9csqo=", - "dev": true - }, - "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==", - "dev": true, - "dependencies": { - "debug": "4" - }, - "engines": { - "node": ">= 6.0.0" - } - }, - "node_modules/agentkeepalive": { - "version": "4.2.0", - "resolved": "https://registry.npmjs.org/agentkeepalive/-/agentkeepalive-4.2.0.tgz", - "integrity": "sha512-0PhAp58jZNw13UJv7NVdTGb0ZcghHUb3DrZ046JiiJY/BOaTTpbwdHq2VObPCBV8M2GPh7sgrJ3AQ8Ey468LJw==", - "dev": true, - "dependencies": { - "debug": "^4.1.0", - "depd": "^1.1.2", - "humanize-ms": "^1.2.1" - }, - "engines": { - "node": ">= 8.0.0" - } - }, - "node_modules/aggregate-error": { - "version": "3.1.0", - "resolved": "https://registry.npmjs.org/aggregate-error/-/aggregate-error-3.1.0.tgz", - "integrity": "sha512-4I7Td01quW/RpocfNayFdFVk1qSuoh0E7JrbRJ16nH01HhKFQ88INq9Sd+nd72zqRySlr9BmDA8xlEJ6vJMrYA==", - "dev": true, - "dependencies": { - "clean-stack": "^2.0.0", - "indent-string": "^4.0.0" - }, - "engines": { - "node": ">=8" - } - }, - "node_modules/ajv": { - "version": "8.8.2", - "resolved": "https://registry.npmjs.org/ajv/-/ajv-8.8.2.tgz", - "integrity": "sha512-x9VuX+R/jcFj1DHo/fCp99esgGDWiHENrKxaCENuCxpoMCmAt/COCGVDwA7kleEpEzJjDnvh3yGoOuLu0Dtllw==", - "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==", - "dependencies": { - "ajv": "^8.0.0" - }, - "peerDependencies": { - "ajv": "^8.0.0" - }, - "peerDependenciesMeta": { - "ajv": { - "optional": true - } - } - }, - "node_modules/align-text": { - "version": "0.1.4", - "resolved": "https://registry.npmjs.org/align-text/-/align-text-0.1.4.tgz", - "integrity": "sha1-DNkKVhCT810KmSVsIrcGlDP60Rc=", - "dependencies": { - "kind-of": "^3.0.2", - "longest": "^1.0.1", - "repeat-string": "^1.5.2" - }, - "engines": { - "node": ">=0.10.0" - } - }, - "node_modules/align-text/node_modules/kind-of": { - "version": "3.2.2", - "resolved": "https://registry.npmjs.org/kind-of/-/kind-of-3.2.2.tgz", - "integrity": "sha1-MeohpzS6ubuw8yRm2JOupR5KPGQ=", - "dependencies": { - "is-buffer": "^1.1.5" - }, - "engines": { - "node": ">=0.10.0" - } - }, - "node_modules/ansi-align": { - "version": "3.0.1", - "resolved": "https://registry.npmjs.org/ansi-align/-/ansi-align-3.0.1.tgz", - "integrity": "sha512-IOfwwBF5iczOjp/WeY4YxyjqAFMQoZufdQWDd19SEExbVLNXqvpzSJ/M7Za4/sCPmQ0+GRquoA7bGcINcxew6w==", - "dev": true, - "dependencies": { - "string-width": "^4.1.0" - } - }, - "node_modules/ansi-colors": { - "version": "4.1.1", - "resolved": "https://registry.npmjs.org/ansi-colors/-/ansi-colors-4.1.1.tgz", - "integrity": "sha512-JoX0apGbHaUJBNl6yF+p6JAFYZ666/hhCGKN5t9QFjbJQKUU/g8MNbFDbvfrgKXvI1QpZplPOnwIo99lX/AAmA==", - "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==", - "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.2", - "resolved": "https://registry.npmjs.org/anymatch/-/anymatch-3.1.2.tgz", - "integrity": "sha512-P43ePfOAIupkguHUycrc4qJ9kz8ZiuOUijaETwX7THt0Y/GNK7v0aa8rY816xWjZ7rJdA5XdMcpVFTKMq+RvWg==", - "dependencies": { - "normalize-path": "^3.0.0", - "picomatch": "^2.0.4" - }, - "engines": { - "node": ">= 8" - } - }, - "node_modules/app-module-path": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/app-module-path/-/app-module-path-1.1.0.tgz", - "integrity": "sha1-pqxTaEUPIJufW4bpo+Smq2/nUxw=" - }, - "node_modules/app-root-dir": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/app-root-dir/-/app-root-dir-1.0.2.tgz", - "integrity": "sha1-OBh+wt6nV3//Az/8sSFyaS/24Rg=" - }, - "node_modules/append-transform": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/append-transform/-/append-transform-2.0.0.tgz", - "integrity": "sha512-7yeyCEurROLQJFv5Xj4lEGTy0borxepjFv1g22oAdqFu//SrAlDl1O1Nxx15SH1RoliUml6p8dwJW9jvZughhg==", - "dev": true, - "dependencies": { - "default-require-extensions": "^3.0.0" - }, - "engines": { - "node": ">=8" - } - }, - "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==", - "dev": true - }, - "node_modules/archy": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/archy/-/archy-1.0.0.tgz", - "integrity": "sha1-+cjBN1fMHde8N5rHeyxipcKGjEA=", - "dev": true - }, - "node_modules/are-we-there-yet": { - "version": "1.1.7", - "resolved": "https://registry.npmjs.org/are-we-there-yet/-/are-we-there-yet-1.1.7.tgz", - "integrity": "sha512-nxwy40TuMiUGqMyRHgCSWZ9FM4VAoRP4xUYSTv5ImRog+h9yISPbVH7H8fASCIzYn9wlEv4zvFL7uKDMCFQm3g==", - "dev": true, - "dependencies": { - "delegates": "^1.0.0", - "readable-stream": "^2.0.6" - } - }, - "node_modules/are-we-there-yet/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/are-we-there-yet/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/arg": { - "version": "4.1.3", - "resolved": "https://registry.npmjs.org/arg/-/arg-4.1.3.tgz", - "integrity": "sha512-58S9QDqG0Xx27YwPSt9fJxivjYl432YCwfDMfZ+71RAqUrZef7LrKQZ3LHLOwCS4FLNBplP533Zx895SeOCHvA==" - }, - "node_modules/argly": { - "version": "1.2.0", - "resolved": "https://registry.npmjs.org/argly/-/argly-1.2.0.tgz", - "integrity": "sha1-KydORVGin/XnGZ0u2XiOtm7TbmA=" - }, - "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==" - }, - "node_modules/arr-diff": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/arr-diff/-/arr-diff-2.0.0.tgz", - "integrity": "sha1-jzuCf5Vai9ZpaX5KQlasPOrjVs8=", - "dependencies": { - "arr-flatten": "^1.0.1" - }, - "engines": { - "node": ">=0.10.0" - } - }, - "node_modules/arr-flatten": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/arr-flatten/-/arr-flatten-1.1.0.tgz", - "integrity": "sha512-L3hKV5R/p5o81R7O02IGnwpDmkp6E982XhtbuwSe3O4qOtMMMtodicASA1Cny2U+aCXcNpml+m4dPsvsJ3jatg==", - "engines": { - "node": ">=0.10.0" - } - }, - "node_modules/array-differ": { - "version": "3.0.0", - "resolved": "https://registry.npmjs.org/array-differ/-/array-differ-3.0.0.tgz", - "integrity": "sha512-THtfYS6KtME/yIAhKjZ2ul7XI96lQGHRputJQHO80LAWQnuGP4iCIN8vdMRboGbIEYBwU33q8Tch1os2+X0kMg==", - "dev": true, - "engines": { - "node": ">=8" - } - }, - "node_modules/array-flatten": { - "version": "1.1.1", - "resolved": "https://registry.npmjs.org/array-flatten/-/array-flatten-1.1.1.tgz", - "integrity": "sha1-ml9pkFGx5wczKPKgCJaLZOopVdI=" - }, - "node_modules/array-ify": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/array-ify/-/array-ify-1.0.0.tgz", - "integrity": "sha1-nlKHYrSpBmrRY6aWKjZEGOlibs4=", - "dev": true - }, - "node_modules/array-includes": { - "version": "3.1.4", - "resolved": "https://registry.npmjs.org/array-includes/-/array-includes-3.1.4.tgz", - "integrity": "sha512-ZTNSQkmWumEbiHO2GF4GmWxYVTiQyJy2XOTa15sdQSrvKn7l+180egQMqlrMOUMCyLMD7pmyQe4mMDUT6Behrw==", - "dev": true, - "dependencies": { - "call-bind": "^1.0.2", - "define-properties": "^1.1.3", - "es-abstract": "^1.19.1", - "get-intrinsic": "^1.1.1", - "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-unique": { - "version": "0.2.1", - "resolved": "https://registry.npmjs.org/array-unique/-/array-unique-0.2.1.tgz", - "integrity": "sha1-odl8yvy8JiXMcPrc6zalDFiwGlM=", - "engines": { - "node": ">=0.10.0" - } - }, - "node_modules/array.prototype.flat": { - "version": "1.2.5", - "resolved": "https://registry.npmjs.org/array.prototype.flat/-/array.prototype.flat-1.2.5.tgz", - "integrity": "sha512-KaYU+S+ndVqyUnignHftkwc58o3uVU1jzczILJ1tN2YaIZpFIKBiP/x/j97E5MVPsaCloPbqWLB/8qCTVvT2qg==", - "dev": true, - "dependencies": { - "call-bind": "^1.0.2", - "define-properties": "^1.1.3", - "es-abstract": "^1.19.0" - }, - "engines": { - "node": ">= 0.4" - }, - "funding": { - "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": "sha1-iYUI2iIm84DfkEcoRWhJwVAaSw0=", - "engines": { - "node": ">=0.10.0" - } - }, - "node_modules/asap": { - "version": "2.0.6", - "resolved": "https://registry.npmjs.org/asap/-/asap-2.0.6.tgz", - "integrity": "sha1-5QNHYR1+aQlDIIu9r+vLwvuGbUY=", - "dev": true - }, - "node_modules/asn1": { - "version": "0.2.6", - "resolved": "https://registry.npmjs.org/asn1/-/asn1-0.2.6.tgz", - "integrity": "sha512-ix/FxPn0MDjeyJ7i/yoHGFt/EX6LyNbxSEhPPXODPL+KB0VPk86UYfL0lMdy+KCnv+fmvIzySwaK5COwqVbWTQ==", - "dev": true, - "dependencies": { - "safer-buffer": "~2.1.0" - } - }, - "node_modules/asn1.js": { - "version": "5.4.1", - "resolved": "https://registry.npmjs.org/asn1.js/-/asn1.js-5.4.1.tgz", - "integrity": "sha512-+I//4cYPccV8LdmBLiX8CYvf9Sp3vQsrqu2QNXRcrbiWvcx/UdlFiqUJJzxRQxgsZmvhXhn4cSKeSmoFjVdupA==", - "optional": true, - "dependencies": { - "bn.js": "^4.0.0", - "inherits": "^2.0.1", - "minimalistic-assert": "^1.0.0", - "safer-buffer": "^2.1.0" - } - }, - "node_modules/assert": { - "version": "1.5.0", - "resolved": "https://registry.npmjs.org/assert/-/assert-1.5.0.tgz", - "integrity": "sha512-EDsgawzwoun2CZkCgtxJbv392v4nbk9XDD06zI+kQYoBM/3RBWLlEyJARDOmhAAosBjWACEkKL6S+lIZtcAubA==", - "dependencies": { - "object-assign": "^4.1.1", - "util": "0.10.3" - } - }, - "node_modules/assert-plus": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/assert-plus/-/assert-plus-1.0.0.tgz", - "integrity": "sha1-8S4PPF13sLHN2RRpQuTpbB5N1SU=", - "dev": true, - "engines": { - "node": ">=0.8" - } - }, - "node_modules/assert/node_modules/inherits": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/inherits/-/inherits-2.0.1.tgz", - "integrity": "sha1-sX0I0ya0Qj5Wjv9xn5GwscvfafE=" - }, - "node_modules/assert/node_modules/util": { - "version": "0.10.3", - "resolved": "https://registry.npmjs.org/util/-/util-0.10.3.tgz", - "integrity": "sha1-evsa/lCAUkZInj23/g7TeTNqwPk=", - "dependencies": { - "inherits": "2.0.1" - } - }, - "node_modules/assertion-error": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/assertion-error/-/assertion-error-1.1.0.tgz", - "integrity": "sha512-jgsaNduz+ndvGyFt3uSuWqvy4lCnIJiovtouQN5JZHOKCS2QuhEdbcQHFhVksz2N2U9hXJo8odG7ETyWlEeuDw==", - "engines": { - "node": "*" - } - }, - "node_modules/async": { - "version": "3.2.2", - "resolved": "https://registry.npmjs.org/async/-/async-3.2.2.tgz", - "integrity": "sha512-H0E+qZaDEfx/FY4t7iLRv1W2fFI6+pyCeTw1uN20AQPiwqwM6ojPxHxdLv4z8hi2DtnW9BOckSspLucW7pIE5g==" - }, - "node_modules/async-limiter": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/async-limiter/-/async-limiter-1.0.1.tgz", - "integrity": "sha512-csOlWGAcRFJaI6m+F2WKdnMKr4HhdhFVBk0H/QbJFMCr+uO2kwohwXQPxw/9OCxp05r5ghVBFSyioixx3gfkNQ==" - }, - "node_modules/asynckit": { - "version": "0.4.0", - "resolved": "https://registry.npmjs.org/asynckit/-/asynckit-0.4.0.tgz", - "integrity": "sha1-x57Zf380y48robyXkLzDZkdLS3k=" - }, - "node_modules/at-least-node": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/at-least-node/-/at-least-node-1.0.0.tgz", - "integrity": "sha512-+q/t7Ekv1EDY2l6Gda6LLiX14rU9TV20Wa3ofeQmwPFZbOMo9DXrLbOjFaaclkXKWidIaopwAObQDqwWtGUjqg==", - "dev": true, - "engines": { - "node": ">= 4.0.0" - } - }, - "node_modules/aws-sign2": { - "version": "0.7.0", - "resolved": "https://registry.npmjs.org/aws-sign2/-/aws-sign2-0.7.0.tgz", - "integrity": "sha1-tG6JCTSpWR8tL2+G1+ap8bP+dqg=", - "dev": true, - "engines": { - "node": "*" - } - }, - "node_modules/aws4": { - "version": "1.11.0", - "resolved": "https://registry.npmjs.org/aws4/-/aws4-1.11.0.tgz", - "integrity": "sha512-xh1Rl34h6Fi1DC2WWKfxUTVqRsNnr6LsKz2+hfwDxQJWmrx8+c7ylaqBMcHfl1U1r2dsifOvKX3LQuLNZ+XSvA==", - "dev": true - }, - "node_modules/axios": { - "version": "0.24.0", - "resolved": "https://registry.npmjs.org/axios/-/axios-0.24.0.tgz", - "integrity": "sha512-Q6cWsys88HoPgAaFAVUb0WpPk0O8iTeisR9IMqy9G8AbO4NlpVknrnQS03zzF9PGAWgO3cgletO3VjV/P7VztA==", - "dependencies": { - "follow-redirects": "^1.14.4" - } - }, - "node_modules/babel-code-frame": { - "version": "6.26.0", - "resolved": "https://registry.npmjs.org/babel-code-frame/-/babel-code-frame-6.26.0.tgz", - "integrity": "sha1-Y/1D99weO7fONZR9uP42mj9Yx0s=", - "dependencies": { - "chalk": "^1.1.3", - "esutils": "^2.0.2", - "js-tokens": "^3.0.2" - } - }, - "node_modules/babel-code-frame/node_modules/ansi-regex": { - "version": "2.1.1", - "resolved": "https://registry.npmjs.org/ansi-regex/-/ansi-regex-2.1.1.tgz", - "integrity": "sha1-w7M6te42DYbg5ijwRorn7yfWVN8=", - "engines": { - "node": ">=0.10.0" - } - }, - "node_modules/babel-code-frame/node_modules/ansi-styles": { - "version": "2.2.1", - "resolved": "https://registry.npmjs.org/ansi-styles/-/ansi-styles-2.2.1.tgz", - "integrity": "sha1-tDLdM1i2NM914eRmQ2gkBTPB3b4=", - "engines": { - "node": ">=0.10.0" - } - }, - "node_modules/babel-code-frame/node_modules/chalk": { - "version": "1.1.3", - "resolved": "https://registry.npmjs.org/chalk/-/chalk-1.1.3.tgz", - "integrity": "sha1-qBFcVeSnAv5NFQq9OHKCKn4J/Jg=", - "dependencies": { - "ansi-styles": "^2.2.1", - "escape-string-regexp": "^1.0.2", - "has-ansi": "^2.0.0", - "strip-ansi": "^3.0.0", - "supports-color": "^2.0.0" - }, - "engines": { - "node": ">=0.10.0" - } - }, - "node_modules/babel-code-frame/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": "sha1-G2HAViGQqN/2rjuyzwIAyhMLhtQ=", - "engines": { - "node": ">=0.8.0" - } - }, - "node_modules/babel-code-frame/node_modules/js-tokens": { - "version": "3.0.2", - "resolved": "https://registry.npmjs.org/js-tokens/-/js-tokens-3.0.2.tgz", - "integrity": "sha1-mGbfOVECEw449/mWvOtlRDIJwls=" - }, - "node_modules/babel-code-frame/node_modules/strip-ansi": { - "version": "3.0.1", - "resolved": "https://registry.npmjs.org/strip-ansi/-/strip-ansi-3.0.1.tgz", - "integrity": "sha1-ajhfuIU9lS1f8F0Oiq+UJ43GPc8=", - "dependencies": { - "ansi-regex": "^2.0.0" - }, - "engines": { - "node": ">=0.10.0" - } - }, - "node_modules/babel-code-frame/node_modules/supports-color": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/supports-color/-/supports-color-2.0.0.tgz", - "integrity": "sha1-U10EXOa2Nj+kARcIRimZXp3zJMc=", - "engines": { - "node": ">=0.8.0" - } - }, - "node_modules/babel-core": { - "version": "6.26.3", - "resolved": "https://registry.npmjs.org/babel-core/-/babel-core-6.26.3.tgz", - "integrity": "sha512-6jyFLuDmeidKmUEb3NM+/yawG0M2bDZ9Z1qbZP59cyHLz8kYGKYwpJP0UwUKKUiTRNvxfLesJnTedqczP7cTDA==", - "dependencies": { - "babel-code-frame": "^6.26.0", - "babel-generator": "^6.26.0", - "babel-helpers": "^6.24.1", - "babel-messages": "^6.23.0", - "babel-register": "^6.26.0", - "babel-runtime": "^6.26.0", - "babel-template": "^6.26.0", - "babel-traverse": "^6.26.0", - "babel-types": "^6.26.0", - "babylon": "^6.18.0", - "convert-source-map": "^1.5.1", - "debug": "^2.6.9", - "json5": "^0.5.1", - "lodash": "^4.17.4", - "minimatch": "^3.0.4", - "path-is-absolute": "^1.0.1", - "private": "^0.1.8", - "slash": "^1.0.0", - "source-map": "^0.5.7" - } - }, - "node_modules/babel-core/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/babel-core/node_modules/json5": { - "version": "0.5.1", - "resolved": "https://registry.npmjs.org/json5/-/json5-0.5.1.tgz", - "integrity": "sha1-Hq3nrMASA0rYTiOWdn6tn6VJWCE=", - "bin": { - "json5": "lib/cli.js" - } - }, - "node_modules/babel-core/node_modules/ms": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/ms/-/ms-2.0.0.tgz", - "integrity": "sha1-VgiurfwAvmwpAd9fmGF4jeDVl8g=" - }, - "node_modules/babel-core/node_modules/slash": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/slash/-/slash-1.0.0.tgz", - "integrity": "sha1-xB8vbDn8FtHNF61LXYlhFK5HDVU=", - "engines": { - "node": ">=0.10.0" - } - }, - "node_modules/babel-core/node_modules/source-map": { - "version": "0.5.7", - "resolved": "https://registry.npmjs.org/source-map/-/source-map-0.5.7.tgz", - "integrity": "sha1-igOdLRAh0i0eoUyA2OpGi6LvP8w=", - "engines": { - "node": ">=0.10.0" - } - }, - "node_modules/babel-generator": { - "version": "6.26.1", - "resolved": "https://registry.npmjs.org/babel-generator/-/babel-generator-6.26.1.tgz", - "integrity": "sha512-HyfwY6ApZj7BYTcJURpM5tznulaBvyio7/0d4zFOeMPUmfxkCjHocCuoLa2SAGzBI8AREcH3eP3758F672DppA==", - "dependencies": { - "babel-messages": "^6.23.0", - "babel-runtime": "^6.26.0", - "babel-types": "^6.26.0", - "detect-indent": "^4.0.0", - "jsesc": "^1.3.0", - "lodash": "^4.17.4", - "source-map": "^0.5.7", - "trim-right": "^1.0.1" - } - }, - "node_modules/babel-generator/node_modules/detect-indent": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/detect-indent/-/detect-indent-4.0.0.tgz", - "integrity": "sha1-920GQ1LN9Docts5hnE7jqUdd4gg=", - "dependencies": { - "repeating": "^2.0.0" - }, - "engines": { - "node": ">=0.10.0" - } - }, - "node_modules/babel-generator/node_modules/jsesc": { - "version": "1.3.0", - "resolved": "https://registry.npmjs.org/jsesc/-/jsesc-1.3.0.tgz", - "integrity": "sha1-RsP+yMGJKxKwgz25vHYiF226s0s=", - "bin": { - "jsesc": "bin/jsesc" - } - }, - "node_modules/babel-generator/node_modules/source-map": { - "version": "0.5.7", - "resolved": "https://registry.npmjs.org/source-map/-/source-map-0.5.7.tgz", - "integrity": "sha1-igOdLRAh0i0eoUyA2OpGi6LvP8w=", - "engines": { - "node": ">=0.10.0" - } - }, - "node_modules/babel-helper-builder-binary-assignment-operator-visitor": { - "version": "6.24.1", - "resolved": "https://registry.npmjs.org/babel-helper-builder-binary-assignment-operator-visitor/-/babel-helper-builder-binary-assignment-operator-visitor-6.24.1.tgz", - "integrity": "sha1-zORReto1b0IgvK6KAsKzRvmlZmQ=", - "dependencies": { - "babel-helper-explode-assignable-expression": "^6.24.1", - "babel-runtime": "^6.22.0", - "babel-types": "^6.24.1" - } - }, - "node_modules/babel-helper-call-delegate": { - "version": "6.24.1", - "resolved": "https://registry.npmjs.org/babel-helper-call-delegate/-/babel-helper-call-delegate-6.24.1.tgz", - "integrity": "sha1-7Oaqzdx25Bw0YfiL/Fdb0Nqi340=", - "dependencies": { - "babel-helper-hoist-variables": "^6.24.1", - "babel-runtime": "^6.22.0", - "babel-traverse": "^6.24.1", - "babel-types": "^6.24.1" - } - }, - "node_modules/babel-helper-define-map": { - "version": "6.26.0", - "resolved": "https://registry.npmjs.org/babel-helper-define-map/-/babel-helper-define-map-6.26.0.tgz", - "integrity": "sha1-pfVtq0GiX5fstJjH66ypgZ+Vvl8=", - "dependencies": { - "babel-helper-function-name": "^6.24.1", - "babel-runtime": "^6.26.0", - "babel-types": "^6.26.0", - "lodash": "^4.17.4" - } - }, - "node_modules/babel-helper-explode-assignable-expression": { - "version": "6.24.1", - "resolved": "https://registry.npmjs.org/babel-helper-explode-assignable-expression/-/babel-helper-explode-assignable-expression-6.24.1.tgz", - "integrity": "sha1-8luCz33BBDPFX3BZLVdGQArCLKo=", - "dependencies": { - "babel-runtime": "^6.22.0", - "babel-traverse": "^6.24.1", - "babel-types": "^6.24.1" - } - }, - "node_modules/babel-helper-function-name": { - "version": "6.24.1", - "resolved": "https://registry.npmjs.org/babel-helper-function-name/-/babel-helper-function-name-6.24.1.tgz", - "integrity": "sha1-00dbjAPtmCQqJbSDUasYOZ01gKk=", - "dependencies": { - "babel-helper-get-function-arity": "^6.24.1", - "babel-runtime": "^6.22.0", - "babel-template": "^6.24.1", - "babel-traverse": "^6.24.1", - "babel-types": "^6.24.1" - } - }, - "node_modules/babel-helper-get-function-arity": { - "version": "6.24.1", - "resolved": "https://registry.npmjs.org/babel-helper-get-function-arity/-/babel-helper-get-function-arity-6.24.1.tgz", - "integrity": "sha1-j3eCqpNAfEHTqlCQj4mwMbG2hT0=", - "dependencies": { - "babel-runtime": "^6.22.0", - "babel-types": "^6.24.1" - } - }, - "node_modules/babel-helper-hoist-variables": { - "version": "6.24.1", - "resolved": "https://registry.npmjs.org/babel-helper-hoist-variables/-/babel-helper-hoist-variables-6.24.1.tgz", - "integrity": "sha1-HssnaJydJVE+rbyZFKc/VAi+enY=", - "dependencies": { - "babel-runtime": "^6.22.0", - "babel-types": "^6.24.1" - } - }, - "node_modules/babel-helper-optimise-call-expression": { - "version": "6.24.1", - "resolved": "https://registry.npmjs.org/babel-helper-optimise-call-expression/-/babel-helper-optimise-call-expression-6.24.1.tgz", - "integrity": "sha1-96E0J7qfc/j0+pk8VKl4gtEkQlc=", - "dependencies": { - "babel-runtime": "^6.22.0", - "babel-types": "^6.24.1" - } - }, - "node_modules/babel-helper-regex": { - "version": "6.26.0", - "resolved": "https://registry.npmjs.org/babel-helper-regex/-/babel-helper-regex-6.26.0.tgz", - "integrity": "sha1-MlxZ+QL4LyS3T6zu0DY5VPZJXnI=", - "dependencies": { - "babel-runtime": "^6.26.0", - "babel-types": "^6.26.0", - "lodash": "^4.17.4" - } - }, - "node_modules/babel-helper-remap-async-to-generator": { - "version": "6.24.1", - "resolved": "https://registry.npmjs.org/babel-helper-remap-async-to-generator/-/babel-helper-remap-async-to-generator-6.24.1.tgz", - "integrity": "sha1-XsWBgnrXI/7N04HxySg5BnbkVRs=", - "dependencies": { - "babel-helper-function-name": "^6.24.1", - "babel-runtime": "^6.22.0", - "babel-template": "^6.24.1", - "babel-traverse": "^6.24.1", - "babel-types": "^6.24.1" - } - }, - "node_modules/babel-helper-replace-supers": { - "version": "6.24.1", - "resolved": "https://registry.npmjs.org/babel-helper-replace-supers/-/babel-helper-replace-supers-6.24.1.tgz", - "integrity": "sha1-v22/5Dk40XNpohPKiov3S2qQqxo=", - "dependencies": { - "babel-helper-optimise-call-expression": "^6.24.1", - "babel-messages": "^6.23.0", - "babel-runtime": "^6.22.0", - "babel-template": "^6.24.1", - "babel-traverse": "^6.24.1", - "babel-types": "^6.24.1" - } - }, - "node_modules/babel-helpers": { - "version": "6.24.1", - "resolved": "https://registry.npmjs.org/babel-helpers/-/babel-helpers-6.24.1.tgz", - "integrity": "sha1-NHHenK7DiOXIUOWX5Yom3fN2ArI=", - "dependencies": { - "babel-runtime": "^6.22.0", - "babel-template": "^6.24.1" - } - }, - "node_modules/babel-loader": { - "version": "8.2.3", - "resolved": "https://registry.npmjs.org/babel-loader/-/babel-loader-8.2.3.tgz", - "integrity": "sha512-n4Zeta8NC3QAsuyiizu0GkmRcQ6clkV9WFUnUf1iXP//IeSKbWjofW3UHyZVwlOB4y039YQKefawyTn64Zwbuw==", - "dependencies": { - "find-cache-dir": "^3.3.1", - "loader-utils": "^1.4.0", - "make-dir": "^3.1.0", - "schema-utils": "^2.6.5" - }, - "engines": { - "node": ">= 8.9" - }, - "peerDependencies": { - "@babel/core": "^7.0.0", - "webpack": ">=2" - } - }, - "node_modules/babel-messages": { - "version": "6.23.0", - "resolved": "https://registry.npmjs.org/babel-messages/-/babel-messages-6.23.0.tgz", - "integrity": "sha1-8830cDhYA1sqKVHG7F7fbGLyYw4=", - "dependencies": { - "babel-runtime": "^6.22.0" - } - }, - "node_modules/babel-plugin-check-es2015-constants": { - "version": "6.22.0", - "resolved": "https://registry.npmjs.org/babel-plugin-check-es2015-constants/-/babel-plugin-check-es2015-constants-6.22.0.tgz", - "integrity": "sha1-NRV7EBQm/S/9PaP3XH0ekYNbv4o=", - "dependencies": { - "babel-runtime": "^6.22.0" - } - }, - "node_modules/babel-plugin-dynamic-import-node": { - "version": "2.3.3", - "resolved": "https://registry.npmjs.org/babel-plugin-dynamic-import-node/-/babel-plugin-dynamic-import-node-2.3.3.tgz", - "integrity": "sha512-jZVI+s9Zg3IqA/kdi0i6UDCybUI3aSBLnglhYbSSjKlV7yF1F/5LWv8MakQmvYpnbJDS6fcBL2KzHSxNCMtWSQ==", - "dependencies": { - "object.assign": "^4.1.0" - } - }, - "node_modules/babel-plugin-istanbul": { - "version": "4.1.6", - "resolved": "https://registry.npmjs.org/babel-plugin-istanbul/-/babel-plugin-istanbul-4.1.6.tgz", - "integrity": "sha512-PWP9FQ1AhZhS01T/4qLSKoHGY/xvkZdVBGlKM/HuxxS3+sC66HhTNR7+MpbO/so/cz/wY94MeSWJuP1hXIPfwQ==", - "dependencies": { - "babel-plugin-syntax-object-rest-spread": "^6.13.0", - "find-up": "^2.1.0", - "istanbul-lib-instrument": "^1.10.1", - "test-exclude": "^4.2.1" - } - }, - "node_modules/babel-plugin-istanbul/node_modules/braces": { - "version": "1.8.5", - "resolved": "https://registry.npmjs.org/braces/-/braces-1.8.5.tgz", - "integrity": "sha1-uneWLhLf+WnWt2cR6RS3N4V79qc=", - "dependencies": { - "expand-range": "^1.8.1", - "preserve": "^0.2.0", - "repeat-element": "^1.1.2" - }, - "engines": { - "node": ">=0.10.0" - } - }, - "node_modules/babel-plugin-istanbul/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==" - }, - "node_modules/babel-plugin-istanbul/node_modules/is-extglob": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/is-extglob/-/is-extglob-1.0.0.tgz", - "integrity": "sha1-rEaBd8SUNAWgkvyPKXYMb/xiBsA=", - "engines": { - "node": ">=0.10.0" - } - }, - "node_modules/babel-plugin-istanbul/node_modules/is-glob": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/is-glob/-/is-glob-2.0.1.tgz", - "integrity": "sha1-0Jb5JqPe1WAPP9/ZEZjLCIjC2GM=", - "dependencies": { - "is-extglob": "^1.0.0" - }, - "engines": { - "node": ">=0.10.0" - } - }, - "node_modules/babel-plugin-istanbul/node_modules/istanbul-lib-coverage": { - "version": "1.2.1", - "resolved": "https://registry.npmjs.org/istanbul-lib-coverage/-/istanbul-lib-coverage-1.2.1.tgz", - "integrity": "sha512-PzITeunAgyGbtY1ibVIUiV679EFChHjoMNRibEIobvmrCRaIgwLxNucOSimtNWUhEib/oO7QY2imD75JVgCJWQ==" - }, - "node_modules/babel-plugin-istanbul/node_modules/istanbul-lib-instrument": { - "version": "1.10.2", - "resolved": "https://registry.npmjs.org/istanbul-lib-instrument/-/istanbul-lib-instrument-1.10.2.tgz", - "integrity": "sha512-aWHxfxDqvh/ZlxR8BBaEPVSWDPUkGD63VjGQn3jcw8jCp7sHEMKcrj4xfJn/ABzdMEHiQNyvDQhqm5o8+SQg7A==", - "dependencies": { - "babel-generator": "^6.18.0", - "babel-template": "^6.16.0", - "babel-traverse": "^6.18.0", - "babel-types": "^6.18.0", - "babylon": "^6.18.0", - "istanbul-lib-coverage": "^1.2.1", - "semver": "^5.3.0" - } - }, - "node_modules/babel-plugin-istanbul/node_modules/kind-of": { - "version": "3.2.2", - "resolved": "https://registry.npmjs.org/kind-of/-/kind-of-3.2.2.tgz", - "integrity": "sha1-MeohpzS6ubuw8yRm2JOupR5KPGQ=", - "dependencies": { - "is-buffer": "^1.1.5" - }, - "engines": { - "node": ">=0.10.0" - } - }, - "node_modules/babel-plugin-istanbul/node_modules/load-json-file": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/load-json-file/-/load-json-file-1.1.0.tgz", - "integrity": "sha1-lWkFcI1YtLq0wiYbBPWfMcmTdMA=", - "dependencies": { - "graceful-fs": "^4.1.2", - "parse-json": "^2.2.0", - "pify": "^2.0.0", - "pinkie-promise": "^2.0.0", - "strip-bom": "^2.0.0" - }, - "engines": { - "node": ">=0.10.0" - } - }, - "node_modules/babel-plugin-istanbul/node_modules/micromatch": { - "version": "2.3.11", - "resolved": "https://registry.npmjs.org/micromatch/-/micromatch-2.3.11.tgz", - "integrity": "sha1-hmd8l9FyCzY0MdBNDRUpO9OMFWU=", - "dependencies": { - "arr-diff": "^2.0.0", - "array-unique": "^0.2.1", - "braces": "^1.8.2", - "expand-brackets": "^0.1.4", - "extglob": "^0.3.1", - "filename-regex": "^2.0.0", - "is-extglob": "^1.0.0", - "is-glob": "^2.0.1", - "kind-of": "^3.0.2", - "normalize-path": "^2.0.1", - "object.omit": "^2.0.0", - "parse-glob": "^3.0.4", - "regex-cache": "^0.4.2" - }, - "engines": { - "node": ">=0.10.0" - } - }, - "node_modules/babel-plugin-istanbul/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==", - "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/babel-plugin-istanbul/node_modules/normalize-path": { - "version": "2.1.1", - "resolved": "https://registry.npmjs.org/normalize-path/-/normalize-path-2.1.1.tgz", - "integrity": "sha1-GrKLVW4Zg2Oowab35vogE3/mrtk=", - "dependencies": { - "remove-trailing-separator": "^1.0.1" - }, - "engines": { - "node": ">=0.10.0" - } - }, - "node_modules/babel-plugin-istanbul/node_modules/parse-json": { - "version": "2.2.0", - "resolved": "https://registry.npmjs.org/parse-json/-/parse-json-2.2.0.tgz", - "integrity": "sha1-9ID0BDTvgHQfhGkJn43qGPVaTck=", - "dependencies": { - "error-ex": "^1.2.0" - }, - "engines": { - "node": ">=0.10.0" - } - }, - "node_modules/babel-plugin-istanbul/node_modules/path-exists": { - "version": "2.1.0", - "resolved": "https://registry.npmjs.org/path-exists/-/path-exists-2.1.0.tgz", - "integrity": "sha1-D+tsZPD8UY2adU3V77YscCJ2H0s=", - "dependencies": { - "pinkie-promise": "^2.0.0" - }, - "engines": { - "node": ">=0.10.0" - } - }, - "node_modules/babel-plugin-istanbul/node_modules/path-type": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/path-type/-/path-type-1.1.0.tgz", - "integrity": "sha1-WcRPfuSR2nBNpBXaWkBwuk+P5EE=", - "dependencies": { - "graceful-fs": "^4.1.2", - "pify": "^2.0.0", - "pinkie-promise": "^2.0.0" - }, - "engines": { - "node": ">=0.10.0" - } - }, - "node_modules/babel-plugin-istanbul/node_modules/pify": { - "version": "2.3.0", - "resolved": "https://registry.npmjs.org/pify/-/pify-2.3.0.tgz", - "integrity": "sha1-7RQaasBDqEnqWISY59yosVMw6Qw=", - "engines": { - "node": ">=0.10.0" - } - }, - "node_modules/babel-plugin-istanbul/node_modules/read-pkg": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/read-pkg/-/read-pkg-1.1.0.tgz", - "integrity": "sha1-9f+qXs0pyzHAR0vKfXVra7KePyg=", - "dependencies": { - "load-json-file": "^1.0.0", - "normalize-package-data": "^2.3.2", - "path-type": "^1.0.0" - }, - "engines": { - "node": ">=0.10.0" - } - }, - "node_modules/babel-plugin-istanbul/node_modules/read-pkg-up": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/read-pkg-up/-/read-pkg-up-1.0.1.tgz", - "integrity": "sha1-nWPBMnbAZZGNV/ACpX9AobZD+wI=", - "dependencies": { - "find-up": "^1.0.0", - "read-pkg": "^1.0.0" - }, - "engines": { - "node": ">=0.10.0" - } - }, - "node_modules/babel-plugin-istanbul/node_modules/read-pkg-up/node_modules/find-up": { - "version": "1.1.2", - "resolved": "https://registry.npmjs.org/find-up/-/find-up-1.1.2.tgz", - "integrity": "sha1-ay6YIrGizgpgq2TWEOzK1TyyTQ8=", - "dependencies": { - "path-exists": "^2.0.0", - "pinkie-promise": "^2.0.0" - }, - "engines": { - "node": ">=0.10.0" - } - }, - "node_modules/babel-plugin-istanbul/node_modules/require-main-filename": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/require-main-filename/-/require-main-filename-1.0.1.tgz", - "integrity": "sha1-l/cXtp1IeE9fUmpsWqj/3aBVpNE=" - }, - "node_modules/babel-plugin-istanbul/node_modules/semver": { - "version": "5.7.1", - "resolved": "https://registry.npmjs.org/semver/-/semver-5.7.1.tgz", - "integrity": "sha512-sauaDf/PZdVgrLTNYHRtpXa1iRiKcaebiKQ1BJdpQlWH2lCvexQdX55snPFyK7QzpudqbCI0qXFfOasHdyNDGQ==", - "bin": { - "semver": "bin/semver" - } - }, - "node_modules/babel-plugin-istanbul/node_modules/strip-bom": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/strip-bom/-/strip-bom-2.0.0.tgz", - "integrity": "sha1-YhmoVhZSBJHzV4i9vxRHqZx+aw4=", - "dependencies": { - "is-utf8": "^0.2.0" - }, - "engines": { - "node": ">=0.10.0" - } - }, - "node_modules/babel-plugin-istanbul/node_modules/test-exclude": { - "version": "4.2.3", - "resolved": "https://registry.npmjs.org/test-exclude/-/test-exclude-4.2.3.tgz", - "integrity": "sha512-SYbXgY64PT+4GAL2ocI3HwPa4Q4TBKm0cwAVeKOt/Aoc0gSpNRjJX8w0pA1LMKZ3LBmd8pYBqApFNQLII9kavA==", - "dependencies": { - "arrify": "^1.0.1", - "micromatch": "^2.3.11", - "object-assign": "^4.1.0", - "read-pkg-up": "^1.0.1", - "require-main-filename": "^1.0.1" - } - }, - "node_modules/babel-plugin-polyfill-corejs2": { - "version": "0.3.0", - "resolved": "https://registry.npmjs.org/babel-plugin-polyfill-corejs2/-/babel-plugin-polyfill-corejs2-0.3.0.tgz", - "integrity": "sha512-wMDoBJ6uG4u4PNFh72Ty6t3EgfA91puCuAwKIazbQlci+ENb/UU9A3xG5lutjUIiXCIn1CY5L15r9LimiJyrSA==", - "dependencies": { - "@babel/compat-data": "^7.13.11", - "@babel/helper-define-polyfill-provider": "^0.3.0", - "semver": "^6.1.1" - }, - "peerDependencies": { - "@babel/core": "^7.0.0-0" - } - }, - "node_modules/babel-plugin-polyfill-corejs2/node_modules/semver": { - "version": "6.3.0", - "resolved": "https://registry.npmjs.org/semver/-/semver-6.3.0.tgz", - "integrity": "sha512-b39TBaTSfV6yBrapU89p5fKekE2m/NwnDocOVruQFS1/veMgdzuPcnOM34M6CwxW8jH/lxEa5rBoDeUwu5HHTw==", - "bin": { - "semver": "bin/semver.js" - } - }, - "node_modules/babel-plugin-polyfill-corejs3": { - "version": "0.4.0", - "resolved": "https://registry.npmjs.org/babel-plugin-polyfill-corejs3/-/babel-plugin-polyfill-corejs3-0.4.0.tgz", - "integrity": "sha512-YxFreYwUfglYKdLUGvIF2nJEsGwj+RhWSX/ije3D2vQPOXuyMLMtg/cCGMDpOA7Nd+MwlNdnGODbd2EwUZPlsw==", - "dependencies": { - "@babel/helper-define-polyfill-provider": "^0.3.0", - "core-js-compat": "^3.18.0" - }, - "peerDependencies": { - "@babel/core": "^7.0.0-0" - } - }, - "node_modules/babel-plugin-polyfill-regenerator": { - "version": "0.3.0", - "resolved": "https://registry.npmjs.org/babel-plugin-polyfill-regenerator/-/babel-plugin-polyfill-regenerator-0.3.0.tgz", - "integrity": "sha512-dhAPTDLGoMW5/84wkgwiLRwMnio2i1fUe53EuvtKMv0pn2p3S8OCoV1xAzfJPl0KOX7IB89s2ib85vbYiea3jg==", - "dependencies": { - "@babel/helper-define-polyfill-provider": "^0.3.0" - }, - "peerDependencies": { - "@babel/core": "^7.0.0-0" - } - }, - "node_modules/babel-plugin-syntax-async-functions": { - "version": "6.13.0", - "resolved": "https://registry.npmjs.org/babel-plugin-syntax-async-functions/-/babel-plugin-syntax-async-functions-6.13.0.tgz", - "integrity": "sha1-ytnK0RkbWtY0vzCuCHI5HgZHvpU=" - }, - "node_modules/babel-plugin-syntax-exponentiation-operator": { - "version": "6.13.0", - "resolved": "https://registry.npmjs.org/babel-plugin-syntax-exponentiation-operator/-/babel-plugin-syntax-exponentiation-operator-6.13.0.tgz", - "integrity": "sha1-nufoM3KQ2pUoggGmpX9BcDF4MN4=" - }, - "node_modules/babel-plugin-syntax-object-rest-spread": { - "version": "6.13.0", - "resolved": "https://registry.npmjs.org/babel-plugin-syntax-object-rest-spread/-/babel-plugin-syntax-object-rest-spread-6.13.0.tgz", - "integrity": "sha1-/WU28rzhODb/o6VFjEkDpZe7O/U=" - }, - "node_modules/babel-plugin-syntax-trailing-function-commas": { - "version": "6.22.0", - "resolved": "https://registry.npmjs.org/babel-plugin-syntax-trailing-function-commas/-/babel-plugin-syntax-trailing-function-commas-6.22.0.tgz", - "integrity": "sha1-ugNgk3+NBuQBgKQ/4NVhb/9TLPM=" - }, - "node_modules/babel-plugin-transform-async-to-generator": { - "version": "6.24.1", - "resolved": "https://registry.npmjs.org/babel-plugin-transform-async-to-generator/-/babel-plugin-transform-async-to-generator-6.24.1.tgz", - "integrity": "sha1-ZTbjeK/2yx1VF6wOQOs+n8jQh2E=", - "dependencies": { - "babel-helper-remap-async-to-generator": "^6.24.1", - "babel-plugin-syntax-async-functions": "^6.8.0", - "babel-runtime": "^6.22.0" - } - }, - "node_modules/babel-plugin-transform-es2015-arrow-functions": { - "version": "6.22.0", - "resolved": "https://registry.npmjs.org/babel-plugin-transform-es2015-arrow-functions/-/babel-plugin-transform-es2015-arrow-functions-6.22.0.tgz", - "integrity": "sha1-RSaSy3EdX3ncf4XkQM5BufJE0iE=", - "dependencies": { - "babel-runtime": "^6.22.0" - } - }, - "node_modules/babel-plugin-transform-es2015-block-scoped-functions": { - "version": "6.22.0", - "resolved": "https://registry.npmjs.org/babel-plugin-transform-es2015-block-scoped-functions/-/babel-plugin-transform-es2015-block-scoped-functions-6.22.0.tgz", - "integrity": "sha1-u8UbSflk1wy42OC5ToICRs46YUE=", - "dependencies": { - "babel-runtime": "^6.22.0" - } - }, - "node_modules/babel-plugin-transform-es2015-block-scoping": { - "version": "6.26.0", - "resolved": "https://registry.npmjs.org/babel-plugin-transform-es2015-block-scoping/-/babel-plugin-transform-es2015-block-scoping-6.26.0.tgz", - "integrity": "sha1-1w9SmcEwjQXBL0Y4E7CgnnOxiV8=", - "dependencies": { - "babel-runtime": "^6.26.0", - "babel-template": "^6.26.0", - "babel-traverse": "^6.26.0", - "babel-types": "^6.26.0", - "lodash": "^4.17.4" - } - }, - "node_modules/babel-plugin-transform-es2015-classes": { - "version": "6.24.1", - "resolved": "https://registry.npmjs.org/babel-plugin-transform-es2015-classes/-/babel-plugin-transform-es2015-classes-6.24.1.tgz", - "integrity": "sha1-WkxYpQyclGHlZLSyo7+ryXolhNs=", - "dependencies": { - "babel-helper-define-map": "^6.24.1", - "babel-helper-function-name": "^6.24.1", - "babel-helper-optimise-call-expression": "^6.24.1", - "babel-helper-replace-supers": "^6.24.1", - "babel-messages": "^6.23.0", - "babel-runtime": "^6.22.0", - "babel-template": "^6.24.1", - "babel-traverse": "^6.24.1", - "babel-types": "^6.24.1" - } - }, - "node_modules/babel-plugin-transform-es2015-computed-properties": { - "version": "6.24.1", - "resolved": "https://registry.npmjs.org/babel-plugin-transform-es2015-computed-properties/-/babel-plugin-transform-es2015-computed-properties-6.24.1.tgz", - "integrity": "sha1-b+Ko0WiV1WNPTNmZttNICjCBWbM=", - "dependencies": { - "babel-runtime": "^6.22.0", - "babel-template": "^6.24.1" - } - }, - "node_modules/babel-plugin-transform-es2015-destructuring": { - "version": "6.23.0", - "resolved": "https://registry.npmjs.org/babel-plugin-transform-es2015-destructuring/-/babel-plugin-transform-es2015-destructuring-6.23.0.tgz", - "integrity": "sha1-mXux8auWf2gtKwh2/jWNYOdlxW0=", - "dependencies": { - "babel-runtime": "^6.22.0" - } - }, - "node_modules/babel-plugin-transform-es2015-duplicate-keys": { - "version": "6.24.1", - "resolved": "https://registry.npmjs.org/babel-plugin-transform-es2015-duplicate-keys/-/babel-plugin-transform-es2015-duplicate-keys-6.24.1.tgz", - "integrity": "sha1-c+s9MQypaePvnskcU3QabxV2Qj4=", - "dependencies": { - "babel-runtime": "^6.22.0", - "babel-types": "^6.24.1" - } - }, - "node_modules/babel-plugin-transform-es2015-for-of": { - "version": "6.23.0", - "resolved": "https://registry.npmjs.org/babel-plugin-transform-es2015-for-of/-/babel-plugin-transform-es2015-for-of-6.23.0.tgz", - "integrity": "sha1-9HyVsrYT3x0+zC/bdXNiPHUkhpE=", - "dependencies": { - "babel-runtime": "^6.22.0" - } - }, - "node_modules/babel-plugin-transform-es2015-function-name": { - "version": "6.24.1", - "resolved": "https://registry.npmjs.org/babel-plugin-transform-es2015-function-name/-/babel-plugin-transform-es2015-function-name-6.24.1.tgz", - "integrity": "sha1-g0yJhTvDaxrw86TF26qU/Y6sqos=", - "dependencies": { - "babel-helper-function-name": "^6.24.1", - "babel-runtime": "^6.22.0", - "babel-types": "^6.24.1" - } - }, - "node_modules/babel-plugin-transform-es2015-literals": { - "version": "6.22.0", - "resolved": "https://registry.npmjs.org/babel-plugin-transform-es2015-literals/-/babel-plugin-transform-es2015-literals-6.22.0.tgz", - "integrity": "sha1-T1SgLWzWbPkVKAAZox0xklN3yi4=", - "dependencies": { - "babel-runtime": "^6.22.0" - } - }, - "node_modules/babel-plugin-transform-es2015-modules-amd": { - "version": "6.24.1", - "resolved": "https://registry.npmjs.org/babel-plugin-transform-es2015-modules-amd/-/babel-plugin-transform-es2015-modules-amd-6.24.1.tgz", - "integrity": "sha1-Oz5UAXI5hC1tGcMBHEvS8AoA0VQ=", - "dependencies": { - "babel-plugin-transform-es2015-modules-commonjs": "^6.24.1", - "babel-runtime": "^6.22.0", - "babel-template": "^6.24.1" - } - }, - "node_modules/babel-plugin-transform-es2015-modules-commonjs": { - "version": "6.26.2", - "resolved": "https://registry.npmjs.org/babel-plugin-transform-es2015-modules-commonjs/-/babel-plugin-transform-es2015-modules-commonjs-6.26.2.tgz", - "integrity": "sha512-CV9ROOHEdrjcwhIaJNBGMBCodN+1cfkwtM1SbUHmvyy35KGT7fohbpOxkE2uLz1o6odKK2Ck/tz47z+VqQfi9Q==", - "dependencies": { - "babel-plugin-transform-strict-mode": "^6.24.1", - "babel-runtime": "^6.26.0", - "babel-template": "^6.26.0", - "babel-types": "^6.26.0" - } - }, - "node_modules/babel-plugin-transform-es2015-modules-systemjs": { - "version": "6.24.1", - "resolved": "https://registry.npmjs.org/babel-plugin-transform-es2015-modules-systemjs/-/babel-plugin-transform-es2015-modules-systemjs-6.24.1.tgz", - "integrity": "sha1-/4mhQrkRmpBhlfXxBuzzBdlAfSM=", - "dependencies": { - "babel-helper-hoist-variables": "^6.24.1", - "babel-runtime": "^6.22.0", - "babel-template": "^6.24.1" - } - }, - "node_modules/babel-plugin-transform-es2015-modules-umd": { - "version": "6.24.1", - "resolved": "https://registry.npmjs.org/babel-plugin-transform-es2015-modules-umd/-/babel-plugin-transform-es2015-modules-umd-6.24.1.tgz", - "integrity": "sha1-rJl+YoXNGO1hdq22B9YCNErThGg=", - "dependencies": { - "babel-plugin-transform-es2015-modules-amd": "^6.24.1", - "babel-runtime": "^6.22.0", - "babel-template": "^6.24.1" - } - }, - "node_modules/babel-plugin-transform-es2015-object-super": { - "version": "6.24.1", - "resolved": "https://registry.npmjs.org/babel-plugin-transform-es2015-object-super/-/babel-plugin-transform-es2015-object-super-6.24.1.tgz", - "integrity": "sha1-JM72muIcuDp/hgPa0CH1cusnj40=", - "dependencies": { - "babel-helper-replace-supers": "^6.24.1", - "babel-runtime": "^6.22.0" - } - }, - "node_modules/babel-plugin-transform-es2015-parameters": { - "version": "6.24.1", - "resolved": "https://registry.npmjs.org/babel-plugin-transform-es2015-parameters/-/babel-plugin-transform-es2015-parameters-6.24.1.tgz", - "integrity": "sha1-V6w1GrScrxSpfNE7CfZv3wpiXys=", - "dependencies": { - "babel-helper-call-delegate": "^6.24.1", - "babel-helper-get-function-arity": "^6.24.1", - "babel-runtime": "^6.22.0", - "babel-template": "^6.24.1", - "babel-traverse": "^6.24.1", - "babel-types": "^6.24.1" - } - }, - "node_modules/babel-plugin-transform-es2015-shorthand-properties": { - "version": "6.24.1", - "resolved": "https://registry.npmjs.org/babel-plugin-transform-es2015-shorthand-properties/-/babel-plugin-transform-es2015-shorthand-properties-6.24.1.tgz", - "integrity": "sha1-JPh11nIch2YbvZmkYi5R8U3jiqA=", - "dependencies": { - "babel-runtime": "^6.22.0", - "babel-types": "^6.24.1" - } - }, - "node_modules/babel-plugin-transform-es2015-spread": { - "version": "6.22.0", - "resolved": "https://registry.npmjs.org/babel-plugin-transform-es2015-spread/-/babel-plugin-transform-es2015-spread-6.22.0.tgz", - "integrity": "sha1-1taKmfia7cRTbIGlQujdnxdG+NE=", - "dependencies": { - "babel-runtime": "^6.22.0" - } - }, - "node_modules/babel-plugin-transform-es2015-sticky-regex": { - "version": "6.24.1", - "resolved": "https://registry.npmjs.org/babel-plugin-transform-es2015-sticky-regex/-/babel-plugin-transform-es2015-sticky-regex-6.24.1.tgz", - "integrity": "sha1-AMHNsaynERLN8M9hJsLta0V8zbw=", - "dependencies": { - "babel-helper-regex": "^6.24.1", - "babel-runtime": "^6.22.0", - "babel-types": "^6.24.1" - } - }, - "node_modules/babel-plugin-transform-es2015-template-literals": { - "version": "6.22.0", - "resolved": "https://registry.npmjs.org/babel-plugin-transform-es2015-template-literals/-/babel-plugin-transform-es2015-template-literals-6.22.0.tgz", - "integrity": "sha1-qEs0UPfp+PH2g51taH2oS7EjbY0=", - "dependencies": { - "babel-runtime": "^6.22.0" - } - }, - "node_modules/babel-plugin-transform-es2015-typeof-symbol": { - "version": "6.23.0", - "resolved": "https://registry.npmjs.org/babel-plugin-transform-es2015-typeof-symbol/-/babel-plugin-transform-es2015-typeof-symbol-6.23.0.tgz", - "integrity": "sha1-3sCfHN3/lLUqxz1QXITfWdzOs3I=", - "dependencies": { - "babel-runtime": "^6.22.0" - } - }, - "node_modules/babel-plugin-transform-es2015-unicode-regex": { - "version": "6.24.1", - "resolved": "https://registry.npmjs.org/babel-plugin-transform-es2015-unicode-regex/-/babel-plugin-transform-es2015-unicode-regex-6.24.1.tgz", - "integrity": "sha1-04sS9C6nMj9yk4fxinxa4frrNek=", - "dependencies": { - "babel-helper-regex": "^6.24.1", - "babel-runtime": "^6.22.0", - "regexpu-core": "^2.0.0" - } - }, - "node_modules/babel-plugin-transform-es2015-unicode-regex/node_modules/jsesc": { - "version": "0.5.0", - "resolved": "https://registry.npmjs.org/jsesc/-/jsesc-0.5.0.tgz", - "integrity": "sha1-597mbjXW/Bb3EP6R1c9p9w8IkR0=", - "bin": { - "jsesc": "bin/jsesc" - } - }, - "node_modules/babel-plugin-transform-es2015-unicode-regex/node_modules/regexpu-core": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/regexpu-core/-/regexpu-core-2.0.0.tgz", - "integrity": "sha1-SdA4g3uNz4v6W5pCE5k45uoq4kA=", - "dependencies": { - "regenerate": "^1.2.1", - "regjsgen": "^0.2.0", - "regjsparser": "^0.1.4" - } - }, - "node_modules/babel-plugin-transform-es2015-unicode-regex/node_modules/regjsgen": { - "version": "0.2.0", - "resolved": "https://registry.npmjs.org/regjsgen/-/regjsgen-0.2.0.tgz", - "integrity": "sha1-bAFq3qxVT3WCP+N6wFuS1aTtsfc=" - }, - "node_modules/babel-plugin-transform-es2015-unicode-regex/node_modules/regjsparser": { - "version": "0.1.5", - "resolved": "https://registry.npmjs.org/regjsparser/-/regjsparser-0.1.5.tgz", - "integrity": "sha1-fuj4Tcb6eS0/0K4ijSS9lJ6tIFw=", - "dependencies": { - "jsesc": "~0.5.0" - }, - "bin": { - "regjsparser": "bin/parser" - } - }, - "node_modules/babel-plugin-transform-exponentiation-operator": { - "version": "6.24.1", - "resolved": "https://registry.npmjs.org/babel-plugin-transform-exponentiation-operator/-/babel-plugin-transform-exponentiation-operator-6.24.1.tgz", - "integrity": "sha1-KrDJx/MJj6SJB3cruBP+QejeOg4=", - "dependencies": { - "babel-helper-builder-binary-assignment-operator-visitor": "^6.24.1", - "babel-plugin-syntax-exponentiation-operator": "^6.8.0", - "babel-runtime": "^6.22.0" - } - }, - "node_modules/babel-plugin-transform-regenerator": { - "version": "6.26.0", - "resolved": "https://registry.npmjs.org/babel-plugin-transform-regenerator/-/babel-plugin-transform-regenerator-6.26.0.tgz", - "integrity": "sha1-4HA2lvveJ/Cj78rPi03KL3s6jy8=", - "dependencies": { - "regenerator-transform": "^0.10.0" - } - }, - "node_modules/babel-plugin-transform-regenerator/node_modules/regenerator-transform": { - "version": "0.10.1", - "resolved": "https://registry.npmjs.org/regenerator-transform/-/regenerator-transform-0.10.1.tgz", - "integrity": "sha512-PJepbvDbuK1xgIgnau7Y90cwaAmO/LCLMI2mPvaXq2heGMR3aWW5/BQvYrhJ8jgmQjXewXvBjzfqKcVOmhjZ6Q==", - "dependencies": { - "babel-runtime": "^6.18.0", - "babel-types": "^6.19.0", - "private": "^0.1.6" - } - }, - "node_modules/babel-plugin-transform-strict-mode": { - "version": "6.24.1", - "resolved": "https://registry.npmjs.org/babel-plugin-transform-strict-mode/-/babel-plugin-transform-strict-mode-6.24.1.tgz", - "integrity": "sha1-1fr3qleKZbvlkc9e2uBKDGcCB1g=", - "dependencies": { - "babel-runtime": "^6.22.0", - "babel-types": "^6.24.1" - } - }, - "node_modules/babel-polyfill": { - "version": "6.26.0", - "resolved": "https://registry.npmjs.org/babel-polyfill/-/babel-polyfill-6.26.0.tgz", - "integrity": "sha1-N5k3q8Z9eJWXCtxiHyhM2WbPIVM=", - "dependencies": { - "babel-runtime": "^6.26.0", - "core-js": "^2.5.0", - "regenerator-runtime": "^0.10.5" - } - }, - "node_modules/babel-preset-env": { - "version": "1.7.0", - "resolved": "https://registry.npmjs.org/babel-preset-env/-/babel-preset-env-1.7.0.tgz", - "integrity": "sha512-9OR2afuKDneX2/q2EurSftUYM0xGu4O2D9adAhVfADDhrYDaxXV0rBbevVYoY9n6nyX1PmQW/0jtpJvUNr9CHg==", - "dependencies": { - "babel-plugin-check-es2015-constants": "^6.22.0", - "babel-plugin-syntax-trailing-function-commas": "^6.22.0", - "babel-plugin-transform-async-to-generator": "^6.22.0", - "babel-plugin-transform-es2015-arrow-functions": "^6.22.0", - "babel-plugin-transform-es2015-block-scoped-functions": "^6.22.0", - "babel-plugin-transform-es2015-block-scoping": "^6.23.0", - "babel-plugin-transform-es2015-classes": "^6.23.0", - "babel-plugin-transform-es2015-computed-properties": "^6.22.0", - "babel-plugin-transform-es2015-destructuring": "^6.23.0", - "babel-plugin-transform-es2015-duplicate-keys": "^6.22.0", - "babel-plugin-transform-es2015-for-of": "^6.23.0", - "babel-plugin-transform-es2015-function-name": "^6.22.0", - "babel-plugin-transform-es2015-literals": "^6.22.0", - "babel-plugin-transform-es2015-modules-amd": "^6.22.0", - "babel-plugin-transform-es2015-modules-commonjs": "^6.23.0", - "babel-plugin-transform-es2015-modules-systemjs": "^6.23.0", - "babel-plugin-transform-es2015-modules-umd": "^6.23.0", - "babel-plugin-transform-es2015-object-super": "^6.22.0", - "babel-plugin-transform-es2015-parameters": "^6.23.0", - "babel-plugin-transform-es2015-shorthand-properties": "^6.22.0", - "babel-plugin-transform-es2015-spread": "^6.22.0", - "babel-plugin-transform-es2015-sticky-regex": "^6.22.0", - "babel-plugin-transform-es2015-template-literals": "^6.22.0", - "babel-plugin-transform-es2015-typeof-symbol": "^6.23.0", - "babel-plugin-transform-es2015-unicode-regex": "^6.22.0", - "babel-plugin-transform-exponentiation-operator": "^6.22.0", - "babel-plugin-transform-regenerator": "^6.22.0", - "browserslist": "^3.2.6", - "invariant": "^2.2.2", - "semver": "^5.3.0" - } - }, - "node_modules/babel-preset-env/node_modules/browserslist": { - "version": "3.2.8", - "resolved": "https://registry.npmjs.org/browserslist/-/browserslist-3.2.8.tgz", - "integrity": "sha512-WHVocJYavUwVgVViC0ORikPHQquXwVh939TaelZ4WDqpWgTX/FsGhl/+P4qBUAGcRvtOgDgC+xftNWWp2RUTAQ==", - "dependencies": { - "caniuse-lite": "^1.0.30000844", - "electron-to-chromium": "^1.3.47" - }, - "bin": { - "browserslist": "cli.js" - } - }, - "node_modules/babel-preset-env/node_modules/semver": { - "version": "5.7.1", - "resolved": "https://registry.npmjs.org/semver/-/semver-5.7.1.tgz", - "integrity": "sha512-sauaDf/PZdVgrLTNYHRtpXa1iRiKcaebiKQ1BJdpQlWH2lCvexQdX55snPFyK7QzpudqbCI0qXFfOasHdyNDGQ==", - "bin": { - "semver": "bin/semver" - } - }, - "node_modules/babel-register": { - "version": "6.26.0", - "resolved": "https://registry.npmjs.org/babel-register/-/babel-register-6.26.0.tgz", - "integrity": "sha1-btAhFz4vy0htestFxgCahW9kcHE=", - "dependencies": { - "babel-core": "^6.26.0", - "babel-runtime": "^6.26.0", - "core-js": "^2.5.0", - "home-or-tmp": "^2.0.0", - "lodash": "^4.17.4", - "mkdirp": "^0.5.1", - "source-map-support": "^0.4.15" - } - }, - "node_modules/babel-register/node_modules/mkdirp": { - "version": "0.5.5", - "resolved": "https://registry.npmjs.org/mkdirp/-/mkdirp-0.5.5.tgz", - "integrity": "sha512-NKmAlESf6jMGym1++R0Ra7wvhV+wFW63FaSOFPwRahvea0gMUcGUhVeAg/0BC0wiv9ih5NYPB1Wn1UEI1/L+xQ==", - "dependencies": { - "minimist": "^1.2.5" - }, - "bin": { - "mkdirp": "bin/cmd.js" - } - }, - "node_modules/babel-register/node_modules/source-map": { - "version": "0.5.7", - "resolved": "https://registry.npmjs.org/source-map/-/source-map-0.5.7.tgz", - "integrity": "sha1-igOdLRAh0i0eoUyA2OpGi6LvP8w=", - "engines": { - "node": ">=0.10.0" - } - }, - "node_modules/babel-register/node_modules/source-map-support": { - "version": "0.4.18", - "resolved": "https://registry.npmjs.org/source-map-support/-/source-map-support-0.4.18.tgz", - "integrity": "sha512-try0/JqxPLF9nOjvSta7tVondkP5dwgyLDjVoyMDlmjugT2lRZ1OfsrYTkCd2hkDnJTKRbO/Rl3orm8vlsUzbA==", - "dependencies": { - "source-map": "^0.5.6" - } - }, - "node_modules/babel-runtime": { - "version": "6.26.0", - "resolved": "https://registry.npmjs.org/babel-runtime/-/babel-runtime-6.26.0.tgz", - "integrity": "sha1-llxwWGaOgrVde/4E/yM3vItWR/4=", - "dependencies": { - "core-js": "^2.4.0", - "regenerator-runtime": "^0.11.0" - } - }, - "node_modules/babel-runtime/node_modules/regenerator-runtime": { - "version": "0.11.1", - "resolved": "https://registry.npmjs.org/regenerator-runtime/-/regenerator-runtime-0.11.1.tgz", - "integrity": "sha512-MguG95oij0fC3QV3URf4V2SDYGJhJnJGqvIIgdECeODCT98wSWDAJ94SSuVpYQUoTcGUIL6L4yNB7j1DFFHSBg==" - }, - "node_modules/babel-template": { - "version": "6.26.0", - "resolved": "https://registry.npmjs.org/babel-template/-/babel-template-6.26.0.tgz", - "integrity": "sha1-3gPi0WOWsGn0bdn/+FIfsaDjXgI=", - "dependencies": { - "babel-runtime": "^6.26.0", - "babel-traverse": "^6.26.0", - "babel-types": "^6.26.0", - "babylon": "^6.18.0", - "lodash": "^4.17.4" - } - }, - "node_modules/babel-traverse": { - "version": "6.26.0", - "resolved": "https://registry.npmjs.org/babel-traverse/-/babel-traverse-6.26.0.tgz", - "integrity": "sha1-RqnL1+3MYsjlwGTi0tjQ9ANXZu4=", - "dependencies": { - "babel-code-frame": "^6.26.0", - "babel-messages": "^6.23.0", - "babel-runtime": "^6.26.0", - "babel-types": "^6.26.0", - "babylon": "^6.18.0", - "debug": "^2.6.8", - "globals": "^9.18.0", - "invariant": "^2.2.2", - "lodash": "^4.17.4" - } - }, - "node_modules/babel-traverse/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/babel-traverse/node_modules/globals": { - "version": "9.18.0", - "resolved": "https://registry.npmjs.org/globals/-/globals-9.18.0.tgz", - "integrity": "sha512-S0nG3CLEQiY/ILxqtztTWH/3iRRdyBLw6KMDxnKMchrtbj2OFmehVh0WUCfW3DUrIgx/qFrJPICrq4Z4sTR9UQ==", - "engines": { - "node": ">=0.10.0" - } - }, - "node_modules/babel-traverse/node_modules/ms": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/ms/-/ms-2.0.0.tgz", - "integrity": "sha1-VgiurfwAvmwpAd9fmGF4jeDVl8g=" - }, - "node_modules/babel-types": { - "version": "6.26.0", - "resolved": "https://registry.npmjs.org/babel-types/-/babel-types-6.26.0.tgz", - "integrity": "sha1-o7Bz+Uq0nrb6Vc1lInozQ4BjJJc=", - "dependencies": { - "babel-runtime": "^6.26.0", - "esutils": "^2.0.2", - "lodash": "^4.17.4", - "to-fast-properties": "^1.0.3" - } - }, - "node_modules/babel-types/node_modules/to-fast-properties": { - "version": "1.0.3", - "resolved": "https://registry.npmjs.org/to-fast-properties/-/to-fast-properties-1.0.3.tgz", - "integrity": "sha1-uDVx+k2MJbguIxsG46MFXeTKGkc=", - "engines": { - "node": ">=0.10.0" - } - }, - "node_modules/babylon": { - "version": "6.18.0", - "resolved": "https://registry.npmjs.org/babylon/-/babylon-6.18.0.tgz", - "integrity": "sha512-q/UEjfGJ2Cm3oKV71DJz9d25TPnq5rhBVL2Q4fA5wcC3jcrdn7+SssEybFIxwAvvP+YCsCYNKughoF33GxgycQ==", - "bin": { - "babylon": "bin/babylon.js" - } - }, - "node_modules/backo2": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/backo2/-/backo2-1.0.2.tgz", - "integrity": "sha1-MasayLEpNjRj41s+u2n038+6eUc=" - }, - "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==" - }, - "node_modules/base64-arraybuffer": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/base64-arraybuffer/-/base64-arraybuffer-1.0.1.tgz", - "integrity": "sha512-vFIUq7FdLtjZMhATwDul5RZWv2jpXQ09Pd6jcVEOvIsqCWTRFD/ONHNfyOS8dA/Ippi5dsIgpyKWKZaAKZltbA==", - "engines": { - "node": ">= 0.6.0" - } - }, - "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==", - "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/base64id": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/base64id/-/base64id-2.0.0.tgz", - "integrity": "sha512-lGe34o6EHj9y3Kts9R4ZYs/Gr+6N7MCaMlIFA3F1R2O5/m7K06AxfSeO5530PEERE6/WyEg3lsuyw4GHlPZHog==", - "engines": { - "node": "^4.5.0 || >= 5.9" - } - }, - "node_modules/bcrypt-pbkdf": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/bcrypt-pbkdf/-/bcrypt-pbkdf-1.0.2.tgz", - "integrity": "sha1-pDAdOJtqQ/m2f/PKEaP2Y342Dp4=", - "dev": true, - "dependencies": { - "tweetnacl": "^0.14.3" - } - }, - "node_modules/bcryptjs": { - "version": "2.4.3", - "resolved": "https://registry.npmjs.org/bcryptjs/-/bcryptjs-2.4.3.tgz", - "integrity": "sha1-mrVie5PmBiH/fNrF2pczAn3x0Ms=" - }, - "node_modules/before-after-hook": { - "version": "2.2.2", - "resolved": "https://registry.npmjs.org/before-after-hook/-/before-after-hook-2.2.2.tgz", - "integrity": "sha512-3pZEU3NT5BFUo/AD5ERPWOgQOCZITni6iavr5AUw5AUwQjMlI0kzu5btnyD39AF0gUEsDPwJT+oY1ORBJijPjQ==", - "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==", - "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==", - "engines": { - "node": ">=8" - } - }, - "node_modules/bl": { - "version": "0.7.0", - "resolved": "https://registry.npmjs.org/bl/-/bl-0.7.0.tgz", - "integrity": "sha1-P7BnBgKsKHjrdw3CA58YNr5irls=", - "dependencies": { - "readable-stream": "~1.0.2" - }, - "peerDependencies": { - "stream-browserify": "*" - } - }, - "node_modules/bl/node_modules/isarray": { - "version": "0.0.1", - "resolved": "https://registry.npmjs.org/isarray/-/isarray-0.0.1.tgz", - "integrity": "sha1-ihis/Kmo9Bd+Cav8YDiTmwXR7t8=" - }, - "node_modules/bl/node_modules/readable-stream": { - "version": "1.0.34", - "resolved": "https://registry.npmjs.org/readable-stream/-/readable-stream-1.0.34.tgz", - "integrity": "sha1-Elgg40vIQtLyqq+v5MKRbuMsFXw=", - "dependencies": { - "core-util-is": "~1.0.0", - "inherits": "~2.0.1", - "isarray": "0.0.1", - "string_decoder": "~0.10.x" - } - }, - "node_modules/bl/node_modules/string_decoder": { - "version": "0.10.31", - "resolved": "https://registry.npmjs.org/string_decoder/-/string_decoder-0.10.31.tgz", - "integrity": "sha1-YuIDvEF2bGwoyfyEMB2rHFMQ+pQ=" - }, - "node_modules/bluebird": { - "version": "3.7.2", - "resolved": "https://registry.npmjs.org/bluebird/-/bluebird-3.7.2.tgz", - "integrity": "sha512-XpNj6GDQzdfW+r2Wnn7xiSAd7TM3jzkxGXBGTtWKuSXv1xUV+azxAm8jdWZN06QTQk+2N2XB9jRDkvbmQmcRtg==" - }, - "node_modules/bn.js": { - "version": "4.12.0", - "resolved": "https://registry.npmjs.org/bn.js/-/bn.js-4.12.0.tgz", - "integrity": "sha512-c98Bf3tPniI+scsdk237ku1Dc3ujXQTSgyiPUDEOe7tRkhrqridvh8klBv0HCEso1OLOYcHuCv/cS6DNxKH+ZA==", - "optional": true - }, - "node_modules/body-parser": { - "version": "1.19.1", - "resolved": "https://registry.npmjs.org/body-parser/-/body-parser-1.19.1.tgz", - "integrity": "sha512-8ljfQi5eBk8EJfECMrgqNGWPEY5jWP+1IzkzkGdFFEwFQZZyaZ21UqdaHktgiMlH0xLHqIFtE/u2OYE5dOtViA==", - "dependencies": { - "bytes": "3.1.1", - "content-type": "~1.0.4", - "debug": "2.6.9", - "depd": "~1.1.2", - "http-errors": "1.8.1", - "iconv-lite": "0.4.24", - "on-finished": "~2.3.0", - "qs": "6.9.6", - "raw-body": "2.4.2", - "type-is": "~1.6.18" - }, - "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==", - "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": "sha1-VgiurfwAvmwpAd9fmGF4jeDVl8g=" - }, - "node_modules/body-parser/node_modules/qs": { - "version": "6.9.6", - "resolved": "https://registry.npmjs.org/qs/-/qs-6.9.6.tgz", - "integrity": "sha512-TIRk4aqYLNoJUbd+g2lEdz5kLWIuTMRagAXxl78Q0RiVjAOugHmeKNGdd3cwo/ktpf9aL9epCfFqWDEKysUlLQ==", - "engines": { - "node": ">=0.6" - }, - "funding": { - "url": "https://github.com/sponsors/ljharb" - } - }, - "node_modules/boxen": { - "version": "5.1.2", - "resolved": "https://registry.npmjs.org/boxen/-/boxen-5.1.2.tgz", - "integrity": "sha512-9gYgQKXx+1nP8mP7CzFyaUARhg7D3n1dF/FnErWmu9l6JvGpNUN278h0aSb+QjoiKSWG+iZ3uHrcqk0qrY9RQQ==", - "dev": true, - "dependencies": { - "ansi-align": "^3.0.0", - "camelcase": "^6.2.0", - "chalk": "^4.1.0", - "cli-boxes": "^2.2.1", - "string-width": "^4.2.2", - "type-fest": "^0.20.2", - "widest-line": "^3.1.0", - "wrap-ansi": "^7.0.0" - }, - "engines": { - "node": ">=10" - }, - "funding": { - "url": "https://github.com/sponsors/sindresorhus" - } - }, - "node_modules/boxen/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/brace-expansion": { - "version": "1.1.11", - "resolved": "https://registry.npmjs.org/brace-expansion/-/brace-expansion-1.1.11.tgz", - "integrity": "sha512-iCuPHDFgrHX7H2vEI/5xpz07zSHB00TpugqhmYtVmMO6518mCuRMoOYFldEBl0g187ufozdaHgWKcYFb61qGiA==", - "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==", - "dependencies": { - "fill-range": "^7.0.1" - }, - "engines": { - "node": ">=8" - } - }, - "node_modules/brorand": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/brorand/-/brorand-1.1.0.tgz", - "integrity": "sha1-EsJe/kCkXjwyPrhnWgoM5XsiNx8=", - "optional": true - }, - "node_modules/browser-refresh-client": { - "version": "1.1.4", - "resolved": "https://registry.npmjs.org/browser-refresh-client/-/browser-refresh-client-1.1.4.tgz", - "integrity": "sha1-jl/4R1/h1UHSroH3oa6gWuIaYhc=" - }, - "node_modules/browser-stdout": { - "version": "1.3.1", - "resolved": "https://registry.npmjs.org/browser-stdout/-/browser-stdout-1.3.1.tgz", - "integrity": "sha512-qhAVI1+Av2X7qelOfAIYwXONood6XlZE/fXaBSmW/T5SzLAmCgzi+eiWE7fUvbHaeNBQH13UftjpXxsfLkMpgw==" - }, - "node_modules/browserslist": { - "version": "4.19.1", - "resolved": "https://registry.npmjs.org/browserslist/-/browserslist-4.19.1.tgz", - "integrity": "sha512-u2tbbG5PdKRTUoctO3NBD8FQ5HdPh1ZXPHzp1rwaa5jTc+RV9/+RlWiAIKmjRPQF+xbGM9Kklj5bZQFa2s/38A==", - "dependencies": { - "caniuse-lite": "^1.0.30001286", - "electron-to-chromium": "^1.4.17", - "escalade": "^3.1.1", - "node-releases": "^2.0.1", - "picocolors": "^1.0.0" - }, - "bin": { - "browserslist": "cli.js" - }, - "engines": { - "node": "^6 || ^7 || ^8 || ^9 || ^10 || ^11 || ^12 || >=13.7" - }, - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/browserslist" - } - }, - "node_modules/bson": { - "version": "4.6.0", - "resolved": "https://registry.npmjs.org/bson/-/bson-4.6.0.tgz", - "integrity": "sha512-8jw1NU1hglS+Da1jDOUYuNcBJ4cNHCFIqzlwoFNnsTOg2R/ox0aTYcTiBN4dzRa9q7Cvy6XErh3L8ReTEb9AQQ==", - "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==", - "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-crc32": { - "version": "0.2.13", - "resolved": "https://registry.npmjs.org/buffer-crc32/-/buffer-crc32-0.2.13.tgz", - "integrity": "sha1-DTM+PwDqxQqhRUq9MO+MKl2ackI=", - "engines": { - "node": "*" - } - }, - "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": "sha1-+OcRMvf/5uAaXJaXpMbz5I1cyBk=" - }, - "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/builtins": { - "version": "1.0.3", - "resolved": "https://registry.npmjs.org/builtins/-/builtins-1.0.3.tgz", - "integrity": "sha1-y5T662HIaWRR2zZTThQi+U8K7og=", - "dev": true - }, - "node_modules/byline": { - "version": "5.0.0", - "resolved": "https://registry.npmjs.org/byline/-/byline-5.0.0.tgz", - "integrity": "sha1-dBxSFkaOrcRXsDQQEYrXfejB3bE=", - "dev": true, - "engines": { - "node": ">=0.10.0" - } - }, - "node_modules/byte-size": { - "version": "7.0.1", - "resolved": "https://registry.npmjs.org/byte-size/-/byte-size-7.0.1.tgz", - "integrity": "sha512-crQdqyCwhokxwV1UyDzLZanhkugAgft7vt0qbbdt60C6Zf3CAiGmtUCylbtYwrU6loOUw3euGrNtW1J651ot1A==", - "dev": true, - "engines": { - "node": ">=10" - } - }, - "node_modules/bytes": { - "version": "3.1.1", - "resolved": "https://registry.npmjs.org/bytes/-/bytes-3.1.1.tgz", - "integrity": "sha512-dWe4nWO/ruEOY7HkUJ5gFt1DCFV9zPRoJr8pV0/ASQermOZjtq8jMjOprC0Kd10GLN+l7xaUPvxzJFWtxGu8Fg==", - "engines": { - "node": ">= 0.8" - } - }, - "node_modules/cacache": { - "version": "15.3.0", - "resolved": "https://registry.npmjs.org/cacache/-/cacache-15.3.0.tgz", - "integrity": "sha512-VVdYzXEn+cnbXpFgWs5hTT7OScegHVmLhJIR8Ufqk3iFD6A6j5iSX1KuBTfNEv4tdJWE2PzA6IVFtcLC7fN9wQ==", - "dev": true, - "dependencies": { - "@npmcli/fs": "^1.0.0", - "@npmcli/move-file": "^1.0.1", - "chownr": "^2.0.0", - "fs-minipass": "^2.0.0", - "glob": "^7.1.4", - "infer-owner": "^1.0.4", - "lru-cache": "^6.0.0", - "minipass": "^3.1.1", - "minipass-collect": "^1.0.2", - "minipass-flush": "^1.0.5", - "minipass-pipeline": "^1.2.2", - "mkdirp": "^1.0.3", - "p-map": "^4.0.0", - "promise-inflight": "^1.0.1", - "rimraf": "^3.0.2", - "ssri": "^8.0.1", - "tar": "^6.0.2", - "unique-filename": "^1.1.1" - }, - "engines": { - "node": ">= 10" - } - }, - "node_modules/cache-content-type": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/cache-content-type/-/cache-content-type-1.0.1.tgz", - "integrity": "sha512-IKufZ1o4Ut42YUrZSo8+qnMTrFuKkvyoLXUywKz9GJ5BrhOFGhLdkx9sG4KAnVvbY6kEcSFjLQul+DVmBm2bgA==", - "dependencies": { - "mime-types": "^2.1.18", - "ylru": "^1.2.0" - }, - "engines": { - "node": ">= 6.0.0" - } - }, - "node_modules/cacheable-request": { - "version": "6.1.0", - "resolved": "https://registry.npmjs.org/cacheable-request/-/cacheable-request-6.1.0.tgz", - "integrity": "sha512-Oj3cAGPCqOZX7Rz64Uny2GYAZNliQSqfbePrgAQ1wKAihYmCUnraBtJtKcGR4xz7wF+LoJC+ssFZvv5BgF9Igg==", - "dev": true, - "dependencies": { - "clone-response": "^1.0.2", - "get-stream": "^5.1.0", - "http-cache-semantics": "^4.0.0", - "keyv": "^3.0.0", - "lowercase-keys": "^2.0.0", - "normalize-url": "^4.1.0", - "responselike": "^1.0.2" - }, - "engines": { - "node": ">=8" - } - }, - "node_modules/cacheable-request/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/cacheable-request/node_modules/lowercase-keys": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/lowercase-keys/-/lowercase-keys-2.0.0.tgz", - "integrity": "sha512-tqNXrS78oMOE73NMxK4EMLQsQowWf8jKooH9g7xPavRT706R6bkQJ6DY2Te7QukaZsulxa30wQ7bk0pm4XiHmA==", - "dev": true, - "engines": { - "node": ">=8" - } - }, - "node_modules/cacheable-request/node_modules/normalize-url": { - "version": "4.5.1", - "resolved": "https://registry.npmjs.org/normalize-url/-/normalize-url-4.5.1.tgz", - "integrity": "sha512-9UZCFRHQdNrfTpGg8+1INIg93B6zE0aXMVFkw1WFwvO4SlZywU6aLg5Of0Ap/PgcbSw4LNxvMWXMeugwMCX0AA==", - "dev": true, - "engines": { - "node": ">=8" - } - }, - "node_modules/caching-transform": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/caching-transform/-/caching-transform-4.0.0.tgz", - "integrity": "sha512-kpqOvwXnjjN44D89K5ccQC+RUrsy7jB/XLlRrx0D7/2HNcTPqzsb6XgYoErwko6QsV184CA2YgS1fxDiiDZMWA==", - "dev": true, - "dependencies": { - "hasha": "^5.0.0", - "make-dir": "^3.0.0", - "package-hash": "^4.0.0", - "write-file-atomic": "^3.0.0" - }, - "engines": { - "node": ">=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==", - "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.30001295", - "resolved": "https://registry.npmjs.org/caniuse-lite/-/caniuse-lite-1.0.30001295.tgz", - "integrity": "sha512-lSP16vcyC0FEy0R4ECc9duSPoKoZy+YkpGkue9G4D81OfPnliopaZrU10+qtPdT8PbGXad/PNx43TIQrOmJZSQ==", - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/browserslist" - } - }, - "node_modules/caseless": { - "version": "0.12.0", - "resolved": "https://registry.npmjs.org/caseless/-/caseless-0.12.0.tgz", - "integrity": "sha1-G2gcIf+EAzyCZUMJBolCDRhxUdw=", - "dev": true - }, - "node_modules/center-align": { - "version": "0.1.3", - "resolved": "https://registry.npmjs.org/center-align/-/center-align-0.1.3.tgz", - "integrity": "sha1-qg0yYptu6XIgBBHL1EYckHvCt60=", - "dependencies": { - "align-text": "^0.1.3", - "lazy-cache": "^1.0.3" - }, - "engines": { - "node": ">=0.10.0" - } - }, - "node_modules/chai": { - "version": "3.5.0", - "resolved": "https://registry.npmjs.org/chai/-/chai-3.5.0.tgz", - "integrity": "sha1-TQJjewZ/6Vi9v906QOxW/vc3Mkc=", - "dependencies": { - "assertion-error": "^1.0.1", - "deep-eql": "^0.1.3", - "type-detect": "^1.0.0" - }, - "engines": { - "node": ">= 0.4.0" - } - }, - "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/char-props": { - "version": "0.1.5", - "resolved": "https://registry.npmjs.org/char-props/-/char-props-0.1.5.tgz", - "integrity": "sha1-W5UvniDqIc0Iyn/hNaEPb+kcEJ4=", - "engines": { - "node": ">= 0.6.0" - } - }, - "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.2", - "resolved": "https://registry.npmjs.org/chokidar/-/chokidar-3.5.2.tgz", - "integrity": "sha512-ekGhOnNVPgT77r4K/U3GDhu+FQ2S8TnK/s2KbIGXi0SZWuwkZ2QNyfWdZW+TVfn84DpEP7rLeCt2UI6bJ8GwbQ==", - "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/chokidar/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==", - "dependencies": { - "is-glob": "^4.0.1" - }, - "engines": { - "node": ">= 6" - } - }, - "node_modules/chownr": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/chownr/-/chownr-2.0.0.tgz", - "integrity": "sha512-bIomtDF5KGpdogkLd9VspvFzk9KfpyyGlS8YFVZl7TGPBHL5snIOnxeshwVgPteQ9b4Eydl+pVbIyE1DcvCWgQ==", - "dev": true, - "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", - "integrity": "sha512-p3KULyQg4S7NIHixdwbGX+nFHkoBiA4YQmyWtjb8XngSKV124nJmRysgAeujbUVb15vh+RvFUfCPqU7rXk+hZg==", - "engines": { - "node": ">=6.0" - } - }, - "node_modules/ci-info": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/ci-info/-/ci-info-2.0.0.tgz", - "integrity": "sha512-5tK7EtrZ0N+OLFMthtqOj4fI2Jeb88C4CAZPu25LDVUgXJ0A3Js4PMGqrn0JU1W0Mh1/Z8wZzYPxqUrXeBboCQ==", - "dev": true - }, - "node_modules/cint": { - "version": "8.2.1", - "resolved": "https://registry.npmjs.org/cint/-/cint-8.2.1.tgz", - "integrity": "sha1-cDhrG0jidz0NYxZqVa/5TvRFahI=", - "dev": true - }, - "node_modules/clean-stack": { - "version": "2.2.0", - "resolved": "https://registry.npmjs.org/clean-stack/-/clean-stack-2.2.0.tgz", - "integrity": "sha512-4diC9HaTE+KRAMWhDhrGOECgWZxoevMc5TlkObMqNSsVU62PYzXZ/SMTjzyGAFF1YusgxGcSWTEXBhp0CPwQ1A==", - "dev": true, - "engines": { - "node": ">=6" - } - }, - "node_modules/cli-boxes": { - "version": "2.2.1", - "resolved": "https://registry.npmjs.org/cli-boxes/-/cli-boxes-2.2.1.tgz", - "integrity": "sha512-y4coMcylgSCdVinjiDBuR8PCC2bLjyGTwEmPb9NHR/QaNU6EUOXcTY/s6VjGMD6ENSEaeQYHCY0GNGS5jfMwPw==", - "dev": true, - "engines": { - "node": ">=6" - }, - "funding": { - "url": "https://github.com/sponsors/sindresorhus" - } - }, - "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-table": { - "version": "0.3.11", - "resolved": "https://registry.npmjs.org/cli-table/-/cli-table-0.3.11.tgz", - "integrity": "sha512-IqLQi4lO0nIB4tcdTpN4LCB9FI3uqrJZK7RC515EnhZ6qBaglkIgICb1wjeAqpdoOabm1+SuQtkXIPdYC93jhQ==", - "dev": true, - "dependencies": { - "colors": "1.0.3" - }, - "engines": { - "node": ">= 0.2.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": "7.0.4", - "resolved": "https://registry.npmjs.org/cliui/-/cliui-7.0.4.tgz", - "integrity": "sha512-OcRE68cOsVMXp1Yvonl/fzkQOyjLSu/8bhPDfQt0e0/Eb283TKP20Fs2MqoPsr9SwA595rRCA+QMzYc9nBP+JQ==", - "dependencies": { - "string-width": "^4.2.0", - "strip-ansi": "^6.0.0", - "wrap-ansi": "^7.0.0" - } - }, - "node_modules/clone": { - "version": "1.0.4", - "resolved": "https://registry.npmjs.org/clone/-/clone-1.0.4.tgz", - "integrity": "sha1-2jCcwmPfFZlMaIypAheco8fNfH4=", - "dev": true, - "engines": { - "node": ">=0.8" - } - }, - "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==", - "dependencies": { - "is-plain-object": "^2.0.4", - "kind-of": "^6.0.2", - "shallow-clone": "^3.0.0" - }, - "engines": { - "node": ">=6" - } - }, - "node_modules/clone-deep/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==", - "dependencies": { - "isobject": "^3.0.1" - }, - "engines": { - "node": ">=0.10.0" - } - }, - "node_modules/clone-response": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/clone-response/-/clone-response-1.0.2.tgz", - "integrity": "sha1-0dyXOSAxTfZ/vrlCI7TuNQI56Ws=", - "dev": true, - "dependencies": { - "mimic-response": "^1.0.0" - } - }, - "node_modules/cmd-shim": { - "version": "4.1.0", - "resolved": "https://registry.npmjs.org/cmd-shim/-/cmd-shim-4.1.0.tgz", - "integrity": "sha512-lb9L7EM4I/ZRVuljLPEtUJOP+xiQVknZ4ZMpMgEp4JzNldPb27HU03hi6K1/6CoIuit/Zm/LQXySErFeXxDprw==", - "dev": true, - "dependencies": { - "mkdirp-infer-owner": "^2.0.0" - }, - "engines": { - "node": ">=10" - } - }, - "node_modules/co": { - "version": "4.6.0", - "resolved": "https://registry.npmjs.org/co/-/co-4.6.0.tgz", - "integrity": "sha1-bqa989hTrlTMuOR7+gvz+QMfsYQ=", - "engines": { - "iojs": ">= 1.0.0", - "node": ">= 0.12.0" - } - }, - "node_modules/co-body": { - "version": "6.1.0", - "resolved": "https://registry.npmjs.org/co-body/-/co-body-6.1.0.tgz", - "integrity": "sha512-m7pOT6CdLN7FuXUcpuz/8lfQ/L77x8SchHCF4G0RBTJO20Wzmhn5Sp4/5WsKy8OSpifBSUrmg83qEqaDHdyFuQ==", - "dependencies": { - "inflation": "^2.0.0", - "qs": "^6.5.2", - "raw-body": "^2.3.3", - "type-is": "^1.6.16" - } - }, - "node_modules/code-point-at": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/code-point-at/-/code-point-at-1.1.0.tgz", - "integrity": "sha1-DQcLTQQ6W+ozovGkDi7bPZpMz3c=", - "dev": true, - "engines": { - "node": ">=0.10.0" - } - }, - "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/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==", - "dev": true, - "bin": { - "color-support": "bin.js" - } - }, - "node_modules/colorette": { - "version": "2.0.16", - "resolved": "https://registry.npmjs.org/colorette/-/colorette-2.0.16.tgz", - "integrity": "sha512-hUewv7oMjCp+wkBv5Rm0v87eJhq4woh5rSR+42YSQJKecCqgIqNkZ6lAlQms/BwHPJA5NKMRlpxPRv0n8HQW6g==" - }, - "node_modules/colors": { - "version": "1.0.3", - "resolved": "https://registry.npmjs.org/colors/-/colors-1.0.3.tgz", - "integrity": "sha1-BDP0TYCWgP3rYO0mDxsMJi6CpAs=", - "dev": true, - "engines": { - "node": ">=0.1.90" - } - }, - "node_modules/columnify": { - "version": "1.5.4", - "resolved": "https://registry.npmjs.org/columnify/-/columnify-1.5.4.tgz", - "integrity": "sha1-Rzfd8ce2mop8NAVweC6UfuyOeLs=", - "dev": true, - "dependencies": { - "strip-ansi": "^3.0.0", - "wcwidth": "^1.0.0" - } - }, - "node_modules/columnify/node_modules/ansi-regex": { - "version": "2.1.1", - "resolved": "https://registry.npmjs.org/ansi-regex/-/ansi-regex-2.1.1.tgz", - "integrity": "sha1-w7M6te42DYbg5ijwRorn7yfWVN8=", - "dev": true, - "engines": { - "node": ">=0.10.0" - } - }, - "node_modules/columnify/node_modules/strip-ansi": { - "version": "3.0.1", - "resolved": "https://registry.npmjs.org/strip-ansi/-/strip-ansi-3.0.1.tgz", - "integrity": "sha1-ajhfuIU9lS1f8F0Oiq+UJ43GPc8=", - "dev": true, - "dependencies": { - "ansi-regex": "^2.0.0" - }, - "engines": { - "node": ">=0.10.0" - } - }, - "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==", - "dependencies": { - "delayed-stream": "~1.0.0" - }, - "engines": { - "node": ">= 0.8" - } - }, - "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": "sha1-3dgA2gxmEnOTzKWVDqloo6rxJTs=" - }, - "node_modules/compare-func": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/compare-func/-/compare-func-2.0.0.tgz", - "integrity": "sha512-zHig5N+tPWARooBnb0Zx1MFcdfpyJrfTJ3Y5L+IFvUm8rM74hHz66z0gw0x4tijh5CorKkKUCnW82R2vmpeCRA==", - "dev": true, - "dependencies": { - "array-ify": "^1.0.0", - "dot-prop": "^5.1.0" - } - }, - "node_modules/compare-func/node_modules/dot-prop": { - "version": "5.3.0", - "resolved": "https://registry.npmjs.org/dot-prop/-/dot-prop-5.3.0.tgz", - "integrity": "sha512-QM8q3zDe58hqUqjraQOmzZ1LIH9SWQJTlEKCH4kJ2oQvLZk7RbQXvtDM2XEq3fwkV9CCvvH4LA0AV+ogFsBM2Q==", - "dev": true, - "dependencies": { - "is-obj": "^2.0.0" - }, - "engines": { - "node": ">=8" - } - }, - "node_modules/complain": { - "version": "1.6.0", - "resolved": "https://registry.npmjs.org/complain/-/complain-1.6.0.tgz", - "integrity": "sha512-9oBfSEfxveaNmo2eSp/vEPkaBVxUhiJTZVgGYayzBchSAXQM6CK1PAQeV5ICShnSgfT+biYzrN7egKwwX+HkCw==", - "dependencies": { - "error-stack-parser": "^2.0.1" - } - }, - "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==" - }, - "node_modules/concat-map": { - "version": "0.0.1", - "resolved": "https://registry.npmjs.org/concat-map/-/concat-map-0.0.1.tgz", - "integrity": "sha1-2Klr13/Wjfd5OnMDajug1UBdR3s=" - }, - "node_modules/concat-stream": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/concat-stream/-/concat-stream-2.0.0.tgz", - "integrity": "sha512-MWufYdFw53ccGjCA+Ol7XJYpAlW6/prSMzuPOTRnJGcGzuhLn4Scrz7qf6o8bROZ514ltazcIFJZevcfbo0x7A==", - "dev": true, - "engines": [ - "node >= 6.0" - ], - "dependencies": { - "buffer-from": "^1.0.0", - "inherits": "^2.0.3", - "readable-stream": "^3.0.2", - "typedarray": "^0.0.6" - } - }, - "node_modules/config": { - "version": "3.3.6", - "resolved": "https://registry.npmjs.org/config/-/config-3.3.6.tgz", - "integrity": "sha512-Hj5916C5HFawjYJat1epbyY2PlAgLpBtDUlr0MxGLgo3p5+7kylyvnRY18PqJHgnNWXcdd0eWDemT7eYWuFgwg==", - "dependencies": { - "json5": "^2.1.1" - }, - "engines": { - "node": ">= 10.0.0" - } - }, - "node_modules/config-chain": { - "version": "1.1.13", - "resolved": "https://registry.npmjs.org/config-chain/-/config-chain-1.1.13.tgz", - "integrity": "sha512-qj+f8APARXHrM0hraqXYb2/bOVSV4PvJQlNZ/DVj0QrmNM2q2euizkeuVckQ57J+W0mRH6Hvi+k50M4Jul2VRQ==", - "dev": true, - "dependencies": { - "ini": "^1.3.4", - "proto-list": "~1.2.1" - } - }, - "node_modules/configstore": { - "version": "5.0.1", - "resolved": "https://registry.npmjs.org/configstore/-/configstore-5.0.1.tgz", - "integrity": "sha512-aMKprgk5YhBNyH25hj8wGt2+D52Sw1DRRIzqBwLp2Ya9mFmY8KPvvtvmna8SxVR9JMZ4kzMD68N22vlaRpkeFA==", - "dev": true, - "dependencies": { - "dot-prop": "^5.2.0", - "graceful-fs": "^4.1.2", - "make-dir": "^3.0.0", - "unique-string": "^2.0.0", - "write-file-atomic": "^3.0.0", - "xdg-basedir": "^4.0.0" - }, - "engines": { - "node": ">=8" - } - }, - "node_modules/configstore/node_modules/dot-prop": { - "version": "5.3.0", - "resolved": "https://registry.npmjs.org/dot-prop/-/dot-prop-5.3.0.tgz", - "integrity": "sha512-QM8q3zDe58hqUqjraQOmzZ1LIH9SWQJTlEKCH4kJ2oQvLZk7RbQXvtDM2XEq3fwkV9CCvvH4LA0AV+ogFsBM2Q==", - "dev": true, - "dependencies": { - "is-obj": "^2.0.0" - }, - "engines": { - "node": ">=8" - } - }, - "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": "sha1-PXz0Rk22RG6mRL9LOVB/mFEAjo4=", - "dev": true - }, - "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-disposition/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/content-type": { - "version": "1.0.4", - "resolved": "https://registry.npmjs.org/content-type/-/content-type-1.0.4.tgz", - "integrity": "sha512-hIP3EEPs8tB9AT1L+NUqtwOAps4mk2Zob89MWXMHjHWg9milF/j4osnnQLXBCBFBk/tvIG/tUc9mOUJiPBhPXA==", - "engines": { - "node": ">= 0.6" - } - }, - "node_modules/conventional-changelog-angular": { - "version": "5.0.13", - "resolved": "https://registry.npmjs.org/conventional-changelog-angular/-/conventional-changelog-angular-5.0.13.tgz", - "integrity": "sha512-i/gipMxs7s8L/QeuavPF2hLnJgH6pEZAttySB6aiQLWcX3puWDL3ACVmvBhJGxnAy52Qc15ua26BufY6KpmrVA==", - "dev": true, - "dependencies": { - "compare-func": "^2.0.0", - "q": "^1.5.1" - }, - "engines": { - "node": ">=10" - } - }, - "node_modules/conventional-changelog-core": { - "version": "4.2.4", - "resolved": "https://registry.npmjs.org/conventional-changelog-core/-/conventional-changelog-core-4.2.4.tgz", - "integrity": "sha512-gDVS+zVJHE2v4SLc6B0sLsPiloR0ygU7HaDW14aNJE1v4SlqJPILPl/aJC7YdtRE4CybBf8gDwObBvKha8Xlyg==", - "dev": true, - "dependencies": { - "add-stream": "^1.0.0", - "conventional-changelog-writer": "^5.0.0", - "conventional-commits-parser": "^3.2.0", - "dateformat": "^3.0.0", - "get-pkg-repo": "^4.0.0", - "git-raw-commits": "^2.0.8", - "git-remote-origin-url": "^2.0.0", - "git-semver-tags": "^4.1.1", - "lodash": "^4.17.15", - "normalize-package-data": "^3.0.0", - "q": "^1.5.1", - "read-pkg": "^3.0.0", - "read-pkg-up": "^3.0.0", - "through2": "^4.0.0" - }, - "engines": { - "node": ">=10" - } - }, - "node_modules/conventional-changelog-preset-loader": { - "version": "2.3.4", - "resolved": "https://registry.npmjs.org/conventional-changelog-preset-loader/-/conventional-changelog-preset-loader-2.3.4.tgz", - "integrity": "sha512-GEKRWkrSAZeTq5+YjUZOYxdHq+ci4dNwHvpaBC3+ENalzFWuCWa9EZXSuZBpkr72sMdKB+1fyDV4takK1Lf58g==", - "dev": true, - "engines": { - "node": ">=10" - } - }, - "node_modules/conventional-changelog-writer": { - "version": "5.0.1", - "resolved": "https://registry.npmjs.org/conventional-changelog-writer/-/conventional-changelog-writer-5.0.1.tgz", - "integrity": "sha512-5WsuKUfxW7suLblAbFnxAcrvf6r+0b7GvNaWUwUIk0bXMnENP/PEieGKVUQrjPqwPT4o3EPAASBXiY6iHooLOQ==", - "dev": true, - "dependencies": { - "conventional-commits-filter": "^2.0.7", - "dateformat": "^3.0.0", - "handlebars": "^4.7.7", - "json-stringify-safe": "^5.0.1", - "lodash": "^4.17.15", - "meow": "^8.0.0", - "semver": "^6.0.0", - "split": "^1.0.0", - "through2": "^4.0.0" - }, - "bin": { - "conventional-changelog-writer": "cli.js" - }, - "engines": { - "node": ">=10" - } - }, - "node_modules/conventional-changelog-writer/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/conventional-commits-filter": { - "version": "2.0.7", - "resolved": "https://registry.npmjs.org/conventional-commits-filter/-/conventional-commits-filter-2.0.7.tgz", - "integrity": "sha512-ASS9SamOP4TbCClsRHxIHXRfcGCnIoQqkvAzCSbZzTFLfcTqJVugB0agRgsEELsqaeWgsXv513eS116wnlSSPA==", - "dev": true, - "dependencies": { - "lodash.ismatch": "^4.4.0", - "modify-values": "^1.0.0" - }, - "engines": { - "node": ">=10" - } - }, - "node_modules/conventional-commits-parser": { - "version": "3.2.4", - "resolved": "https://registry.npmjs.org/conventional-commits-parser/-/conventional-commits-parser-3.2.4.tgz", - "integrity": "sha512-nK7sAtfi+QXbxHCYfhpZsfRtaitZLIA6889kFIouLvz6repszQDgxBu7wf2WbU+Dco7sAnNCJYERCwt54WPC2Q==", - "dev": true, - "dependencies": { - "is-text-path": "^1.0.1", - "JSONStream": "^1.0.4", - "lodash": "^4.17.15", - "meow": "^8.0.0", - "split2": "^3.0.0", - "through2": "^4.0.0" - }, - "bin": { - "conventional-commits-parser": "cli.js" - }, - "engines": { - "node": ">=10" - } - }, - "node_modules/conventional-recommended-bump": { - "version": "6.1.0", - "resolved": "https://registry.npmjs.org/conventional-recommended-bump/-/conventional-recommended-bump-6.1.0.tgz", - "integrity": "sha512-uiApbSiNGM/kkdL9GTOLAqC4hbptObFo4wW2QRyHsKciGAfQuLU1ShZ1BIVI/+K2BE/W1AWYQMCXAsv4dyKPaw==", - "dev": true, - "dependencies": { - "concat-stream": "^2.0.0", - "conventional-changelog-preset-loader": "^2.3.4", - "conventional-commits-filter": "^2.0.7", - "conventional-commits-parser": "^3.2.0", - "git-raw-commits": "^2.0.8", - "git-semver-tags": "^4.1.1", - "meow": "^8.0.0", - "q": "^1.5.1" - }, - "bin": { - "conventional-recommended-bump": "cli.js" - }, - "engines": { - "node": ">=10" - } - }, - "node_modules/convert-source-map": { - "version": "1.8.0", - "resolved": "https://registry.npmjs.org/convert-source-map/-/convert-source-map-1.8.0.tgz", - "integrity": "sha512-+OQdjP49zViI/6i7nIJpA8rAl4sV/JdPfU9nZs3VqOwGIgizICvuN2ru6fMd+4llL0tar18UYJXfZ/TWtmhUjA==", - "dependencies": { - "safe-buffer": "~5.1.1" - } - }, - "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", - "integrity": "sha1-4wOogrNCzD7oylE6eZmXNNqzriw=" - }, - "node_modules/cookiejar": { - "version": "2.1.3", - "resolved": "https://registry.npmjs.org/cookiejar/-/cookiejar-2.1.3.tgz", - "integrity": "sha512-JxbCBUdrfr6AQjOXrxoTvAMJO4HBTUIlBzslcJPAz+/KT8yk53fXun51u+RenNYvad/+Vc2DIz5o9UxlCDymFQ==" - }, - "node_modules/cookies": { - "version": "0.8.0", - "resolved": "https://registry.npmjs.org/cookies/-/cookies-0.8.0.tgz", - "integrity": "sha512-8aPsApQfebXnuI+537McwYsDtjVxGm8gTIzQI3FDW6t5t/DAhERxtnbEPN/8RX+uZthoz4eCOgloXaE5cYyNow==", - "dependencies": { - "depd": "~2.0.0", - "keygrip": "~1.1.0" - }, - "engines": { - "node": ">= 0.8" - } - }, - "node_modules/cookies/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/copy-to": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/copy-to/-/copy-to-2.0.1.tgz", - "integrity": "sha1-JoD7uAaKSNCGVrYJgJK9r8kG9KU=" - }, - "node_modules/core-js": { - "version": "2.6.12", - "resolved": "https://registry.npmjs.org/core-js/-/core-js-2.6.12.tgz", - "integrity": "sha512-Kb2wC0fvsWfQrgk8HU5lW6U/Lcs8+9aaYcy4ZFc6DDlo4nZ7n70dEgE5rtR0oG6ufKDUnrwfWL1mXR5ljDatrQ==", - "deprecated": "core-js@<3.4 is no longer maintained and not recommended for usage due to the number of issues. Because of the V8 engine whims, feature detection in old core-js versions could cause a slowdown up to 100x even if nothing is polyfilled. Please, upgrade your dependencies to the actual version of core-js.", - "hasInstallScript": true - }, - "node_modules/core-js-compat": { - "version": "3.20.2", - "resolved": "https://registry.npmjs.org/core-js-compat/-/core-js-compat-3.20.2.tgz", - "integrity": "sha512-qZEzVQ+5Qh6cROaTPFLNS4lkvQ6mBzE3R6A6EEpssj7Zr2egMHgsy4XapdifqJDGC9CBiNv7s+ejI96rLNQFdg==", - "dependencies": { - "browserslist": "^4.19.1", - "semver": "7.0.0" - }, - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/core-js" - } - }, - "node_modules/core-js-compat/node_modules/semver": { - "version": "7.0.0", - "resolved": "https://registry.npmjs.org/semver/-/semver-7.0.0.tgz", - "integrity": "sha512-+GB6zVA9LWh6zovYQLALHwv5rb2PHGlJi3lfiqIHxR0uuwCgefcOJc59v9fv1w8GbStwxuuqqAjI9NMAOOgq1A==", - "bin": { - "semver": "bin/semver.js" - } - }, - "node_modules/core-util-is": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/core-util-is/-/core-util-is-1.0.2.tgz", - "integrity": "sha1-tf1UIgqivFq1eqtxQMlAdUUDwac=" - }, - "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.0.1", - "resolved": "https://registry.npmjs.org/cosmiconfig/-/cosmiconfig-7.0.1.tgz", - "integrity": "sha512-a1YWNUV2HwGimB7dU2s1wUMurNKjpx60HxBB6xUM8Re+2s1g1IIfJvFR0/iCF+XHdE0GMTKTuLR32UQff4TEyQ==", - "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==" - }, - "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==", - "dependencies": { - "path-key": "^3.1.0", - "shebang-command": "^2.0.0", - "which": "^2.0.1" - }, - "engines": { - "node": ">= 8" - } - }, - "node_modules/crypto-random-string": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/crypto-random-string/-/crypto-random-string-2.0.0.tgz", - "integrity": "sha512-v1plID3y9r/lPhviJ1wrXpLeyUIGAZ2SHNYTEapm7/8A9nLPoyvVp3RK/EPFqn5kEznyWgYZNsRtYYIWbuG8KA==", - "dev": true, - "engines": { - "node": ">=8" - } - }, - "node_modules/dargs": { - "version": "7.0.0", - "resolved": "https://registry.npmjs.org/dargs/-/dargs-7.0.0.tgz", - "integrity": "sha512-2iy1EkLdlBzQGvbweYRFxmFath8+K7+AKB0TlhHWkNuH+TmovaMH/Wp7V7R4u7f4SnX3OgLsU9t1NI9ioDnUpg==", - "dev": true, - "engines": { - "node": ">=8" - } - }, - "node_modules/dashdash": { - "version": "1.14.1", - "resolved": "https://registry.npmjs.org/dashdash/-/dashdash-1.14.1.tgz", - "integrity": "sha1-hTz6D3y+L+1d4gMmuN1YEDX24vA=", - "dev": true, - "dependencies": { - "assert-plus": "^1.0.0" - }, - "engines": { - "node": ">=0.10" - } - }, - "node_modules/dateformat": { - "version": "3.0.3", - "resolved": "https://registry.npmjs.org/dateformat/-/dateformat-3.0.3.tgz", - "integrity": "sha512-jyCETtSl3VMZMWeRo7iY1FL19ges1t55hMo5yaam4Jrsm5EPL89UQkoQRyiI+Yf4k8r2ZpdngkV8hr1lIdjb3Q==", - "dev": true, - "engines": { - "node": "*" - } - }, - "node_modules/debug": { - "version": "4.3.3", - "resolved": "https://registry.npmjs.org/debug/-/debug-4.3.3.tgz", - "integrity": "sha512-/zxw5+vh1Tfv+4Qn7a5nsbcJKPaSvCDhojn6FEl9vupwK2VCSDtEiEtqr8DFtzYFOdz63LBkxec7DYuc2jon6Q==", - "dependencies": { - "ms": "2.1.2" - }, - "engines": { - "node": ">=6.0" - }, - "peerDependenciesMeta": { - "supports-color": { - "optional": true - } - } - }, - "node_modules/debuglog": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/debuglog/-/debuglog-1.0.1.tgz", - "integrity": "sha1-qiT/uaw9+aI1GDfPstJ5NgzXhJI=", - "dev": true, - "engines": { - "node": "*" - } - }, - "node_modules/decamelize": { - "version": "1.2.0", - "resolved": "https://registry.npmjs.org/decamelize/-/decamelize-1.2.0.tgz", - "integrity": "sha1-9lNNFRSCabIDUue+4m9QH5oZEpA=", - "engines": { - "node": ">=0.10.0" - } - }, - "node_modules/decamelize-keys": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/decamelize-keys/-/decamelize-keys-1.1.0.tgz", - "integrity": "sha1-0XGoeTMlKAfrPLYdwcFEXQeN8tk=", - "dev": true, - "dependencies": { - "decamelize": "^1.1.0", - "map-obj": "^1.0.0" - }, - "engines": { - "node": ">=0.10.0" - } - }, - "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": "sha1-2TPOuSBdgr3PSIb2dCvcK03qFG0=", - "dev": true, - "engines": { - "node": ">=0.10.0" - } - }, - "node_modules/decode-uri-component": { - "version": "0.2.0", - "resolved": "https://registry.npmjs.org/decode-uri-component/-/decode-uri-component-0.2.0.tgz", - "integrity": "sha1-6zkTMzRYd1y4TNGh+uBiEGu4dUU=", - "dev": true, - "engines": { - "node": ">=0.10" - } - }, - "node_modules/decompress-response": { - "version": "3.3.0", - "resolved": "https://registry.npmjs.org/decompress-response/-/decompress-response-3.3.0.tgz", - "integrity": "sha1-gKTdMjdIOEv6JICDYirt7Jgq3/M=", - "dev": true, - "dependencies": { - "mimic-response": "^1.0.0" - }, - "engines": { - "node": ">=4" - } - }, - "node_modules/dedent": { - "version": "0.7.0", - "resolved": "https://registry.npmjs.org/dedent/-/dedent-0.7.0.tgz", - "integrity": "sha1-JJXduvbrh0q7Dhvp3yLS5aVEMmw=", - "dev": true - }, - "node_modules/deep-eql": { - "version": "0.1.3", - "resolved": "https://registry.npmjs.org/deep-eql/-/deep-eql-0.1.3.tgz", - "integrity": "sha1-71WKyrjeJSBs1xOQbXTlaTDrafI=", - "dependencies": { - "type-detect": "0.1.1" - }, - "engines": { - "node": "*" - } - }, - "node_modules/deep-eql/node_modules/type-detect": { - "version": "0.1.1", - "resolved": "https://registry.npmjs.org/type-detect/-/type-detect-0.1.1.tgz", - "integrity": "sha1-C6XsKohWQORw6k6FBZcZANrFiCI=", - "engines": { - "node": "*" - } - }, - "node_modules/deep-equal": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/deep-equal/-/deep-equal-1.0.1.tgz", - "integrity": "sha1-9dJgKStmDghO/0zbyfCK0yR0SLU=" - }, - "node_modules/deep-extend": { - "version": "0.6.0", - "resolved": "https://registry.npmjs.org/deep-extend/-/deep-extend-0.6.0.tgz", - "integrity": "sha512-LOHxIOaPYdHlJRtCQfDIVZtfw/ufM8+rVj649RIHzcm/vGwQRXFt6OPqIFWsm2XEMrNIEtWR64sY1LEKD2vAOA==", - "dev": true, - "engines": { - "node": ">=4.0.0" - } - }, - "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==" - }, - "node_modules/default-require-extensions": { - "version": "3.0.0", - "resolved": "https://registry.npmjs.org/default-require-extensions/-/default-require-extensions-3.0.0.tgz", - "integrity": "sha512-ek6DpXq/SCpvjhpFsLFRVtIxJCRw6fUR42lYMVZuUMK7n8eMz4Uh5clckdBjEpLhn/gEBZo7hDJnJcwdKLKQjg==", - "dev": true, - "dependencies": { - "strip-bom": "^4.0.0" - }, - "engines": { - "node": ">=8" - } - }, - "node_modules/defaults": { - "version": "1.0.3", - "resolved": "https://registry.npmjs.org/defaults/-/defaults-1.0.3.tgz", - "integrity": "sha1-xlYFHpgX2f8I7YgUd/P+QBnz730=", - "dev": true, - "dependencies": { - "clone": "^1.0.2" - } - }, - "node_modules/defer-to-connect": { - "version": "1.1.3", - "resolved": "https://registry.npmjs.org/defer-to-connect/-/defer-to-connect-1.1.3.tgz", - "integrity": "sha512-0ISdNousHvZT2EiFlZeZAHBUvSxmKswVCEf8hW7KWgG4a8MVEu/3Vb6uWYozkjylyCxe0JBIiRB1jV45S70WVQ==", - "dev": true - }, - "node_modules/define-properties": { - "version": "1.1.3", - "resolved": "https://registry.npmjs.org/define-properties/-/define-properties-1.1.3.tgz", - "integrity": "sha512-3MqfYKj2lLzdMSf8ZIZE/V+Zuy+BgD6f164e8K2w7dgnpKArBDerGYpM46IYYcjnkdPNMjPk9A6VFB8+3SKlXQ==", - "dependencies": { - "object-keys": "^1.0.12" - }, - "engines": { - "node": ">= 0.4" - } - }, - "node_modules/delayed-stream": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/delayed-stream/-/delayed-stream-1.0.0.tgz", - "integrity": "sha1-3zrhmayt+31ECqrgsp4icrJOxhk=", - "engines": { - "node": ">=0.4.0" - } - }, - "node_modules/delegates": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/delegates/-/delegates-1.0.0.tgz", - "integrity": "sha1-hMbhWbgZBP3KWaDvRM2HDTElD5o=" - }, - "node_modules/denque": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/denque/-/denque-2.0.1.tgz", - "integrity": "sha512-tfiWc6BQLXNLpNiR5iGd0Ocu3P3VpxfzFiqubLgMfhfOw9WyvgJBd46CClNn9k3qfbjvT//0cf7AlYRX/OslMQ==", - "engines": { - "node": ">=0.10" - } - }, - "node_modules/depd": { - "version": "1.1.2", - "resolved": "https://registry.npmjs.org/depd/-/depd-1.1.2.tgz", - "integrity": "sha1-m81S4UwJd2PnSbJ0xDRu0uVgtak=", - "engines": { - "node": ">= 0.6" - } - }, - "node_modules/deprecation": { - "version": "2.3.1", - "resolved": "https://registry.npmjs.org/deprecation/-/deprecation-2.3.1.tgz", - "integrity": "sha512-xmHIy4F3scKVwMsQ4WnVaS8bHOx0DmVwRywosKhaILI0ywMDWPtBSku2HNxRvF7jtwDRsoEwYQSfbxj8b7RlJQ==", - "dev": true - }, - "node_modules/deresolve": { - "version": "1.1.2", - "resolved": "https://registry.npmjs.org/deresolve/-/deresolve-1.1.2.tgz", - "integrity": "sha1-nPI3nI0tYx3EuZVylLkOSnLLbOA=", - "dependencies": { - "lasso-package-root": "^1.0.0", - "raptor-polyfill": "^1.0.2", - "resolve-from": "^1.0.1" - } - }, - "node_modules/deresolve/node_modules/resolve-from": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/resolve-from/-/resolve-from-1.0.1.tgz", - "integrity": "sha1-Jsv+k10a7uq7Kbw/5a6wHpPUQiY=", - "engines": { - "node": ">=0.10.0" - } - }, - "node_modules/destroy": { - "version": "1.0.4", - "resolved": "https://registry.npmjs.org/destroy/-/destroy-1.0.4.tgz", - "integrity": "sha1-l4hXRCxEdJ5CBmE+N5RiBYJqvYA=" - }, - "node_modules/detect-indent": { - "version": "6.1.0", - "resolved": "https://registry.npmjs.org/detect-indent/-/detect-indent-6.1.0.tgz", - "integrity": "sha512-reYkTUJAZb9gUuZ2RvVCNhVHdg62RHnJ7WJl8ftMi4diZ6NWlciOzQN88pUhSELEwflJht4oQDv0F0BMlwaYtA==", - "dev": true, - "engines": { - "node": ">=8" - } - }, - "node_modules/dezalgo": { - "version": "1.0.3", - "resolved": "https://registry.npmjs.org/dezalgo/-/dezalgo-1.0.3.tgz", - "integrity": "sha1-f3Qt4Gb8dIvI24IFad3c5Jvw1FY=", - "dev": true, - "dependencies": { - "asap": "^2.0.0", - "wrappy": "1" - } - }, - "node_modules/diff": { - "version": "5.0.0", - "resolved": "https://registry.npmjs.org/diff/-/diff-5.0.0.tgz", - "integrity": "sha512-/VTCrvm5Z0JGty/BWHljh+BAiw3IK+2j87NGMu8Nwc/f48WoDAC395uomO9ZD117ZOBaHmkX1oyLvkVM/aIT3w==", - "engines": { - "node": ">=0.3.1" - } - }, - "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/dissolve": { - "version": "0.3.3", - "resolved": "https://registry.npmjs.org/dissolve/-/dissolve-0.3.3.tgz", - "integrity": "sha1-uX7x/ymJx4nOz7AxB+F0EfqL5uU=", - "dependencies": { - "bl": "^0.7.0", - "readable-stream": "^1.0.26" - }, - "engines": { - "node": "~0.10.0" - } - }, - "node_modules/dissolve/node_modules/isarray": { - "version": "0.0.1", - "resolved": "https://registry.npmjs.org/isarray/-/isarray-0.0.1.tgz", - "integrity": "sha1-ihis/Kmo9Bd+Cav8YDiTmwXR7t8=" - }, - "node_modules/dissolve/node_modules/readable-stream": { - "version": "1.1.14", - "resolved": "https://registry.npmjs.org/readable-stream/-/readable-stream-1.1.14.tgz", - "integrity": "sha1-fPTFTvZI44EwhMY23SB54WbAgdk=", - "dependencies": { - "core-util-is": "~1.0.0", - "inherits": "~2.0.1", - "isarray": "0.0.1", - "string_decoder": "~0.10.x" - } - }, - "node_modules/dissolve/node_modules/string_decoder": { - "version": "0.10.31", - "resolved": "https://registry.npmjs.org/string_decoder/-/string_decoder-0.10.31.tgz", - "integrity": "sha1-YuIDvEF2bGwoyfyEMB2rHFMQ+pQ=" - }, - "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/dot-prop": { - "version": "6.0.1", - "resolved": "https://registry.npmjs.org/dot-prop/-/dot-prop-6.0.1.tgz", - "integrity": "sha512-tE7ztYzXHIeyvc7N+hR3oi7FIbf/NIjVP9hmAt3yMXzrQ072/fpjGLx2GxNxGxUl5V73MEqYzioOMoVhGMJ5cA==", - "dev": true, - "dependencies": { - "is-obj": "^2.0.0" - }, - "engines": { - "node": ">=10" - }, - "funding": { - "url": "https://github.com/sponsors/sindresorhus" - } - }, - "node_modules/duplexer": { - "version": "0.1.2", - "resolved": "https://registry.npmjs.org/duplexer/-/duplexer-0.1.2.tgz", - "integrity": "sha512-jtD6YG370ZCIi/9GTaJKQxWTZD045+4R4hTk/x1UyoqadyJ9x9CgSi1RlVDQF8U2sxLLSnFkCaMihqljHIWgMg==", - "dev": true - }, - "node_modules/duplexer3": { - "version": "0.1.4", - "resolved": "https://registry.npmjs.org/duplexer3/-/duplexer3-0.1.4.tgz", - "integrity": "sha1-7gHdHKwO08vH/b6jfcCo8c4ALOI=", - "dev": true - }, - "node_modules/ecc-jsbn": { - "version": "0.1.2", - "resolved": "https://registry.npmjs.org/ecc-jsbn/-/ecc-jsbn-0.1.2.tgz", - "integrity": "sha1-OoOpBOVDUyh4dMVkt1SThoSamMk=", - "dev": true, - "dependencies": { - "jsbn": "~0.1.0", - "safer-buffer": "^2.1.0" - } - }, - "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", - "integrity": "sha1-WQxhFWsK4vTwJVcyoViyZrxWsh0=" - }, - "node_modules/electron-to-chromium": { - "version": "1.4.32", - "resolved": "https://registry.npmjs.org/electron-to-chromium/-/electron-to-chromium-1.4.32.tgz", - "integrity": "sha512-7QRVfMlccTFs7cZV3lB0k9Wcm6R6F+w1yBPX+xBAlAP/1oJIstxTev3A4r8REnUUAFph/cIB8y/EBU7PDbJTQw==" - }, - "node_modules/elliptic": { - "version": "6.5.4", - "resolved": "https://registry.npmjs.org/elliptic/-/elliptic-6.5.4.tgz", - "integrity": "sha512-iLhC6ULemrljPZb+QutR5TQGB+pdW6KGD5RSegS+8sorOZT+rdQFbsQFJgvN3eRqNALqJer4oQ16YvJHlU8hzQ==", - "optional": true, - "dependencies": { - "bn.js": "^4.11.9", - "brorand": "^1.1.0", - "hash.js": "^1.0.0", - "hmac-drbg": "^1.0.1", - "inherits": "^2.0.4", - "minimalistic-assert": "^1.0.1", - "minimalistic-crypto-utils": "^1.0.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==" - }, - "node_modules/emojis-list": { - "version": "3.0.0", - "resolved": "https://registry.npmjs.org/emojis-list/-/emojis-list-3.0.0.tgz", - "integrity": "sha512-/kyM18EfinwXZbno9FyUGeFh87KC8HRQBQGildHZbEuRyWFOmv1U10o9BBp8XVZDVNNuQKyIGIu5ZYAAXJ0V2Q==", - "engines": { - "node": ">= 4" - } - }, - "node_modules/encodeurl": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/encodeurl/-/encodeurl-1.0.2.tgz", - "integrity": "sha1-rT/0yG7C0CkyL1oCw6mmBslbP1k=", - "engines": { - "node": ">= 0.8" - } - }, - "node_modules/encoding": { - "version": "0.1.13", - "resolved": "https://registry.npmjs.org/encoding/-/encoding-0.1.13.tgz", - "integrity": "sha512-ETBauow1T35Y/WZMkio9jiM0Z5xjHHmJ4XmjZOq1l/dXz3lr2sRn87nJy20RupqSh1F2m3HHPSp8ShIPQJrJ3A==", - "dev": true, - "optional": true, - "dependencies": { - "iconv-lite": "^0.6.2" - } - }, - "node_modules/encoding/node_modules/iconv-lite": { - "version": "0.6.3", - "resolved": "https://registry.npmjs.org/iconv-lite/-/iconv-lite-0.6.3.tgz", - "integrity": "sha512-4fCk79wshMdzMp2rH06qWrJE4iolqLhCUH+OiuIgU++RB0+94NlDL81atO7GX55uUKueo0txHNtvEyI6D7WdMw==", - "dev": true, - "optional": true, - "dependencies": { - "safer-buffer": ">= 2.1.2 < 3.0.0" - }, - "engines": { - "node": ">=0.10.0" - } - }, - "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/engine.io": { - "version": "6.1.0", - "resolved": "https://registry.npmjs.org/engine.io/-/engine.io-6.1.0.tgz", - "integrity": "sha512-ErhZOVu2xweCjEfYcTdkCnEYUiZgkAcBBAhW4jbIvNG8SLU3orAqoJCiytZjYF7eTpVmmCrLDjLIEaPlUAs1uw==", - "dependencies": { - "@types/cookie": "^0.4.1", - "@types/cors": "^2.8.12", - "@types/node": ">=10.0.0", - "accepts": "~1.3.4", - "base64id": "2.0.0", - "cookie": "~0.4.1", - "cors": "~2.8.5", - "debug": "~4.3.1", - "engine.io-parser": "~5.0.0", - "ws": "~8.2.3" - }, - "engines": { - "node": ">=10.0.0" - } - }, - "node_modules/engine.io-client": { - "version": "6.1.1", - "resolved": "https://registry.npmjs.org/engine.io-client/-/engine.io-client-6.1.1.tgz", - "integrity": "sha512-V05mmDo4gjimYW+FGujoGmmmxRaDsrVr7AXA3ZIfa04MWM1jOfZfUwou0oNqhNwy/votUDvGDt4JA4QF4e0b4g==", - "dependencies": { - "@socket.io/component-emitter": "~3.0.0", - "debug": "~4.3.1", - "engine.io-parser": "~5.0.0", - "has-cors": "1.1.0", - "parseqs": "0.0.6", - "parseuri": "0.0.6", - "ws": "~8.2.3", - "xmlhttprequest-ssl": "~2.0.0", - "yeast": "0.1.2" - } - }, - "node_modules/engine.io-client/node_modules/ws": { - "version": "8.2.3", - "resolved": "https://registry.npmjs.org/ws/-/ws-8.2.3.tgz", - "integrity": "sha512-wBuoj1BDpC6ZQ1B7DWQBYVLphPWkm8i9Y0/3YdHjHKHiohOJ1ws+3OccDWtH+PoC9DZD5WOTrJvNbWvjS6JWaA==", - "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/engine.io-parser": { - "version": "5.0.2", - "resolved": "https://registry.npmjs.org/engine.io-parser/-/engine.io-parser-5.0.2.tgz", - "integrity": "sha512-wuiO7qO/OEkPJSFueuATIXtrxF7/6GTbAO9QLv7nnbjwZ5tYhLm9zxvLwxstRs0dcT0KUlWTjtIOs1T86jt12g==", - "dependencies": { - "base64-arraybuffer": "~1.0.1" - }, - "engines": { - "node": ">=10.0.0" - } - }, - "node_modules/engine.io/node_modules/ws": { - "version": "8.2.3", - "resolved": "https://registry.npmjs.org/ws/-/ws-8.2.3.tgz", - "integrity": "sha512-wBuoj1BDpC6ZQ1B7DWQBYVLphPWkm8i9Y0/3YdHjHKHiohOJ1ws+3OccDWtH+PoC9DZD5WOTrJvNbWvjS6JWaA==", - "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/enhanced-resolve": { - "version": "5.8.3", - "resolved": "https://registry.npmjs.org/enhanced-resolve/-/enhanced-resolve-5.8.3.tgz", - "integrity": "sha512-EGAbGvH7j7Xt2nc0E7D99La1OiEs8LnyimkRgwExpUMScN6O+3x9tIWs7PLQZVNx4YD+00skHXPXi1yQHpAmZA==", - "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/env-paths": { - "version": "2.2.1", - "resolved": "https://registry.npmjs.org/env-paths/-/env-paths-2.2.1.tgz", - "integrity": "sha512-+h1lkLKhZMTYjog1VEpJNG7NZJWcuc2DDk/qsqSTRRCOXiLjeQ1d1/udrUGhqMxUgAlwKNZ0cf2uqan5GLuS2A==", - "dev": true, - "engines": { - "node": ">=6" - } - }, - "node_modules/envinfo": { - "version": "7.8.1", - "resolved": "https://registry.npmjs.org/envinfo/-/envinfo-7.8.1.tgz", - "integrity": "sha512-/o+BXHmB7ocbHEAs6F2EnG0ogybVVUdkRunTT2glZU9XAaGmhqskrvKwqXuDfNjEO0LZKWdejEEpnq8aM0tOaw==", - "bin": { - "envinfo": "dist/cli.js" - }, - "engines": { - "node": ">=4" - } - }, - "node_modules/err-code": { - "version": "2.0.3", - "resolved": "https://registry.npmjs.org/err-code/-/err-code-2.0.3.tgz", - "integrity": "sha512-2bmlRpNKBxT/CRmPOlyISQpNj+qSeYvcym/uT0Jx2bMOlKLtSy1ZmLuVxSEKKyor/N5yhvp/ZiG1oE3DEYMSFA==", - "dev": true - }, - "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==", - "dependencies": { - "is-arrayish": "^0.2.1" - } - }, - "node_modules/error-stack-parser": { - "version": "2.0.6", - "resolved": "https://registry.npmjs.org/error-stack-parser/-/error-stack-parser-2.0.6.tgz", - "integrity": "sha512-d51brTeqC+BHlwF0BhPtcYgF5nlzf9ZZ0ZIUQNZpc9ZB9qw5IJ2diTrBY9jlCJkTLITYPjmiX6OWCwH+fuyNgQ==", - "dependencies": { - "stackframe": "^1.1.1" - } - }, - "node_modules/es-abstract": { - "version": "1.19.1", - "resolved": "https://registry.npmjs.org/es-abstract/-/es-abstract-1.19.1.tgz", - "integrity": "sha512-2vJ6tjA/UfqLm2MPs7jxVybLoB8i1t1Jd9R3kISld20sIxPcTbLuggQOUxeWeAvIUkduv/CfMjuh4WmiXr2v9w==", - "dev": true, - "dependencies": { - "call-bind": "^1.0.2", - "es-to-primitive": "^1.2.1", - "function-bind": "^1.1.1", - "get-intrinsic": "^1.1.1", - "get-symbol-description": "^1.0.0", - "has": "^1.0.3", - "has-symbols": "^1.0.2", - "internal-slot": "^1.0.3", - "is-callable": "^1.2.4", - "is-negative-zero": "^2.0.1", - "is-regex": "^1.1.4", - "is-shared-array-buffer": "^1.0.1", - "is-string": "^1.0.7", - "is-weakref": "^1.0.1", - "object-inspect": "^1.11.0", - "object-keys": "^1.1.1", - "object.assign": "^4.1.2", - "string.prototype.trimend": "^1.0.4", - "string.prototype.trimstart": "^1.0.4", - "unbox-primitive": "^1.0.1" - }, - "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==" - }, - "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/es6-error": { - "version": "4.1.1", - "resolved": "https://registry.npmjs.org/es6-error/-/es6-error-4.1.1.tgz", - "integrity": "sha512-Um/+FxMr9CISWh0bi5Zv0iOD+4cFh5qLeks1qhAopKVAJw3drgKbKySikp7wGhDL0HPeaja0P5ULZrxLkniUVg==", - "dev": true - }, - "node_modules/es6-promise": { - "version": "4.2.8", - "resolved": "https://registry.npmjs.org/es6-promise/-/es6-promise-4.2.8.tgz", - "integrity": "sha512-HJDGx5daxeIvxdBxvG2cb9g4tEvwIk3i8+nhX0yGrYmZUzbkdg8QbDevheDB8gd0//uPj4c1EQua8Q+MViT0/w==" - }, - "node_modules/es6-promisify": { - "version": "5.0.0", - "resolved": "https://registry.npmjs.org/es6-promisify/-/es6-promisify-5.0.0.tgz", - "integrity": "sha1-UQnWLz5W6pZ8S2NQWu8IKRyKUgM=", - "dependencies": { - "es6-promise": "^4.0.3" - } - }, - "node_modules/escalade": { - "version": "3.1.1", - "resolved": "https://registry.npmjs.org/escalade/-/escalade-3.1.1.tgz", - "integrity": "sha512-k0er2gUkLf8O0zKJiAhmkTnJlTvINGv7ygDNPbeIsX/TJjGJZHuh9B2UxbsaEkmlEo9MfhrSzmhIlhRlI2GXnw==", - "engines": { - "node": ">=6" - } - }, - "node_modules/escape-goat": { - "version": "2.1.1", - "resolved": "https://registry.npmjs.org/escape-goat/-/escape-goat-2.1.1.tgz", - "integrity": "sha512-8/uIhbG12Csjy2JEW7D9pHbreaVaS/OpN3ycnyvElTdwM5n6GY6W6e2IPemfvGZeUMqZ9A/3GqIZMgKnBhAw/Q==", - "dev": true, - "engines": { - "node": ">=8" - } - }, - "node_modules/escape-html": { - "version": "1.0.3", - "resolved": "https://registry.npmjs.org/escape-html/-/escape-html-1.0.3.tgz", - "integrity": "sha1-Aljq5NPQwJdN4cFpGI7wBR0dGYg=" - }, - "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==", - "engines": { - "node": ">=10" - }, - "funding": { - "url": "https://github.com/sponsors/sindresorhus" - } - }, - "node_modules/escodegen": { - "version": "1.14.3", - "resolved": "https://registry.npmjs.org/escodegen/-/escodegen-1.14.3.tgz", - "integrity": "sha512-qFcX0XJkdg+PB3xjZZG/wKSuT1PnQWx57+TVSjIMmILd2yC/6ByYElPwJnslDsuWuSAp4AwJGumarAAmJch5Kw==", - "dependencies": { - "esprima": "^4.0.1", - "estraverse": "^4.2.0", - "esutils": "^2.0.2", - "optionator": "^0.8.1" - }, - "bin": { - "escodegen": "bin/escodegen.js", - "esgenerate": "bin/esgenerate.js" - }, - "engines": { - "node": ">=4.0" - }, - "optionalDependencies": { - "source-map": "~0.6.1" - } - }, - "node_modules/escodegen/node_modules/levn": { - "version": "0.3.0", - "resolved": "https://registry.npmjs.org/levn/-/levn-0.3.0.tgz", - "integrity": "sha1-OwmSTt+fCDwEkP3UwLxEIeBHZO4=", - "dependencies": { - "prelude-ls": "~1.1.2", - "type-check": "~0.3.2" - }, - "engines": { - "node": ">= 0.8.0" - } - }, - "node_modules/escodegen/node_modules/optionator": { - "version": "0.8.3", - "resolved": "https://registry.npmjs.org/optionator/-/optionator-0.8.3.tgz", - "integrity": "sha512-+IW9pACdk3XWmmTXG8m3upGUJst5XRGzxMRjXzAuJ1XnIFNvfhjjIuYkDvysnPQ7qzqVzLt78BCruntqRhWQbA==", - "dependencies": { - "deep-is": "~0.1.3", - "fast-levenshtein": "~2.0.6", - "levn": "~0.3.0", - "prelude-ls": "~1.1.2", - "type-check": "~0.3.2", - "word-wrap": "~1.2.3" - }, - "engines": { - "node": ">= 0.8.0" - } - }, - "node_modules/escodegen/node_modules/prelude-ls": { - "version": "1.1.2", - "resolved": "https://registry.npmjs.org/prelude-ls/-/prelude-ls-1.1.2.tgz", - "integrity": "sha1-IZMqVJ9eUv/ZqCf1cOBL5iqX2lQ=", - "engines": { - "node": ">= 0.8.0" - } - }, - "node_modules/escodegen/node_modules/type-check": { - "version": "0.3.2", - "resolved": "https://registry.npmjs.org/type-check/-/type-check-0.3.2.tgz", - "integrity": "sha1-WITKtRLPHTVeP7eE8wgEsrUg23I=", - "dependencies": { - "prelude-ls": "~1.1.2" - }, - "engines": { - "node": ">= 0.8.0" - } - }, - "node_modules/eslint": { - "version": "8.6.0", - "resolved": "https://registry.npmjs.org/eslint/-/eslint-8.6.0.tgz", - "integrity": "sha512-UvxdOJ7mXFlw7iuHZA4jmzPaUqIw54mZrv+XPYKNbKdLR0et4rf60lIZUU9kiNtnzzMzGWxMV+tQ7uG7JG8DPw==", - "dev": true, - "dependencies": { - "@eslint/eslintrc": "^1.0.5", - "@humanwhocodes/config-array": "^0.9.2", - "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": "^7.1.0", - "eslint-utils": "^3.0.0", - "eslint-visitor-keys": "^3.1.0", - "espree": "^9.3.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-import-resolver-node": { - "version": "0.3.6", - "resolved": "https://registry.npmjs.org/eslint-import-resolver-node/-/eslint-import-resolver-node-0.3.6.tgz", - "integrity": "sha512-0En0w03NRVMn9Uiyn8YRPDKvWjxCWkslUEhGNTdGx15RvPJYQ+lbOlqrlNI2vEAs4pDYK4f/HN2TbDmk5TP0iw==", - "dev": true, - "dependencies": { - "debug": "^3.2.7", - "resolve": "^1.20.0" - } - }, - "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, - "dependencies": { - "ms": "^2.1.1" - } - }, - "node_modules/eslint-module-utils": { - "version": "2.7.2", - "resolved": "https://registry.npmjs.org/eslint-module-utils/-/eslint-module-utils-2.7.2.tgz", - "integrity": "sha512-zquepFnWCY2ISMFwD/DqzaM++H+7PDzOpUvotJWm/y1BAFt5R4oeULgdrTejKqLkz7MA/tgstsUMNYc7wNdTrg==", - "dev": true, - "dependencies": { - "debug": "^3.2.7", - "find-up": "^2.1.0" - }, - "engines": { - "node": ">=4" - } - }, - "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, - "dependencies": { - "ms": "^2.1.1" - } - }, - "node_modules/eslint-plugin-import": { - "version": "2.25.4", - "resolved": "https://registry.npmjs.org/eslint-plugin-import/-/eslint-plugin-import-2.25.4.tgz", - "integrity": "sha512-/KJBASVFxpu0xg1kIBn9AUa8hQVnszpwgE7Ld0lKAlx7Ie87yzEzCgSkekt+le/YVhiaosO4Y14GDAOc41nfxA==", - "dev": true, - "dependencies": { - "array-includes": "^3.1.4", - "array.prototype.flat": "^1.2.5", - "debug": "^2.6.9", - "doctrine": "^2.1.0", - "eslint-import-resolver-node": "^0.3.6", - "eslint-module-utils": "^2.7.2", - "has": "^1.0.3", - "is-core-module": "^2.8.0", - "is-glob": "^4.0.3", - "minimatch": "^3.0.4", - "object.values": "^1.1.5", - "resolve": "^1.20.0", - "tsconfig-paths": "^3.12.0" - }, - "engines": { - "node": ">=4" - }, - "peerDependencies": { - "eslint": "^2 || ^3 || ^4 || ^5 || ^6 || ^7.2.0 || ^8" - } - }, - "node_modules/eslint-plugin-import/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/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, - "dependencies": { - "esutils": "^2.0.2" - }, - "engines": { - "node": ">=0.10.0" - } - }, - "node_modules/eslint-plugin-import/node_modules/ms": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/ms/-/ms-2.0.0.tgz", - "integrity": "sha1-VgiurfwAvmwpAd9fmGF4jeDVl8g=", - "dev": true - }, - "node_modules/eslint-plugin-prefer-arrow": { - "version": "1.2.3", - "resolved": "https://registry.npmjs.org/eslint-plugin-prefer-arrow/-/eslint-plugin-prefer-arrow-1.2.3.tgz", - "integrity": "sha512-J9I5PKCOJretVuiZRGvPQxCbllxGAV/viI20JO3LYblAodofBxyMnZAJ+WGeClHgANnSJberTNoFWWjrWKBuXQ==", - "dev": true, - "peerDependencies": { - "eslint": ">=2.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==", - "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.1.0", - "resolved": "https://registry.npmjs.org/eslint-visitor-keys/-/eslint-visitor-keys-3.1.0.tgz", - "integrity": "sha512-yWJFpu4DtjsWKkt5GeNBBuZMlNcYVs6vRCLoCVEJrTjaSB6LC98gFipNK/erM2Heg/E8mIK+hXG/pJMLK+eRZA==", - "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/eslint-scope": { - "version": "7.1.0", - "resolved": "https://registry.npmjs.org/eslint-scope/-/eslint-scope-7.1.0.tgz", - "integrity": "sha512-aWwkhnS0qAXqNOgKOK0dJ2nvzEbhEvpy8OlJ9kZ0FeZnA6zpjv1/Vei+puGFFX7zkPCkHHXb7IDX3A+7yPrRWg==", - "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/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.3.0", - "resolved": "https://registry.npmjs.org/espree/-/espree-9.3.0.tgz", - "integrity": "sha512-d/5nCsb0JcqsSEeQzFZ8DH1RmxPcglRWh24EFTlUEmCKoehXGdpsx0RkHDubqUI8LSAIKMQp4r9SzQ3n+sm4HQ==", - "dev": true, - "dependencies": { - "acorn": "^8.7.0", - "acorn-jsx": "^5.3.1", - "eslint-visitor-keys": "^3.1.0" - }, - "engines": { - "node": "^12.22.0 || ^14.17.0 || >=16.0.0" - } - }, - "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==", - "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==", - "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==", - "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==", - "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==", - "engines": { - "node": ">=0.10.0" - } - }, - "node_modules/etag": { - "version": "1.8.1", - "resolved": "https://registry.npmjs.org/etag/-/etag-1.8.1.tgz", - "integrity": "sha1-Qa4u62XvpiJorr/qg6x9eSmbCIc=", - "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==", - "engines": { - "node": ">=0.8.x" - } - }, - "node_modules/events-light": { - "version": "1.0.5", - "resolved": "https://registry.npmjs.org/events-light/-/events-light-1.0.5.tgz", - "integrity": "sha1-lk5jRQugr0prAiqpVbF//vZXte4=", - "dependencies": { - "chai": "^3.5.0" - } - }, - "node_modules/execa": { - "version": "5.1.1", - "resolved": "https://registry.npmjs.org/execa/-/execa-5.1.1.tgz", - "integrity": "sha512-8uSpZZocAZRBAPIEINJj3Lo9HyGitllczc27Eh5YYojjMFMn8yHMDMaUHE2Jqfq05D/wucwI4JGURyXt1vchyg==", - "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/expand-brackets": { - "version": "0.1.5", - "resolved": "https://registry.npmjs.org/expand-brackets/-/expand-brackets-0.1.5.tgz", - "integrity": "sha1-3wcoTjQqgHzXM6xa9yQR5YHRF3s=", - "dependencies": { - "is-posix-bracket": "^0.1.0" - }, - "engines": { - "node": ">=0.10.0" - } - }, - "node_modules/expand-range": { - "version": "1.8.2", - "resolved": "https://registry.npmjs.org/expand-range/-/expand-range-1.8.2.tgz", - "integrity": "sha1-opnv/TNf4nIeuujiV+x5ZE/IUzc=", - "dependencies": { - "fill-range": "^2.1.0" - }, - "engines": { - "node": ">=0.10.0" - } - }, - "node_modules/expand-range/node_modules/fill-range": { - "version": "2.2.4", - "resolved": "https://registry.npmjs.org/fill-range/-/fill-range-2.2.4.tgz", - "integrity": "sha512-cnrcCbj01+j2gTG921VZPnHbjmdAf8oQV/iGeV2kZxGSyfYjjTyY79ErsK1WJWMpw6DaApEX72binqJE+/d+5Q==", - "dependencies": { - "is-number": "^2.1.0", - "isobject": "^2.0.0", - "randomatic": "^3.0.0", - "repeat-element": "^1.1.2", - "repeat-string": "^1.5.2" - }, - "engines": { - "node": ">=0.10.0" - } - }, - "node_modules/expand-range/node_modules/is-number": { - "version": "2.1.0", - "resolved": "https://registry.npmjs.org/is-number/-/is-number-2.1.0.tgz", - "integrity": "sha1-Afy7s5NGOlSPL0ZszhbezknbkI8=", - "dependencies": { - "kind-of": "^3.0.2" - }, - "engines": { - "node": ">=0.10.0" - } - }, - "node_modules/expand-range/node_modules/isobject": { - "version": "2.1.0", - "resolved": "https://registry.npmjs.org/isobject/-/isobject-2.1.0.tgz", - "integrity": "sha1-8GVWEJaj8dou9GJy+BXIQNh+DIk=", - "dependencies": { - "isarray": "1.0.0" - }, - "engines": { - "node": ">=0.10.0" - } - }, - "node_modules/expand-range/node_modules/kind-of": { - "version": "3.2.2", - "resolved": "https://registry.npmjs.org/kind-of/-/kind-of-3.2.2.tgz", - "integrity": "sha1-MeohpzS6ubuw8yRm2JOupR5KPGQ=", - "dependencies": { - "is-buffer": "^1.1.5" - }, - "engines": { - "node": ">=0.10.0" - } - }, - "node_modules/express": { - "version": "4.17.2", - "resolved": "https://registry.npmjs.org/express/-/express-4.17.2.tgz", - "integrity": "sha512-oxlxJxcQlYwqPWKVJJtvQiwHgosH/LrLSPA+H4UxpyvSS6jC5aH+5MoHFM+KABgTOt0APue4w66Ha8jCUo9QGg==", - "dependencies": { - "accepts": "~1.3.7", - "array-flatten": "1.1.1", - "body-parser": "1.19.1", - "content-disposition": "0.5.4", - "content-type": "~1.0.4", - "cookie": "0.4.1", - "cookie-signature": "1.0.6", - "debug": "2.6.9", - "depd": "~1.1.2", - "encodeurl": "~1.0.2", - "escape-html": "~1.0.3", - "etag": "~1.8.1", - "finalhandler": "~1.1.2", - "fresh": "0.5.2", - "merge-descriptors": "1.0.1", - "methods": "~1.1.2", - "on-finished": "~2.3.0", - "parseurl": "~1.3.3", - "path-to-regexp": "0.1.7", - "proxy-addr": "~2.0.7", - "qs": "6.9.6", - "range-parser": "~1.2.1", - "safe-buffer": "5.2.1", - "send": "0.17.2", - "serve-static": "1.14.2", - "setprototypeof": "1.2.0", - "statuses": "~1.5.0", - "type-is": "~1.6.18", - "utils-merge": "1.0.1", - "vary": "~1.1.2" - }, - "engines": { - "node": ">= 0.10.0" - } - }, - "node_modules/express-session": { - "version": "1.17.2", - "resolved": "https://registry.npmjs.org/express-session/-/express-session-1.17.2.tgz", - "integrity": "sha512-mPcYcLA0lvh7D4Oqr5aNJFMtBMKPLl++OKKxkHzZ0U0oDq1rpKBnkR5f5vCHR26VeArlTOEF9td4x5IjICksRQ==", - "dependencies": { - "cookie": "0.4.1", - "cookie-signature": "1.0.6", - "debug": "2.6.9", - "depd": "~2.0.0", - "on-headers": "~1.0.2", - "parseurl": "~1.3.3", - "safe-buffer": "5.2.1", - "uid-safe": "~2.1.5" - }, - "engines": { - "node": ">= 0.8.0" - } - }, - "node_modules/express-session/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-session/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/express-session/node_modules/ms": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/ms/-/ms-2.0.0.tgz", - "integrity": "sha1-VgiurfwAvmwpAd9fmGF4jeDVl8g=" - }, - "node_modules/express-session/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/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": "sha1-VgiurfwAvmwpAd9fmGF4jeDVl8g=" - }, - "node_modules/express/node_modules/qs": { - "version": "6.9.6", - "resolved": "https://registry.npmjs.org/qs/-/qs-6.9.6.tgz", - "integrity": "sha512-TIRk4aqYLNoJUbd+g2lEdz5kLWIuTMRagAXxl78Q0RiVjAOugHmeKNGdd3cwo/ktpf9aL9epCfFqWDEKysUlLQ==", - "engines": { - "node": ">=0.6" - }, - "funding": { - "url": "https://github.com/sponsors/ljharb" - } - }, - "node_modules/express/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/extend": { - "version": "3.0.2", - "resolved": "https://registry.npmjs.org/extend/-/extend-3.0.2.tgz", - "integrity": "sha512-fjquC59cD7CyW6urNXK0FBufkZcoiGG80wTuPujX590cB5Ttln20E2UB4S/WARVqhXffZl2LNgS+gQdPIIim/g==" - }, - "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/extglob": { - "version": "0.3.2", - "resolved": "https://registry.npmjs.org/extglob/-/extglob-0.3.2.tgz", - "integrity": "sha1-Lhj/PS9JqydlzskCPwEdqo2DSaE=", - "dependencies": { - "is-extglob": "^1.0.0" - }, - "engines": { - "node": ">=0.10.0" - } - }, - "node_modules/extglob/node_modules/is-extglob": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/is-extglob/-/is-extglob-1.0.0.tgz", - "integrity": "sha1-rEaBd8SUNAWgkvyPKXYMb/xiBsA=", - "engines": { - "node": ">=0.10.0" - } - }, - "node_modules/extract-zip": { - "version": "1.7.0", - "resolved": "https://registry.npmjs.org/extract-zip/-/extract-zip-1.7.0.tgz", - "integrity": "sha512-xoh5G1W/PB0/27lXgMQyIhP5DSY/LhoCsOyZgb+6iMmRtCwVBo55uKaMoEYrDCKQhWvqEip5ZPKAc6eFNyf/MA==", - "dependencies": { - "concat-stream": "^1.6.2", - "debug": "^2.6.9", - "mkdirp": "^0.5.4", - "yauzl": "^2.10.0" - }, - "bin": { - "extract-zip": "cli.js" - } - }, - "node_modules/extract-zip/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/extract-zip/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/extract-zip/node_modules/mkdirp": { - "version": "0.5.5", - "resolved": "https://registry.npmjs.org/mkdirp/-/mkdirp-0.5.5.tgz", - "integrity": "sha512-NKmAlESf6jMGym1++R0Ra7wvhV+wFW63FaSOFPwRahvea0gMUcGUhVeAg/0BC0wiv9ih5NYPB1Wn1UEI1/L+xQ==", - "dependencies": { - "minimist": "^1.2.5" - }, - "bin": { - "mkdirp": "bin/cmd.js" - } - }, - "node_modules/extract-zip/node_modules/ms": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/ms/-/ms-2.0.0.tgz", - "integrity": "sha1-VgiurfwAvmwpAd9fmGF4jeDVl8g=" - }, - "node_modules/extract-zip/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/extract-zip/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/extsprintf": { - "version": "1.3.0", - "resolved": "https://registry.npmjs.org/extsprintf/-/extsprintf-1.3.0.tgz", - "integrity": "sha1-lpGEQOMEGnpBT4xS48V06zw+HgU=", - "dev": true, - "engines": [ - "node >=0.6.0" - ] - }, - "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==" - }, - "node_modules/fast-glob": { - "version": "3.2.7", - "resolved": "https://registry.npmjs.org/fast-glob/-/fast-glob-3.2.7.tgz", - "integrity": "sha512-rYGMRwip6lUMvYD3BTScMwT1HtAs2d71SMv66Vrxs0IekGZEjhM0pcMfjQPnknBt2zeCwQMEupiN02ZP4DiT1Q==", - "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" - } - }, - "node_modules/fast-glob/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/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==" - }, - "node_modules/fast-levenshtein": { - "version": "2.0.6", - "resolved": "https://registry.npmjs.org/fast-levenshtein/-/fast-levenshtein-2.0.6.tgz", - "integrity": "sha1-PYpcZog6FqMMqGQ+hR8Zuqd5eRc=" - }, - "node_modules/fast-memoize": { - "version": "2.5.2", - "resolved": "https://registry.npmjs.org/fast-memoize/-/fast-memoize-2.5.2.tgz", - "integrity": "sha512-Ue0LwpDYErFbmNnZSF0UH6eImUwDmogUO1jyE+JbN2gsQz/jICm1Ve7t9QT0rNSsfJt+Hs4/S3GnsDVjL4HVrw==", - "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/fastest-levenshtein": { - "version": "1.0.12", - "resolved": "https://registry.npmjs.org/fastest-levenshtein/-/fastest-levenshtein-1.0.12.tgz", - "integrity": "sha512-On2N+BpYJ15xIC974QNVuYGMOlEVt4s0EOI3wwMqOmK1fdDY+FN/zltPV8vosq4ad4c/gJ1KHScUn/6AWIgiow==" - }, - "node_modules/fastq": { - "version": "1.13.0", - "resolved": "https://registry.npmjs.org/fastq/-/fastq-1.13.0.tgz", - "integrity": "sha512-YpkpUnK8od0o1hmeSc7UUs/eB/vIPWJYjKck2QKIzAf71Vm1AAQ3EbuZB3g2JIy+pg+ERD0vqI79KyZiB2e2Nw==", - "dev": true, - "dependencies": { - "reusify": "^1.0.4" - } - }, - "node_modules/fd-slicer": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/fd-slicer/-/fd-slicer-1.1.0.tgz", - "integrity": "sha1-JcfInLH5B3+IkbvmHY85Dq4lbx4=", - "dependencies": { - "pend": "~1.2.0" - } - }, - "node_modules/figgy-pudding": { - "version": "3.5.2", - "resolved": "https://registry.npmjs.org/figgy-pudding/-/figgy-pudding-3.5.2.tgz", - "integrity": "sha512-0btnI/H8f2pavGMN8w40mlSKOfTK2SVJmBfBeVIj3kNw0swwgzyRq0d5TJVOwodFmtvpPeWPN/MCcfuWF0Ezbw==", - "dev": true - }, - "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": "sha1-G2HAViGQqN/2rjuyzwIAyhMLhtQ=", - "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/filename-regex": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/filename-regex/-/filename-regex-2.0.1.tgz", - "integrity": "sha1-wcS5vuPglyXdsQa3XB4wH+LxiyY=", - "engines": { - "node": ">=0.10.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==", - "dependencies": { - "to-regex-range": "^5.0.1" - }, - "engines": { - "node": ">=8" - } - }, - "node_modules/filter-obj": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/filter-obj/-/filter-obj-1.1.0.tgz", - "integrity": "sha1-mzERErxsYSehbgFsbF1/GeCAXFs=", - "dev": true, - "engines": { - "node": ">=0.10.0" - } - }, - "node_modules/finalhandler": { - "version": "1.1.2", - "resolved": "https://registry.npmjs.org/finalhandler/-/finalhandler-1.1.2.tgz", - "integrity": "sha512-aAWcW57uxVNrQZqFXjITpW3sIUQmHGG3qSb9mUah9MgMC4NeWhNOlNjXEYq3HjRAvL6arUviZGGJsBg6z0zsWA==", - "dependencies": { - "debug": "2.6.9", - "encodeurl": "~1.0.2", - "escape-html": "~1.0.3", - "on-finished": "~2.3.0", - "parseurl": "~1.3.3", - "statuses": "~1.5.0", - "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": "sha1-VgiurfwAvmwpAd9fmGF4jeDVl8g=" - }, - "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==", - "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": "2.1.0", - "resolved": "https://registry.npmjs.org/find-up/-/find-up-2.1.0.tgz", - "integrity": "sha1-RdG35QbHF93UgndaK3eSCjwMV6c=", - "dependencies": { - "locate-path": "^2.0.0" - }, - "engines": { - "node": ">=4" - } - }, - "node_modules/flat": { - "version": "5.0.2", - "resolved": "https://registry.npmjs.org/flat/-/flat-5.0.2.tgz", - "integrity": "sha512-b6suED+5/3rTpUBdG1gupIl8MPFCAMA0QXwmljLhvCUKcUvdE4gWky9zpuGCcXHOsz4J9wPGNWq6OKpmIzz3hQ==", - "bin": { - "flat": "cli.js" - } - }, - "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/flatted": { - "version": "3.2.4", - "resolved": "https://registry.npmjs.org/flatted/-/flatted-3.2.4.tgz", - "integrity": "sha512-8/sOawo8tJ4QOBX8YlQBMxL8+RLZfxMQOif9o0KUKTNTjMYElWPE0r/m5VNFxTRd0NSw8qSy8dajrwX4RYI1Hw==", - "dev": true - }, - "node_modules/follow-redirects": { - "version": "1.14.6", - "resolved": "https://registry.npmjs.org/follow-redirects/-/follow-redirects-1.14.6.tgz", - "integrity": "sha512-fhUl5EwSJbbl8AR+uYL2KQDxLkdSjZGR36xy46AO7cOMTrCMON6Sa28FmAnC2tRTDbd/Uuzz3aJBv7EBN7JH8A==", - "funding": [ - { - "type": "individual", - "url": "https://github.com/sponsors/RubenVerborgh" - } - ], - "engines": { - "node": ">=4.0" - }, - "peerDependenciesMeta": { - "debug": { - "optional": true - } - } - }, - "node_modules/for-in": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/for-in/-/for-in-1.0.2.tgz", - "integrity": "sha1-gQaNKVqBQuwKxybG4iAMMPttXoA=", - "engines": { - "node": ">=0.10.0" - } - }, - "node_modules/for-own": { - "version": "0.1.5", - "resolved": "https://registry.npmjs.org/for-own/-/for-own-0.1.5.tgz", - "integrity": "sha1-UmXGgaTylNq78XyVCbZ2OqhFEM4=", - "dependencies": { - "for-in": "^1.0.1" - }, - "engines": { - "node": ">=0.10.0" - } - }, - "node_modules/foreground-child": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/foreground-child/-/foreground-child-2.0.0.tgz", - "integrity": "sha512-dCIq9FpEcyQyXKCkyzmlPTFNgrCzPudOe+mhvJU5zAtlBnGVy2yKxtfsxK2tQBThwq225jcvBjpw1Gr40uzZCA==", - "dev": true, - "dependencies": { - "cross-spawn": "^7.0.0", - "signal-exit": "^3.0.2" - }, - "engines": { - "node": ">=8.0.0" - } - }, - "node_modules/forever-agent": { - "version": "0.6.1", - "resolved": "https://registry.npmjs.org/forever-agent/-/forever-agent-0.6.1.tgz", - "integrity": "sha1-+8cfDEGt6zf5bFd60e1C2P2sypE=", - "dev": true, - "engines": { - "node": "*" - } - }, - "node_modules/form-data": { - "version": "2.3.3", - "resolved": "https://registry.npmjs.org/form-data/-/form-data-2.3.3.tgz", - "integrity": "sha512-1lLKB2Mu3aGP1Q/2eCOx0fNbRMe7XdwktwOruhfqqd0rIJWwN4Dh+E3hrPSlDCXnSR7UtZ1N38rVXm+6+MEhJQ==", - "dependencies": { - "asynckit": "^0.4.0", - "combined-stream": "^1.0.6", - "mime-types": "^2.1.12" - }, - "engines": { - "node": ">= 0.12" - } - }, - "node_modules/formidable": { - "version": "1.2.6", - "resolved": "https://registry.npmjs.org/formidable/-/formidable-1.2.6.tgz", - "integrity": "sha512-KcpbcpuLNOwrEjnbpMC0gS+X8ciDoZE1kkqzat4a8vrprf+s9pKNQ/QIwWfbfs4ltgmFl3MD177SNTkve3BwGQ==", - "deprecated": "Please upgrade to latest, formidable@v2 or formidable@v3! Check these notes: https://bit.ly/2ZEqIau", - "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/fp-and-or": { - "version": "0.1.3", - "resolved": "https://registry.npmjs.org/fp-and-or/-/fp-and-or-0.1.3.tgz", - "integrity": "sha512-wJaE62fLaB3jCYvY2ZHjZvmKK2iiLiiehX38rz5QZxtdN8fVPJDeZUiVvJrHStdTc+23LHlyZuSEKgFc0pxi2g==", - "dev": true, - "engines": { - "node": ">=10" - } - }, - "node_modules/fresh": { - "version": "0.5.2", - "resolved": "https://registry.npmjs.org/fresh/-/fresh-0.5.2.tgz", - "integrity": "sha1-PYyt2Q2XZWn6g1qx+OSyOhBWBac=", - "engines": { - "node": ">= 0.6" - } - }, - "node_modules/fromentries": { - "version": "1.3.2", - "resolved": "https://registry.npmjs.org/fromentries/-/fromentries-1.3.2.tgz", - "integrity": "sha512-cHEpEQHUg0f8XdtZCc2ZAhrHzKzT0MrFUTcvx+hfxYu7rGMDc5SKoXFh+n4YigxsHXRzc6OrCshdR1bWH6HHyg==", - "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/fs-extra": { - "version": "9.1.0", - "resolved": "https://registry.npmjs.org/fs-extra/-/fs-extra-9.1.0.tgz", - "integrity": "sha512-hcg3ZmepS30/7BSFqRvoo3DOMQu7IjqxO5nCDt+zM9XWjb33Wg7ziNT+Qvqbuc3+gWpzO02JubVyk2G4Zvo1OQ==", - "dev": true, - "dependencies": { - "at-least-node": "^1.0.0", - "graceful-fs": "^4.2.0", - "jsonfile": "^6.0.1", - "universalify": "^2.0.0" - }, - "engines": { - "node": ">=10" - } - }, - "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==", - "dev": true, - "dependencies": { - "minipass": "^3.0.0" - }, - "engines": { - "node": ">= 8" - } - }, - "node_modules/fs-walk": { - "version": "0.0.1", - "resolved": "https://registry.npmjs.org/fs-walk/-/fs-walk-0.0.1.tgz", - "integrity": "sha1-9/yRw64e6tB8mYvF0N1B8tvr0zU=", - "dependencies": { - "async": "*" - } - }, - "node_modules/fs.realpath": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/fs.realpath/-/fs.realpath-1.0.0.tgz", - "integrity": "sha1-FQStJSMVjKpA20onh8sBQRmU6k8=" - }, - "node_modules/fsevents": { - "version": "2.3.2", - "resolved": "https://registry.npmjs.org/fsevents/-/fsevents-2.3.2.tgz", - "integrity": "sha512-xiqMQR4xAeHTuB9uWm+fFRcIOgKBMiOBP+eXiyT7jsgVCq1bkVygt00oASowB7EdtpOHaaPgKt812P9ab+DDKA==", - "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/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": "sha1-GwqzvVU7Kg1jmdKcDj6gslIHgyc=", - "dev": true - }, - "node_modules/gauge": { - "version": "2.7.4", - "resolved": "https://registry.npmjs.org/gauge/-/gauge-2.7.4.tgz", - "integrity": "sha1-LANAXHU4w51+s3sxcCLjJfsBi/c=", - "dev": true, - "dependencies": { - "aproba": "^1.0.3", - "console-control-strings": "^1.0.0", - "has-unicode": "^2.0.0", - "object-assign": "^4.1.0", - "signal-exit": "^3.0.0", - "string-width": "^1.0.1", - "strip-ansi": "^3.0.1", - "wide-align": "^1.1.0" - } - }, - "node_modules/gauge/node_modules/ansi-regex": { - "version": "2.1.1", - "resolved": "https://registry.npmjs.org/ansi-regex/-/ansi-regex-2.1.1.tgz", - "integrity": "sha1-w7M6te42DYbg5ijwRorn7yfWVN8=", - "dev": true, - "engines": { - "node": ">=0.10.0" - } - }, - "node_modules/gauge/node_modules/aproba": { - "version": "1.2.0", - "resolved": "https://registry.npmjs.org/aproba/-/aproba-1.2.0.tgz", - "integrity": "sha512-Y9J6ZjXtoYh8RnXVCMOU/ttDmk1aBjunq9vO0ta5x85WDQiQfUF9sIPBITdbiiIVcBo03Hi3jMxigBtsddlXRw==", - "dev": true - }, - "node_modules/gauge/node_modules/is-fullwidth-code-point": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/is-fullwidth-code-point/-/is-fullwidth-code-point-1.0.0.tgz", - "integrity": "sha1-754xOG8DGn8NZDr4L95QxFfvAMs=", - "dev": true, - "dependencies": { - "number-is-nan": "^1.0.0" - }, - "engines": { - "node": ">=0.10.0" - } - }, - "node_modules/gauge/node_modules/string-width": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/string-width/-/string-width-1.0.2.tgz", - "integrity": "sha1-EYvfW4zcUaKn5w0hHgfisLmxB9M=", - "dev": true, - "dependencies": { - "code-point-at": "^1.0.0", - "is-fullwidth-code-point": "^1.0.0", - "strip-ansi": "^3.0.0" - }, - "engines": { - "node": ">=0.10.0" - } - }, - "node_modules/gauge/node_modules/strip-ansi": { - "version": "3.0.1", - "resolved": "https://registry.npmjs.org/strip-ansi/-/strip-ansi-3.0.1.tgz", - "integrity": "sha1-ajhfuIU9lS1f8F0Oiq+UJ43GPc8=", - "dev": true, - "dependencies": { - "ansi-regex": "^2.0.0" - }, - "engines": { - "node": ">=0.10.0" - } - }, - "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==", - "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==", - "engines": { - "node": "6.* || 8.* || >= 10.*" - } - }, - "node_modules/get-intrinsic": { - "version": "1.1.1", - "resolved": "https://registry.npmjs.org/get-intrinsic/-/get-intrinsic-1.1.1.tgz", - "integrity": "sha512-kWZrnVM42QCiEA2Ig1bG8zjoIMOgxWwYCEeNdwY6Tv/cOSeGpcoX4pXHfKUxNKVoArnrEr2e9srnAxxGIraS9Q==", - "dependencies": { - "function-bind": "^1.1.1", - "has": "^1.0.3", - "has-symbols": "^1.0.1" - }, - "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-pkg-repo": { - "version": "4.2.1", - "resolved": "https://registry.npmjs.org/get-pkg-repo/-/get-pkg-repo-4.2.1.tgz", - "integrity": "sha512-2+QbHjFRfGB74v/pYWjd5OhU3TDIC2Gv/YKUTk/tCvAz0pkn/Mz6P3uByuBimLOcPvN2jYdScl3xGFSrx0jEcA==", - "dev": true, - "dependencies": { - "@hutson/parse-repository-url": "^3.0.0", - "hosted-git-info": "^4.0.0", - "through2": "^2.0.0", - "yargs": "^16.2.0" - }, - "bin": { - "get-pkg-repo": "src/cli.js" - }, - "engines": { - "node": ">=6.9.0" - } - }, - "node_modules/get-pkg-repo/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/get-pkg-repo/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/get-pkg-repo/node_modules/through2": { - "version": "2.0.5", - "resolved": "https://registry.npmjs.org/through2/-/through2-2.0.5.tgz", - "integrity": "sha512-/mrRod8xqpA+IHSLyGCQ2s8SPHiCDEeQJSep1jqLYeEUClOFG2Qsh+4FU6G9VeqpZnGW/Su8LQGc4YKni5rYSQ==", - "dev": true, - "dependencies": { - "readable-stream": "~2.3.6", - "xtend": "~4.0.1" - } - }, - "node_modules/get-port": { - "version": "5.1.1", - "resolved": "https://registry.npmjs.org/get-port/-/get-port-5.1.1.tgz", - "integrity": "sha512-g/Q1aTSDOxFpchXC4i8ZWvxA1lnPqx/JHqcpIw0/LX9T8x/GBbi6YnlN5nhaKIFkT8oFsscUKgDJYxfwfS6QsQ==", - "dev": true, - "engines": { - "node": ">=8" - }, - "funding": { - "url": "https://github.com/sponsors/sindresorhus" - } - }, - "node_modules/get-stdin": { - "version": "8.0.0", - "resolved": "https://registry.npmjs.org/get-stdin/-/get-stdin-8.0.0.tgz", - "integrity": "sha512-sY22aA6xchAzprjyqmSEQv4UbAAzRN0L2dQB0NlN5acTTK9Don6nhoc3eAbUnpZiCANAMfd/+40kVdKfFygohg==", - "dev": true, - "engines": { - "node": ">=10" - }, - "funding": { - "url": "https://github.com/sponsors/sindresorhus" - } - }, - "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==", - "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/getpass": { - "version": "0.1.7", - "resolved": "https://registry.npmjs.org/getpass/-/getpass-0.1.7.tgz", - "integrity": "sha1-Xv+OPmhNVprkyysSgmBOi6YhSfo=", - "dev": true, - "dependencies": { - "assert-plus": "^1.0.0" - } - }, - "node_modules/git-raw-commits": { - "version": "2.0.11", - "resolved": "https://registry.npmjs.org/git-raw-commits/-/git-raw-commits-2.0.11.tgz", - "integrity": "sha512-VnctFhw+xfj8Va1xtfEqCUD2XDrbAPSJx+hSrE5K7fGdjZruW7XV+QOrN7LF/RJyvspRiD2I0asWsxFp0ya26A==", - "dev": true, - "dependencies": { - "dargs": "^7.0.0", - "lodash": "^4.17.15", - "meow": "^8.0.0", - "split2": "^3.0.0", - "through2": "^4.0.0" - }, - "bin": { - "git-raw-commits": "cli.js" - }, - "engines": { - "node": ">=10" - } - }, - "node_modules/git-remote-origin-url": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/git-remote-origin-url/-/git-remote-origin-url-2.0.0.tgz", - "integrity": "sha1-UoJlna4hBxRaERJhEq0yFuxfpl8=", - "dev": true, - "dependencies": { - "gitconfiglocal": "^1.0.0", - "pify": "^2.3.0" - }, - "engines": { - "node": ">=4" - } - }, - "node_modules/git-remote-origin-url/node_modules/pify": { - "version": "2.3.0", - "resolved": "https://registry.npmjs.org/pify/-/pify-2.3.0.tgz", - "integrity": "sha1-7RQaasBDqEnqWISY59yosVMw6Qw=", - "dev": true, - "engines": { - "node": ">=0.10.0" - } - }, - "node_modules/git-semver-tags": { - "version": "4.1.1", - "resolved": "https://registry.npmjs.org/git-semver-tags/-/git-semver-tags-4.1.1.tgz", - "integrity": "sha512-OWyMt5zBe7xFs8vglMmhM9lRQzCWL3WjHtxNNfJTMngGym7pC1kh8sP6jevfydJ6LP3ZvGxfb6ABYgPUM0mtsA==", - "dev": true, - "dependencies": { - "meow": "^8.0.0", - "semver": "^6.0.0" - }, - "bin": { - "git-semver-tags": "cli.js" - }, - "engines": { - "node": ">=10" - } - }, - "node_modules/git-semver-tags/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/git-up": { - "version": "4.0.5", - "resolved": "https://registry.npmjs.org/git-up/-/git-up-4.0.5.tgz", - "integrity": "sha512-YUvVDg/vX3d0syBsk/CKUTib0srcQME0JyHkL5BaYdwLsiCslPWmDSi8PUMo9pXYjrryMcmsCoCgsTpSCJEQaA==", - "dev": true, - "dependencies": { - "is-ssh": "^1.3.0", - "parse-url": "^6.0.0" - } - }, - "node_modules/git-url-parse": { - "version": "11.6.0", - "resolved": "https://registry.npmjs.org/git-url-parse/-/git-url-parse-11.6.0.tgz", - "integrity": "sha512-WWUxvJs5HsyHL6L08wOusa/IXYtMuCAhrMmnTjQPpBU0TTHyDhnOATNH3xNQz7YOQUsqIIPTGr4xiVti1Hsk5g==", - "dev": true, - "dependencies": { - "git-up": "^4.0.0" - } - }, - "node_modules/gitconfiglocal": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/gitconfiglocal/-/gitconfiglocal-1.0.0.tgz", - "integrity": "sha1-QdBF84UaXqiPA/JMocYXgRRGS5s=", - "dev": true, - "dependencies": { - "ini": "^1.3.2" - } - }, - "node_modules/glob": { - "version": "7.2.0", - "resolved": "https://registry.npmjs.org/glob/-/glob-7.2.0.tgz", - "integrity": "sha512-lmLf6gtyrPq8tTjSmrO94wBeQbFR3HbLHbuyD69wuyQkImp2hWqMGB47OX65FBkPffO641IP9jWa1z4ivqG26Q==", - "dependencies": { - "fs.realpath": "^1.0.0", - "inflight": "^1.0.4", - "inherits": "2", - "minimatch": "^3.0.4", - "once": "^1.3.0", - "path-is-absolute": "^1.0.0" - }, - "engines": { - "node": "*" - }, - "funding": { - "url": "https://github.com/sponsors/isaacs" - } - }, - "node_modules/glob-base": { - "version": "0.3.0", - "resolved": "https://registry.npmjs.org/glob-base/-/glob-base-0.3.0.tgz", - "integrity": "sha1-27Fk9iIbHAscz4Kuoyi0l98Oo8Q=", - "dependencies": { - "glob-parent": "^2.0.0", - "is-glob": "^2.0.0" - }, - "engines": { - "node": ">=0.10.0" - } - }, - "node_modules/glob-base/node_modules/glob-parent": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/glob-parent/-/glob-parent-2.0.0.tgz", - "integrity": "sha1-gTg9ctsFT8zPUzbaqQLxgvbtuyg=", - "dependencies": { - "is-glob": "^2.0.0" - } - }, - "node_modules/glob-base/node_modules/is-extglob": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/is-extglob/-/is-extglob-1.0.0.tgz", - "integrity": "sha1-rEaBd8SUNAWgkvyPKXYMb/xiBsA=", - "engines": { - "node": ">=0.10.0" - } - }, - "node_modules/glob-base/node_modules/is-glob": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/is-glob/-/is-glob-2.0.1.tgz", - "integrity": "sha1-0Jb5JqPe1WAPP9/ZEZjLCIjC2GM=", - "dependencies": { - "is-extglob": "^1.0.0" - }, - "engines": { - "node": ">=0.10.0" - } - }, - "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/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==" - }, - "node_modules/global-dirs": { - "version": "3.0.0", - "resolved": "https://registry.npmjs.org/global-dirs/-/global-dirs-3.0.0.tgz", - "integrity": "sha512-v8ho2DS5RiCjftj1nD9NmnfaOzTdud7RRnVd9kFNOjqZbISlx5DQ+OrTkywgd0dIt7oFCvKetZSHoHcP3sDdiA==", - "dev": true, - "dependencies": { - "ini": "2.0.0" - }, - "engines": { - "node": ">=10" - }, - "funding": { - "url": "https://github.com/sponsors/sindresorhus" - } - }, - "node_modules/global-dirs/node_modules/ini": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/ini/-/ini-2.0.0.tgz", - "integrity": "sha512-7PnF4oN3CvZF23ADhA5wRaYEQpJ8qygSkbtTXWBeXWXmEVRXK+1ITciHWwHhsjv1TmW0MgacIv6hEi5pX5NQdA==", - "dev": true, - "engines": { - "node": ">=10" - } - }, - "node_modules/globals": { - "version": "13.12.0", - "resolved": "https://registry.npmjs.org/globals/-/globals-13.12.0.tgz", - "integrity": "sha512-uS8X6lSKN2JumVoXrbUz+uG4BYG+eiawqm3qFcT7ammfbUHeCBoJMlHcec/S3krSk73/AE/f0szYFmgAA3kYZg==", - "dev": true, - "dependencies": { - "type-fest": "^0.20.2" - }, - "engines": { - "node": ">=8" - }, - "funding": { - "url": "https://github.com/sponsors/sindresorhus" - } - }, - "node_modules/globby": { - "version": "11.0.4", - "resolved": "https://registry.npmjs.org/globby/-/globby-11.0.4.tgz", - "integrity": "sha512-9O4MVG9ioZJ08ffbcyVYyLOJLk5JQ688pJ4eMGLpdWLHq/Wr1D9BlriLQyL0E+jbkuePVZXYFj47QM/v093wHg==", - "dev": true, - "dependencies": { - "array-union": "^2.1.0", - "dir-glob": "^3.0.1", - "fast-glob": "^3.1.1", - "ignore": "^5.1.4", - "merge2": "^1.3.0", - "slash": "^3.0.0" - }, - "engines": { - "node": ">=10" - }, - "funding": { - "url": "https://github.com/sponsors/sindresorhus" - } - }, - "node_modules/got": { - "version": "9.6.0", - "resolved": "https://registry.npmjs.org/got/-/got-9.6.0.tgz", - "integrity": "sha512-R7eWptXuGYxwijs0eV+v3o6+XH1IqVK8dJOEecQfTmkncw9AV4dcw/Dhxi8MdlqPthxxpZyizMzyg8RTmEsG+Q==", - "dev": true, - "dependencies": { - "@sindresorhus/is": "^0.14.0", - "@szmarczak/http-timer": "^1.1.2", - "cacheable-request": "^6.0.0", - "decompress-response": "^3.3.0", - "duplexer3": "^0.1.4", - "get-stream": "^4.1.0", - "lowercase-keys": "^1.0.1", - "mimic-response": "^1.0.1", - "p-cancelable": "^1.0.0", - "to-readable-stream": "^1.0.0", - "url-parse-lax": "^3.0.0" - }, - "engines": { - "node": ">=8.6" - } - }, - "node_modules/got/node_modules/get-stream": { - "version": "4.1.0", - "resolved": "https://registry.npmjs.org/get-stream/-/get-stream-4.1.0.tgz", - "integrity": "sha512-GMat4EJ5161kIy2HevLlr4luNjBgvmj413KaQA7jt4V8B4RDsfpHk7WQ9GVqfYyyx8OS/L66Kox+rJRNklLK7w==", - "dev": true, - "dependencies": { - "pump": "^3.0.0" - }, - "engines": { - "node": ">=6" - } - }, - "node_modules/graceful-fs": { - "version": "4.2.8", - "resolved": "https://registry.npmjs.org/graceful-fs/-/graceful-fs-4.2.8.tgz", - "integrity": "sha512-qkIilPUYcNhJpd33n0GBXTB1MMPp14TxEsEs0pTrsSVucApsYzW5V+Q8Qxhik6KU3evy+qkAAowTByymK0avdg==" - }, - "node_modules/graceful-readlink": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/graceful-readlink/-/graceful-readlink-1.0.1.tgz", - "integrity": "sha1-TK+tdrxi8C+gObL5Tpo906ORpyU=" - }, - "node_modules/grant": { - "version": "5.4.19", - "resolved": "https://registry.npmjs.org/grant/-/grant-5.4.19.tgz", - "integrity": "sha512-VCYpHZP2ss7OYdKFIsSK2/WD7Vrf5klzj+CA/6p8PC1mPHqTLEDhMFejnmjICBZytl858eNUWFs8yCUZ28eevg==", - "dependencies": { - "qs": "^6.10.2", - "request-compose": "^2.1.4", - "request-oauth": "^1.0.1" - }, - "engines": { - "node": ">=12.0.0" - }, - "optionalDependencies": { - "cookie": "^0.4.1", - "cookie-signature": "^1.1.0", - "jwk-to-pem": "^2.0.5", - "jws": "^4.0.0" - } - }, - "node_modules/grant/node_modules/cookie-signature": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/cookie-signature/-/cookie-signature-1.1.0.tgz", - "integrity": "sha512-Alvs19Vgq07eunykd3Xy2jF0/qSNv2u7KDbAek9H5liV1UMijbqFs5cycZvv5dVsvseT/U4H8/7/w8Koh35C4A==", - "optional": true, - "engines": { - "node": ">=6.6.0" - } - }, - "node_modules/growl": { - "version": "1.10.5", - "resolved": "https://registry.npmjs.org/growl/-/growl-1.10.5.tgz", - "integrity": "sha512-qBr4OuELkhPenW6goKVXiv47US3clb3/IbuWF9KNKEijAy9oeHxU9IgzjvJhHkUzhaj7rOUD7+YGWqUjLp5oSA==", - "engines": { - "node": ">=4.x" - } - }, - "node_modules/handlebars": { - "version": "4.7.7", - "resolved": "https://registry.npmjs.org/handlebars/-/handlebars-4.7.7.tgz", - "integrity": "sha512-aAcXm5OAfE/8IXkcZvCepKU3VzW1/39Fb5ZuqMtgI/hT8X2YgoMvBY5dLhq/cpOvw7Lk1nK/UF71aLG/ZnVYRA==", - "dev": true, - "dependencies": { - "minimist": "^1.2.5", - "neo-async": "^2.6.0", - "source-map": "^0.6.1", - "wordwrap": "^1.0.0" - }, - "bin": { - "handlebars": "bin/handlebars" - }, - "engines": { - "node": ">=0.4.7" - }, - "optionalDependencies": { - "uglify-js": "^3.1.4" - } - }, - "node_modules/har-schema": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/har-schema/-/har-schema-2.0.0.tgz", - "integrity": "sha1-qUwiJOvKwEeCoNkDVSHyRzW37JI=", - "dev": true, - "engines": { - "node": ">=4" - } - }, - "node_modules/har-validator": { - "version": "5.1.5", - "resolved": "https://registry.npmjs.org/har-validator/-/har-validator-5.1.5.tgz", - "integrity": "sha512-nmT2T0lljbxdQZfspsno9hgrG3Uir6Ks5afism62poxqBM6sDnMEuPmzTq8XN0OEwqKLLdh1jQI3qyE66Nzb3w==", - "deprecated": "this library is no longer supported", - "dev": true, - "dependencies": { - "ajv": "^6.12.3", - "har-schema": "^2.0.0" - }, - "engines": { - "node": ">=6" - } - }, - "node_modules/har-validator/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/har-validator/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/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", - "integrity": "sha512-f2dvO0VU6Oej7RkWJGrehjbzMAjFp5/VKPp5tTpWIV4JHHZK1/BxbFRtf/siA2SWTe09caDmVtYYzWEIbBS4zw==", - "dependencies": { - "function-bind": "^1.1.1" - }, - "engines": { - "node": ">= 0.4.0" - } - }, - "node_modules/has-ansi": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/has-ansi/-/has-ansi-2.0.0.tgz", - "integrity": "sha1-NPUEnOHs3ysGSa8+8k5F7TVBbZE=", - "dependencies": { - "ansi-regex": "^2.0.0" - }, - "engines": { - "node": ">=0.10.0" - } - }, - "node_modules/has-ansi/node_modules/ansi-regex": { - "version": "2.1.1", - "resolved": "https://registry.npmjs.org/ansi-regex/-/ansi-regex-2.1.1.tgz", - "integrity": "sha1-w7M6te42DYbg5ijwRorn7yfWVN8=", - "engines": { - "node": ">=0.10.0" - } - }, - "node_modules/has-bigints": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/has-bigints/-/has-bigints-1.0.1.tgz", - "integrity": "sha512-LSBS2LjbNBTf6287JEbEzvJgftkF5qFkmCo9hDRpAzKhUOlJ+hx8dd4USs00SgsUNwc4617J9ki5YtEClM2ffA==", - "dev": true, - "funding": { - "url": "https://github.com/sponsors/ljharb" - } - }, - "node_modules/has-cors": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/has-cors/-/has-cors-1.1.0.tgz", - "integrity": "sha1-XkdHk/fqmEPRu5nCPu9J/xJv/zk=" - }, - "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-symbols": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/has-symbols/-/has-symbols-1.0.2.tgz", - "integrity": "sha512-chXa79rL/UC2KlX17jo3vRGz0azaWEx5tGqZg5pO3NUyEJVB17dMruQlzCCOfUvElghKcm5194+BCRvi2Rv/Gw==", - "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==", - "dependencies": { - "has-symbols": "^1.0.2" - }, - "engines": { - "node": ">= 0.4" - }, - "funding": { - "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": "sha1-4Ob+aijPUROIVeCG0Wkedx3iqLk=", - "dev": true - }, - "node_modules/has-yarn": { - "version": "2.1.0", - "resolved": "https://registry.npmjs.org/has-yarn/-/has-yarn-2.1.0.tgz", - "integrity": "sha512-UqBRqi4ju7T+TqGNdqAO0PaSVGsDGJUBQvk9eUWNGRY1CFGDzYhLWoM7JQEemnlvVcv/YEmc2wNW8BC24EnUsw==", - "dev": true, - "engines": { - "node": ">=8" - } - }, - "node_modules/hash.js": { - "version": "1.1.7", - "resolved": "https://registry.npmjs.org/hash.js/-/hash.js-1.1.7.tgz", - "integrity": "sha512-taOaskGt4z4SOANNseOviYDvjEJinIkRgmp7LbKP2YTTmVxWBl87s/uzK9r+44BclBSp2X7K1hqeNfz9JbBeXA==", - "optional": true, - "dependencies": { - "inherits": "^2.0.3", - "minimalistic-assert": "^1.0.1" - } - }, - "node_modules/hasha": { - "version": "5.2.2", - "resolved": "https://registry.npmjs.org/hasha/-/hasha-5.2.2.tgz", - "integrity": "sha512-Hrp5vIK/xr5SkeN2onO32H0MgNZ0f17HRNH39WfL0SYUNOTZ5Lz1TJ8Pajo/87dYGEFlLMm7mIc/k/s6Bvz9HQ==", - "dev": true, - "dependencies": { - "is-stream": "^2.0.0", - "type-fest": "^0.8.0" - }, - "engines": { - "node": ">=8" - }, - "funding": { - "url": "https://github.com/sponsors/sindresorhus" - } - }, - "node_modules/hasha/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/he": { - "version": "1.2.0", - "resolved": "https://registry.npmjs.org/he/-/he-1.2.0.tgz", - "integrity": "sha512-F/1DnUGPopORZi0ni+CvrCgHQ5FyEAHRLSApuYWMmrbSwoN2Mn/7k+Gl38gJnR7yyDZk6WLXwiGod1JOWNDKGw==", - "bin": { - "he": "bin/he" - } - }, - "node_modules/hmac-drbg": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/hmac-drbg/-/hmac-drbg-1.0.1.tgz", - "integrity": "sha1-0nRXAQJabHdabFRXk+1QL8DGSaE=", - "optional": true, - "dependencies": { - "hash.js": "^1.0.3", - "minimalistic-assert": "^1.0.0", - "minimalistic-crypto-utils": "^1.0.1" - } - }, - "node_modules/home-or-tmp": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/home-or-tmp/-/home-or-tmp-2.0.0.tgz", - "integrity": "sha1-42w/LSyufXRqhX440Y1fMqeILbg=", - "dependencies": { - "os-homedir": "^1.0.0", - "os-tmpdir": "^1.0.1" - }, - "engines": { - "node": ">=0.10.0" - } - }, - "node_modules/hosted-git-info": { - "version": "4.0.2", - "resolved": "https://registry.npmjs.org/hosted-git-info/-/hosted-git-info-4.0.2.tgz", - "integrity": "sha512-c9OGXbZ3guC/xOlCg1Ci/VgWlwsqDv1yMQL1CWqXDL0hDjXuNcq0zuR4xqPSuasI3kqFDhqSyTjREz5gzq0fXg==", - "dev": true, - "dependencies": { - "lru-cache": "^6.0.0" - }, - "engines": { - "node": ">=10" - } - }, - "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/htmljs-parser": { - "version": "2.11.1", - "resolved": "https://registry.npmjs.org/htmljs-parser/-/htmljs-parser-2.11.1.tgz", - "integrity": "sha512-9TM67eoRSSYFYi+R0yP8ysFOzhQiXClQ41r8V+HCWXuQHKG5qEtY/H8wAhOIsBEVroIeMHU/DatFKOkMXmDnwg==", - "dependencies": { - "char-props": "^0.1.5", - "complain": "^1.0.0" - } - }, - "node_modules/http-assert": { - "version": "1.5.0", - "resolved": "https://registry.npmjs.org/http-assert/-/http-assert-1.5.0.tgz", - "integrity": "sha512-uPpH7OKX4H25hBmU6G1jWNaqJGpTXxey+YOUizJUAgu0AjLUeC8D73hTrhvDS5D+GJN1DN1+hhc/eF/wpxtp0w==", - "dependencies": { - "deep-equal": "~1.0.1", - "http-errors": "~1.8.0" - }, - "engines": { - "node": ">= 0.8" - } - }, - "node_modules/http-cache-semantics": { - "version": "4.1.0", - "resolved": "https://registry.npmjs.org/http-cache-semantics/-/http-cache-semantics-4.1.0.tgz", - "integrity": "sha512-carPklcUh7ROWRK7Cv27RPtdhYhUsela/ue5/jKzjegVvXDqM2ILE9Q2BGn9JZJh1g87cp56su/FgQSzcWS8cQ==", - "dev": true - }, - "node_modules/http-errors": { - "version": "1.8.1", - "resolved": "https://registry.npmjs.org/http-errors/-/http-errors-1.8.1.tgz", - "integrity": "sha512-Kpk9Sm7NmI+RHhnj6OIWDI1d6fIoFAtFt9RLaTMRlg/8w49juAStsrBgp0Dp4OdxdVbRIeKhtCUvoi/RuAhO4g==", - "dependencies": { - "depd": "~1.1.2", - "inherits": "2.0.4", - "setprototypeof": "1.2.0", - "statuses": ">= 1.5.0 < 2", - "toidentifier": "1.0.1" - }, - "engines": { - "node": ">= 0.6" - } - }, - "node_modules/http-proxy-agent": { - "version": "4.0.1", - "resolved": "https://registry.npmjs.org/http-proxy-agent/-/http-proxy-agent-4.0.1.tgz", - "integrity": "sha512-k0zdNgqWTGA6aeIRVpvfVob4fL52dTfaehylg0Y4UvSySvOq/Y+BOyPrgpUrA7HylqvU8vIZGsRuXmspskV0Tg==", - "dev": true, - "dependencies": { - "@tootallnate/once": "1", - "agent-base": "6", - "debug": "4" - }, - "engines": { - "node": ">= 6" - } - }, - "node_modules/http-signature": { - "version": "1.2.0", - "resolved": "https://registry.npmjs.org/http-signature/-/http-signature-1.2.0.tgz", - "integrity": "sha1-muzZJRFHcvPZW2WmCruPfBj7rOE=", - "dev": true, - "dependencies": { - "assert-plus": "^1.0.0", - "jsprim": "^1.2.2", - "sshpk": "^1.7.0" - }, - "engines": { - "node": ">=0.8", - "npm": ">=1.3.7" - } - }, - "node_modules/https-proxy-agent": { - "version": "5.0.0", - "resolved": "https://registry.npmjs.org/https-proxy-agent/-/https-proxy-agent-5.0.0.tgz", - "integrity": "sha512-EkYm5BcKUGiduxzSt3Eppko+PiNWNEpa4ySk9vTC6wDsQJW9rHSa+UhGNJoRYp7bz6Ht1eaRIa6QaJqO5rCFbA==", - "dev": true, - "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", - "integrity": "sha512-B4FFZ6q/T2jhhksgkbEW3HBvWIfDW85snkQgawt07S7J5QXTk6BkNV+0yAeZrM5QpMAdYlocGoljn0sJ/WQkFw==", - "engines": { - "node": ">=10.17.0" - } - }, - "node_modules/humanize-ms": { - "version": "1.2.1", - "resolved": "https://registry.npmjs.org/humanize-ms/-/humanize-ms-1.2.1.tgz", - "integrity": "sha1-xG4xWaKT9riW2ikxbYtv6Lt5u+0=", - "dev": true, - "dependencies": { - "ms": "^2.0.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==", - "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.0", - "resolved": "https://registry.npmjs.org/ignore/-/ignore-5.2.0.tgz", - "integrity": "sha512-CmxgYGiEPCLhfLnpPp1MoRmifwEIOgjcHXxOBjv7mY96c+eWScsOP9c112ZyLdWHi0FxHjI+4uVhKYp/gcdRmQ==", - "engines": { - "node": ">= 4" - } - }, - "node_modules/ignore-walk": { - "version": "3.0.4", - "resolved": "https://registry.npmjs.org/ignore-walk/-/ignore-walk-3.0.4.tgz", - "integrity": "sha512-PY6Ii8o1jMRA1z4F2hRkH/xN59ox43DavKvD3oDpfurRlOJyAHpifIwpbdv1n4jt4ov0jSpw3kQ4GhJnpBL6WQ==", - "dev": true, - "dependencies": { - "minimatch": "^3.0.4" - } - }, - "node_modules/image-size": { - "version": "0.3.5", - "resolved": "https://registry.npmjs.org/image-size/-/image-size-0.3.5.tgz", - "integrity": "sha1-gyQOqy+1sAsEqrjHSwRx6cunrYw=", - "bin": { - "image-size": "bin/image-size" - }, - "engines": { - "node": ">=0.10.0" - } - }, - "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-lazy": { - "version": "2.1.0", - "resolved": "https://registry.npmjs.org/import-lazy/-/import-lazy-2.1.0.tgz", - "integrity": "sha1-BWmOPUXIjo1+nZLLBYTnfwlvPkM=", - "dev": true, - "engines": { - "node": ">=4" - } - }, - "node_modules/import-local": { - "version": "3.0.3", - "resolved": "https://registry.npmjs.org/import-local/-/import-local-3.0.3.tgz", - "integrity": "sha512-bE9iaUY3CXH8Cwfan/abDKAxe1KGT9kyGsBPqf6DMK/z0a2OzAsrukeYNgIH6cH5Xr452jb1TUL8rSfCLjZ9uA==", - "dependencies": { - "pkg-dir": "^4.2.0", - "resolve-cwd": "^3.0.0" - }, - "bin": { - "import-local-fixture": "fixtures/cli.js" - }, - "engines": { - "node": ">=8" - } - }, - "node_modules/imurmurhash": { - "version": "0.1.4", - "resolved": "https://registry.npmjs.org/imurmurhash/-/imurmurhash-0.1.4.tgz", - "integrity": "sha1-khi5srkoojixPcT7a21XbyMUU+o=", - "dev": true, - "engines": { - "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/infer-owner": { - "version": "1.0.4", - "resolved": "https://registry.npmjs.org/infer-owner/-/infer-owner-1.0.4.tgz", - "integrity": "sha512-IClj+Xz94+d7irH5qRyfJonOdfTzuDaifE6ZPWfx0N0+/ATZCbuTPq2prFl526urkQd90WyUKIh1DfBQ2hMz9A==", - "dev": true - }, - "node_modules/inflation": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/inflation/-/inflation-2.0.0.tgz", - "integrity": "sha1-i0F+R8KPklpFEz2RTKH9OJEH8w8=", - "engines": { - "node": ">= 0.8.0" - } - }, - "node_modules/inflight": { - "version": "1.0.6", - "resolved": "https://registry.npmjs.org/inflight/-/inflight-1.0.6.tgz", - "integrity": "sha1-Sb1jMdfQLQwJvJEKEHW6gWW1bfk=", - "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/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/init-package-json": { - "version": "2.0.5", - "resolved": "https://registry.npmjs.org/init-package-json/-/init-package-json-2.0.5.tgz", - "integrity": "sha512-u1uGAtEFu3VA6HNl/yUWw57jmKEMx8SKOxHhxjGnOFUiIlFnohKDFg4ZrPpv9wWqk44nDxGJAtqjdQFm+9XXQA==", - "dev": true, - "dependencies": { - "npm-package-arg": "^8.1.5", - "promzard": "^0.3.0", - "read": "~1.0.1", - "read-package-json": "^4.1.1", - "semver": "^7.3.5", - "validate-npm-package-license": "^3.0.4", - "validate-npm-package-name": "^3.0.0" - }, - "engines": { - "node": ">=10" - } - }, - "node_modules/init-package-json/node_modules/read-package-json": { - "version": "4.1.1", - "resolved": "https://registry.npmjs.org/read-package-json/-/read-package-json-4.1.1.tgz", - "integrity": "sha512-P82sbZJ3ldDrWCOSKxJT0r/CXMWR0OR3KRh55SgKo3p91GSIEEC32v3lSHAvO/UcH3/IoL7uqhOFBduAnwdldw==", - "dev": true, - "dependencies": { - "glob": "^7.1.1", - "json-parse-even-better-errors": "^2.3.0", - "normalize-package-data": "^3.0.0", - "npm-normalize-package-bin": "^1.0.0" - }, - "engines": { - "node": ">=10" - } - }, - "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/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/internal-slot": { - "version": "1.0.3", - "resolved": "https://registry.npmjs.org/internal-slot/-/internal-slot-1.0.3.tgz", - "integrity": "sha512-O0DB1JC/sPyZl7cIo78n5dR7eUSwwpYPiXRhTzNxZVAMUuB8vlnRFyLxdrVToks6XPLVnFfbzaVd5WLjhgg+vA==", - "dev": true, - "dependencies": { - "get-intrinsic": "^1.1.0", - "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==", - "engines": { - "node": ">= 0.10" - } - }, - "node_modules/invariant": { - "version": "2.2.4", - "resolved": "https://registry.npmjs.org/invariant/-/invariant-2.2.4.tgz", - "integrity": "sha512-phJfQVBuaJM5raOpJjSfkiD6BpbCE4Ns//LaXl6wGYtUBY83nWS6Rf9tXm2e8VaK60JEjYldbPif/A2B1C2gNA==", - "dependencies": { - "loose-envify": "^1.0.0" - } - }, - "node_modules/ip": { - "version": "1.1.5", - "resolved": "https://registry.npmjs.org/ip/-/ip-1.1.5.tgz", - "integrity": "sha1-vd7XARQpCCjAoDnnLvJfWq7ENUo=", - "dev": true - }, - "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-absolute": { - "version": "0.2.6", - "resolved": "https://registry.npmjs.org/is-absolute/-/is-absolute-0.2.6.tgz", - "integrity": "sha1-IN5p89uULvLYe5wto28XIjWxtes=", - "dependencies": { - "is-relative": "^0.2.1", - "is-windows": "^0.2.0" - }, - "engines": { - "node": ">=0.10.0" - } - }, - "node_modules/is-absolute/node_modules/is-windows": { - "version": "0.2.0", - "resolved": "https://registry.npmjs.org/is-windows/-/is-windows-0.2.0.tgz", - "integrity": "sha1-3hqm1j6indJIc3tp8f+LgALSEIw=", - "engines": { - "node": ">=0.10.0" - } - }, - "node_modules/is-arrayish": { - "version": "0.2.1", - "resolved": "https://registry.npmjs.org/is-arrayish/-/is-arrayish-0.2.1.tgz", - "integrity": "sha1-d8mYQFJ6qOyxqLppe4BkWnqSap0=" - }, - "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==", - "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-buffer": { - "version": "1.1.6", - "resolved": "https://registry.npmjs.org/is-buffer/-/is-buffer-1.1.6.tgz", - "integrity": "sha512-NcdALwpXkTm5Zvvbk7owOUSvVvBKDgKP5/ewfXEznmQFfs4ZRmanOeKBTjRVjka3QFoN6XJ+9F3USqfHqTaU5w==" - }, - "node_modules/is-callable": { - "version": "1.2.4", - "resolved": "https://registry.npmjs.org/is-callable/-/is-callable-1.2.4.tgz", - "integrity": "sha512-nsuwtxZfMX67Oryl9LCQ+upnC0Z0BgpwntpS89m1H/TLF0zNfzfLMV/9Wa/6MZsj0acpEjAO0KF1xT6ZdLl95w==", - "dev": true, - "engines": { - "node": ">= 0.4" - }, - "funding": { - "url": "https://github.com/sponsors/ljharb" - } - }, - "node_modules/is-ci": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/is-ci/-/is-ci-2.0.0.tgz", - "integrity": "sha512-YfJT7rkpQB0updsdHLGWrvhBJfcfzNNawYDNIyQXJz0IViGf75O8EBPKSdvw2rF+LGCsX4FZ8tcr3b19LcZq4w==", - "dev": true, - "dependencies": { - "ci-info": "^2.0.0" - }, - "bin": { - "is-ci": "bin.js" - } - }, - "node_modules/is-core-module": { - "version": "2.8.0", - "resolved": "https://registry.npmjs.org/is-core-module/-/is-core-module-2.8.0.tgz", - "integrity": "sha512-vd15qHsaqrRL7dtH6QNuy0ndJmRDrS9HAM1CAiSifNUFv4x1a0CCVsj18hJ1mShxIG6T2i1sO78MkP56r0nYRw==", - "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-dotfile": { - "version": "1.0.3", - "resolved": "https://registry.npmjs.org/is-dotfile/-/is-dotfile-1.0.3.tgz", - "integrity": "sha1-pqLzL/0t+wT1yiXs0Pa4PPeYoeE=", - "engines": { - "node": ">=0.10.0" - } - }, - "node_modules/is-equal-shallow": { - "version": "0.1.3", - "resolved": "https://registry.npmjs.org/is-equal-shallow/-/is-equal-shallow-0.1.3.tgz", - "integrity": "sha1-IjgJj8Ih3gvPpdnqxMRdY4qhxTQ=", - "dependencies": { - "is-primitive": "^2.0.0" - }, - "engines": { - "node": ">=0.10.0" - } - }, - "node_modules/is-extendable": { - "version": "0.1.1", - "resolved": "https://registry.npmjs.org/is-extendable/-/is-extendable-0.1.1.tgz", - "integrity": "sha1-YrEQ4omkcUGOPsNqYX1HLjAd/Ik=", - "engines": { - "node": ">=0.10.0" - } - }, - "node_modules/is-extglob": { - "version": "2.1.1", - "resolved": "https://registry.npmjs.org/is-extglob/-/is-extglob-2.1.1.tgz", - "integrity": "sha1-qIwCU1eR8C7TfHahueqXc8gz+MI=", - "engines": { - "node": ">=0.10.0" - } - }, - "node_modules/is-finite": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/is-finite/-/is-finite-1.1.0.tgz", - "integrity": "sha512-cdyMtqX/BOqqNBBiKlIVkytNHm49MtMlYyn1zxzvJKWmFMlGzm+ry5BBfYyeY9YmNKbRSo/o7OX9w9ale0wg3w==", - "engines": { - "node": ">=0.10.0" - }, - "funding": { - "url": "https://github.com/sponsors/sindresorhus" - } - }, - "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==", - "engines": { - "node": ">=8" - } - }, - "node_modules/is-generator-function": { - "version": "1.0.10", - "resolved": "https://registry.npmjs.org/is-generator-function/-/is-generator-function-1.0.10.tgz", - "integrity": "sha512-jsEjy9l3yiXEQ+PsXdmBwEPcOxaXWLspKdplFUVI9vq1iZgIekeC0L167qeu86czQaxed3q/Uzuw0swL0irL8A==", - "dependencies": { - "has-tostringtag": "^1.0.0" - }, - "engines": { - "node": ">= 0.4" - }, - "funding": { - "url": "https://github.com/sponsors/ljharb" - } - }, - "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==", - "dependencies": { - "is-extglob": "^2.1.1" - }, - "engines": { - "node": ">=0.10.0" - } - }, - "node_modules/is-installed-globally": { - "version": "0.4.0", - "resolved": "https://registry.npmjs.org/is-installed-globally/-/is-installed-globally-0.4.0.tgz", - "integrity": "sha512-iwGqO3J21aaSkC7jWnHP/difazwS7SFeIqxv6wEtLU8Y5KlzFTjyqcSIT0d8s4+dDhKytsk9PJZ2BkS5eZwQRQ==", - "dev": true, - "dependencies": { - "global-dirs": "^3.0.0", - "is-path-inside": "^3.0.2" - }, - "engines": { - "node": ">=10" - }, - "funding": { - "url": "https://github.com/sponsors/sindresorhus" - } - }, - "node_modules/is-lambda": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/is-lambda/-/is-lambda-1.0.1.tgz", - "integrity": "sha1-PZh3iZ5qU+/AFgUEzeFfgubwYdU=", - "dev": true - }, - "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-npm": { - "version": "5.0.0", - "resolved": "https://registry.npmjs.org/is-npm/-/is-npm-5.0.0.tgz", - "integrity": "sha512-WW/rQLOazUq+ST/bCAVBp/2oMERWLsR7OrKyt052dNDk4DHcDE0/7QSXITlmi+VBcV13DfIbysG3tZJm5RfdBA==", - "dev": true, - "engines": { - "node": ">=10" - }, - "funding": { - "url": "https://github.com/sponsors/sindresorhus" - } - }, - "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==", - "engines": { - "node": ">=0.12.0" - } - }, - "node_modules/is-number-object": { - "version": "1.0.6", - "resolved": "https://registry.npmjs.org/is-number-object/-/is-number-object-1.0.6.tgz", - "integrity": "sha512-bEVOqiRcvo3zO1+G2lVMy+gkkEm9Yh7cDMRusKKu5ZJKPUYSJwICTKZrNKHA2EbSP0Tu0+6B/emsYNHZyn6K8g==", - "dev": true, - "dependencies": { - "has-tostringtag": "^1.0.0" - }, - "engines": { - "node": ">= 0.4" - }, - "funding": { - "url": "https://github.com/sponsors/ljharb" - } - }, - "node_modules/is-obj": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/is-obj/-/is-obj-2.0.0.tgz", - "integrity": "sha512-drqDG3cbczxxEJRoOXcOjtdp1J/lyp1mNn0xaznRs8+muBhgQcrnbspox5X5fOw0HnMnbfDzvnEMEtqDEJEo8w==", - "dev": true, - "engines": { - "node": ">=8" - } - }, - "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": ">=8" - } - }, - "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": "sha1-caUMhCnfync8kqOQpKA7OfzVHT4=", - "dev": true, - "engines": { - "node": ">=0.10.0" - } - }, - "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/is-posix-bracket": { - "version": "0.1.1", - "resolved": "https://registry.npmjs.org/is-posix-bracket/-/is-posix-bracket-0.1.1.tgz", - "integrity": "sha1-MzTceXdDaOkvAW5vvAqI9c1ua8Q=", - "engines": { - "node": ">=0.10.0" - } - }, - "node_modules/is-primitive": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/is-primitive/-/is-primitive-2.0.0.tgz", - "integrity": "sha1-IHurkWOEmcB7Kt8kCkGochADRXU=", - "engines": { - "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-relative": { - "version": "0.2.1", - "resolved": "https://registry.npmjs.org/is-relative/-/is-relative-0.2.1.tgz", - "integrity": "sha1-0n9MfVFtF1+2ENuEu+7yPDvJeqU=", - "dependencies": { - "is-unc-path": "^0.1.1" - }, - "engines": { - "node": ">=0.10.0" - } - }, - "node_modules/is-shared-array-buffer": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/is-shared-array-buffer/-/is-shared-array-buffer-1.0.1.tgz", - "integrity": "sha512-IU0NmyknYZN0rChcKhRO1X8LYz5Isj/Fsqh8NJOSf+N/hCOTwy29F32Ik7a+QszE63IdvmwdTPDd6cZ5pg4cwA==", - "dev": true, - "funding": { - "url": "https://github.com/sponsors/ljharb" - } - }, - "node_modules/is-ssh": { - "version": "1.3.3", - "resolved": "https://registry.npmjs.org/is-ssh/-/is-ssh-1.3.3.tgz", - "integrity": "sha512-NKzJmQzJfEEma3w5cJNcUMxoXfDjz0Zj0eyCalHn2E6VOwlzjZo0yuO2fcBSf8zhFuVCL/82/r5gRcoi6aEPVQ==", - "dev": true, - "dependencies": { - "protocols": "^1.1.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==", - "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-text-path": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/is-text-path/-/is-text-path-1.0.1.tgz", - "integrity": "sha1-Thqg+1G/vLPpJogAE5cgLBd1tm4=", - "dev": true, - "dependencies": { - "text-extensions": "^1.0.0" - }, - "engines": { - "node": ">=0.10.0" - } - }, - "node_modules/is-typedarray": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/is-typedarray/-/is-typedarray-1.0.0.tgz", - "integrity": "sha1-5HnICFjfDBsR3dppQPlgEfzaSpo=", - "dev": true - }, - "node_modules/is-unc-path": { - "version": "0.1.2", - "resolved": "https://registry.npmjs.org/is-unc-path/-/is-unc-path-0.1.2.tgz", - "integrity": "sha1-arBTpyVzwQJQ/0FqOBTDUXivObk=", - "dependencies": { - "unc-path-regex": "^0.1.0" - }, - "engines": { - "node": ">=0.10.0" - } - }, - "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==", - "engines": { - "node": ">=10" - }, - "funding": { - "url": "https://github.com/sponsors/sindresorhus" - } - }, - "node_modules/is-utf8": { - "version": "0.2.1", - "resolved": "https://registry.npmjs.org/is-utf8/-/is-utf8-0.2.1.tgz", - "integrity": "sha1-Sw2hRCEE0bM2NA6AeX6GXPOffXI=" - }, - "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-windows": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/is-windows/-/is-windows-1.0.2.tgz", - "integrity": "sha512-eXK1UInq2bPmjyX6e3VHIzMLobc4J94i4AWn+Hpq3OU5KkrRC96OAcR3PRJ/pGu6m8TRnBHP9dkXQVsT/COVIA==", - "dev": true, - "engines": { - "node": ">=0.10.0" - } - }, - "node_modules/is-yarn-global": { - "version": "0.3.0", - "resolved": "https://registry.npmjs.org/is-yarn-global/-/is-yarn-global-0.3.0.tgz", - "integrity": "sha512-VjSeb/lHmkoyd8ryPVIKvOCn4D1koMqY+vqyjjUfc3xyKtP4dYOxM44sZrnqQSzSds3xyOrUTLTC9LVCVgLngw==", - "dev": true - }, - "node_modules/isarray": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/isarray/-/isarray-1.0.0.tgz", - "integrity": "sha1-u5NdSFgsuhaMBoNJV6VKPgcSTxE=" - }, - "node_modules/isexe": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/isexe/-/isexe-2.0.0.tgz", - "integrity": "sha1-6PvzdNxVb/iUehDcsFctYz8s+hA=" - }, - "node_modules/isobject": { - "version": "3.0.1", - "resolved": "https://registry.npmjs.org/isobject/-/isobject-3.0.1.tgz", - "integrity": "sha1-TkMekrEalzFjaqH5yNHMvP2reN8=", - "engines": { - "node": ">=0.10.0" - } - }, - "node_modules/isstream": { - "version": "0.1.2", - "resolved": "https://registry.npmjs.org/isstream/-/isstream-0.1.2.tgz", - "integrity": "sha1-R+Y/evVa+m+S4VAOaQ64uFKcCZo=", - "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-hook": { - "version": "3.0.0", - "resolved": "https://registry.npmjs.org/istanbul-lib-hook/-/istanbul-lib-hook-3.0.0.tgz", - "integrity": "sha512-Pt/uge1Q9s+5VAZ+pCo16TYMWPBIl+oaNIjgLQxcX0itS6ueeaA+pEfThZpH8WxhFgCiEb8sAJY6MdUKgiIWaQ==", - "dev": true, - "dependencies": { - "append-transform": "^2.0.0" - }, - "engines": { - "node": ">=8" - } - }, - "node_modules/istanbul-lib-instrument": { - "version": "4.0.3", - "resolved": "https://registry.npmjs.org/istanbul-lib-instrument/-/istanbul-lib-instrument-4.0.3.tgz", - "integrity": "sha512-BXgQl9kf4WTCPCCpmFGoJkz/+uhvm7h7PFKUYxh7qarQd3ER33vHG//qaE8eN25l07YqZPpHXU9I09l/RD5aGQ==", - "dev": true, - "dependencies": { - "@babel/core": "^7.7.5", - "@istanbuljs/schema": "^0.1.2", - "istanbul-lib-coverage": "^3.0.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-processinfo": { - "version": "2.0.2", - "resolved": "https://registry.npmjs.org/istanbul-lib-processinfo/-/istanbul-lib-processinfo-2.0.2.tgz", - "integrity": "sha512-kOwpa7z9hme+IBPZMzQ5vdQj8srYgAtaRqeI48NGmAQ+/5yKiHLV0QbYqQpxsdEF0+w14SoB8YbnHKcXE2KnYw==", - "dev": true, - "dependencies": { - "archy": "^1.0.0", - "cross-spawn": "^7.0.0", - "istanbul-lib-coverage": "^3.0.0-alpha.1", - "make-dir": "^3.0.0", - "p-map": "^3.0.0", - "rimraf": "^3.0.0", - "uuid": "^3.3.3" - }, - "engines": { - "node": ">=8" - } - }, - "node_modules/istanbul-lib-processinfo/node_modules/p-map": { - "version": "3.0.0", - "resolved": "https://registry.npmjs.org/p-map/-/p-map-3.0.0.tgz", - "integrity": "sha512-d3qXVTF/s+W+CdJ5A29wywV2n8CQQYahlgz2bFiA+4eVNJbHJodPZ+/gXwPGh0bOqA+j8S+6+ckmvLGPk1QpxQ==", - "dev": true, - "dependencies": { - "aggregate-error": "^3.0.0" - }, - "engines": { - "node": ">=8" - } - }, - "node_modules/istanbul-lib-processinfo/node_modules/uuid": { - "version": "3.4.0", - "resolved": "https://registry.npmjs.org/uuid/-/uuid-3.4.0.tgz", - "integrity": "sha512-HjSDRw6gZE5JMggctHBcjVak08+KEVhSIiDzFnT9S9aegmp85S/bReBVTb4QTFaRNptJ9kuYaNhnbNEOkbKb/A==", - "deprecated": "Please upgrade to version 7 or higher. Older versions may use Math.random() in certain circumstances, which is known to be problematic. See https://v8.dev/blog/math-random for details.", - "dev": true, - "bin": { - "uuid": "bin/uuid" - } - }, - "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-reports": { - "version": "3.1.3", - "resolved": "https://registry.npmjs.org/istanbul-reports/-/istanbul-reports-3.1.3.tgz", - "integrity": "sha512-x9LtDVtfm/t1GFiLl3NffC7hz+I1ragvgX1P/Lg1NlIagifZDKUkuuaAxH/qpwj2IuEfD8G2Bs/UKp+sZ/pKkg==", - "dev": true, - "dependencies": { - "html-escaper": "^2.0.0", - "istanbul-lib-report": "^3.0.0" - }, - "engines": { - "node": ">=8" - } - }, - "node_modules/jest-worker": { - "version": "27.4.5", - "resolved": "https://registry.npmjs.org/jest-worker/-/jest-worker-27.4.5.tgz", - "integrity": "sha512-f2s8kEdy15cv9r7q4KkzGXvlY0JTcmCbMHZBfSQDwW77REr45IDWwd0lksDFeVHH2jJ5pqb90T77XscrjeGzzg==", - "dependencies": { - "@types/node": "*", - "merge-stream": "^2.0.0", - "supports-color": "^8.0.0" - }, - "engines": { - "node": ">= 10.13.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==", - "dependencies": { - "has-flag": "^4.0.0" - }, - "engines": { - "node": ">=10" - }, - "funding": { - "url": "https://github.com/chalk/supports-color?sponsor=1" - } - }, - "node_modules/jju": { - "version": "1.4.0", - "resolved": "https://registry.npmjs.org/jju/-/jju-1.4.0.tgz", - "integrity": "sha1-o6vicYryQaKykE+EpiWXDzia4yo=", - "dev": true - }, - "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==" - }, - "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==", - "dependencies": { - "argparse": "^2.0.1" - }, - "bin": { - "js-yaml": "bin/js-yaml.js" - } - }, - "node_modules/jsbn": { - "version": "0.1.1", - "resolved": "https://registry.npmjs.org/jsbn/-/jsbn-0.1.1.tgz", - "integrity": "sha1-peZUwuWi3rXyAdls77yoDA7y9RM=", - "dev": true - }, - "node_modules/jsesc": { - "version": "2.5.2", - "resolved": "https://registry.npmjs.org/jsesc/-/jsesc-2.5.2.tgz", - "integrity": "sha512-OYu7XEzjkCQ3C5Ps3QIZsQfNpqoJyZZA99wd9aWd05NCtC5pWOkShK2mkL6HXQR6/Cy2lbNdPlZBpuQHXE63gA==", - "bin": { - "jsesc": "bin/jsesc" - }, - "engines": { - "node": ">=4" - } - }, - "node_modules/json-buffer": { - "version": "3.0.0", - "resolved": "https://registry.npmjs.org/json-buffer/-/json-buffer-3.0.0.tgz", - "integrity": "sha1-Wx85evx11ne96Lz8Dkfh+aPZqJg=", - "dev": true - }, - "node_modules/json-parse-better-errors": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/json-parse-better-errors/-/json-parse-better-errors-1.0.2.tgz", - "integrity": "sha512-mrqyZKfX5EhL7hvqcV6WG1yYjnjeuYDzDhhcAAUrq8Po85NBQBJP+ZDUT75qZQ98IkUoBqdkExkukOU7Ts2wrw==" - }, - "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-parse-helpfulerror": { - "version": "1.0.3", - "resolved": "https://registry.npmjs.org/json-parse-helpfulerror/-/json-parse-helpfulerror-1.0.3.tgz", - "integrity": "sha1-E/FM4C7tTpgSl7ZOueO5MuLdE9w=", - "dev": true, - "dependencies": { - "jju": "^1.1.0" - } - }, - "node_modules/json-schema": { - "version": "0.4.0", - "resolved": "https://registry.npmjs.org/json-schema/-/json-schema-0.4.0.tgz", - "integrity": "sha512-es94M3nTIfsEPisRafak+HDLfHXnKBhV3vU5eqPcS3flIWqcxJWgXHXiey3YrpaNsanY5ei1VoYEbOzijuq9BA==" - }, - "node_modules/json-schema-to-ts": { - "version": "1.6.4", - "resolved": "https://registry.npmjs.org/json-schema-to-ts/-/json-schema-to-ts-1.6.4.tgz", - "integrity": "sha512-pR4yQ9DHz6itqswtHCm26mw45FSNfQ9rEQjosaZErhn5J3J2sIViQiz8rDaezjKAhFGpmsoczYVBgGHzFw/stA==", - "dependencies": { - "@types/json-schema": "^7.0.6", - "ts-toolbelt": "^6.15.5" - } - }, - "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==" - }, - "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": "sha1-nbe1lJatPzz+8wp1FC0tkwrXJlE=", - "dev": true - }, - "node_modules/json-stringify-safe": { - "version": "5.0.1", - "resolved": "https://registry.npmjs.org/json-stringify-safe/-/json-stringify-safe-5.0.1.tgz", - "integrity": "sha1-Epai1Y/UXxmg9s4B1lcB4sc1tus=", - "dev": true - }, - "node_modules/json3": { - "version": "3.3.2", - "resolved": "https://registry.npmjs.org/json3/-/json3-3.3.2.tgz", - "integrity": "sha1-PAQ0dD35Pi9cQq7nsZvLSDV19OE=", - "deprecated": "Please use the native JSON object instead of JSON 3" - }, - "node_modules/json5": { - "version": "2.2.0", - "resolved": "https://registry.npmjs.org/json5/-/json5-2.2.0.tgz", - "integrity": "sha512-f+8cldu7X/y7RAJurMEJmdoKXGB/X550w2Nr3tTbezL6RwEE/iMcm+tZnXeoZtKuOq6ft8+CqzEkrIgx1fPoQA==", - "dependencies": { - "minimist": "^1.2.5" - }, - "bin": { - "json5": "lib/cli.js" - }, - "engines": { - "node": ">=6" - } - }, - "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/jsonlines": { - "version": "0.1.1", - "resolved": "https://registry.npmjs.org/jsonlines/-/jsonlines-0.1.1.tgz", - "integrity": "sha1-T80kbcXQ44aRkHxEqwAveC0dlMw=", - "dev": true - }, - "node_modules/jsonparse": { - "version": "1.3.1", - "resolved": "https://registry.npmjs.org/jsonparse/-/jsonparse-1.3.1.tgz", - "integrity": "sha1-P02uSpH6wxX3EGL4UhzCOfE2YoA=", - "dev": true, - "engines": [ - "node >= 0.2.0" - ] - }, - "node_modules/JSONStream": { - "version": "1.3.5", - "resolved": "https://registry.npmjs.org/JSONStream/-/JSONStream-1.3.5.tgz", - "integrity": "sha512-E+iruNOY8VV9s4JEbe1aNEm6MiszPRr/UfcHMz0TQh1BXSxHK+ASV1R6W4HpjBhSeS+54PIsAMCBmwD06LLsqQ==", - "dev": true, - "dependencies": { - "jsonparse": "^1.2.0", - "through": ">=2.2.7 <3" - }, - "bin": { - "JSONStream": "bin.js" - }, - "engines": { - "node": "*" - } - }, - "node_modules/jsonwebtoken": { - "version": "8.5.1", - "resolved": "https://registry.npmjs.org/jsonwebtoken/-/jsonwebtoken-8.5.1.tgz", - "integrity": "sha512-XjwVfRS6jTMsqYs0EsuJ4LGxXV14zQybNd4L2r0UvbVnSF9Af8x7p5MzbJ90Ioz/9TI41/hTCvznF/loiSzn8w==", - "dependencies": { - "jws": "^3.2.2", - "lodash.includes": "^4.3.0", - "lodash.isboolean": "^3.0.3", - "lodash.isinteger": "^4.0.4", - "lodash.isnumber": "^3.0.3", - "lodash.isplainobject": "^4.0.6", - "lodash.isstring": "^4.0.1", - "lodash.once": "^4.0.0", - "ms": "^2.1.1", - "semver": "^5.6.0" - }, - "engines": { - "node": ">=4", - "npm": ">=1.4.28" - } - }, - "node_modules/jsonwebtoken/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/jsonwebtoken/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/jsonwebtoken/node_modules/semver": { - "version": "5.7.1", - "resolved": "https://registry.npmjs.org/semver/-/semver-5.7.1.tgz", - "integrity": "sha512-sauaDf/PZdVgrLTNYHRtpXa1iRiKcaebiKQ1BJdpQlWH2lCvexQdX55snPFyK7QzpudqbCI0qXFfOasHdyNDGQ==", - "bin": { - "semver": "bin/semver" - } - }, - "node_modules/jsprim": { - "version": "1.4.2", - "resolved": "https://registry.npmjs.org/jsprim/-/jsprim-1.4.2.tgz", - "integrity": "sha512-P2bSOMAc/ciLz6DzgjVlGJP9+BrJWu5UDGK70C2iweC5QBIeFf0ZXRvGjEj2uYgrY2MkAAhsSWHDWlFtEroZWw==", - "dev": true, - "dependencies": { - "assert-plus": "1.0.0", - "extsprintf": "1.3.0", - "json-schema": "0.4.0", - "verror": "1.10.0" - }, - "engines": { - "node": ">=0.6.0" - } - }, - "node_modules/jwa": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/jwa/-/jwa-2.0.0.tgz", - "integrity": "sha512-jrZ2Qx916EA+fq9cEAeCROWPTfCwi1IVHqT2tapuqLEVVDKFDENFw1oL+MwrTvH6msKxsd1YTDVw6uKEcsrLEA==", - "optional": true, - "dependencies": { - "buffer-equal-constant-time": "1.0.1", - "ecdsa-sig-formatter": "1.0.11", - "safe-buffer": "^5.0.1" - } - }, - "node_modules/jwk-to-pem": { - "version": "2.0.5", - "resolved": "https://registry.npmjs.org/jwk-to-pem/-/jwk-to-pem-2.0.5.tgz", - "integrity": "sha512-L90jwellhO8jRKYwbssU9ifaMVqajzj3fpRjDKcsDzrslU9syRbFqfkXtT4B89HYAap+xsxNcxgBSB09ig+a7A==", - "optional": true, - "dependencies": { - "asn1.js": "^5.3.0", - "elliptic": "^6.5.4", - "safe-buffer": "^5.0.1" - } - }, - "node_modules/jws": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/jws/-/jws-4.0.0.tgz", - "integrity": "sha512-KDncfTmOZoOMTFG4mBlG0qUIOlc03fmzH+ru6RgYVZhPkyiy/92Owlt/8UEN+a4TXR1FQetfIpJE8ApdvdVxTg==", - "optional": true, - "dependencies": { - "jwa": "^2.0.0", - "safe-buffer": "^5.0.1" - } - }, - "node_modules/keygrip": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/keygrip/-/keygrip-1.1.0.tgz", - "integrity": "sha512-iYSchDJ+liQ8iwbSI2QqsQOvqv58eJCEanyJPJi+Khyu8smkcKSFUCbPwzFcL7YVtZ6eONjqRX/38caJ7QjRAQ==", - "dependencies": { - "tsscmp": "1.0.6" - }, - "engines": { - "node": ">= 0.6" - } - }, - "node_modules/keyv": { - "version": "3.1.0", - "resolved": "https://registry.npmjs.org/keyv/-/keyv-3.1.0.tgz", - "integrity": "sha512-9ykJ/46SN/9KPM/sichzQ7OvXyGDYKGTaDlKMGCAlg2UK8KRy4jb0d8sFc+0Tt0YYnThq8X2RZgCg74RPxgcVA==", - "dev": true, - "dependencies": { - "json-buffer": "3.0.0" - } - }, - "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==", - "engines": { - "node": ">=0.10.0" - } - }, - "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/koa": { - "version": "2.13.4", - "resolved": "https://registry.npmjs.org/koa/-/koa-2.13.4.tgz", - "integrity": "sha512-43zkIKubNbnrULWlHdN5h1g3SEKXOEzoAlRsHOTFpnlDu8JlAOZSMJBLULusuXRequboiwJcj5vtYXKB3k7+2g==", - "dependencies": { - "accepts": "^1.3.5", - "cache-content-type": "^1.0.0", - "content-disposition": "~0.5.2", - "content-type": "^1.0.4", - "cookies": "~0.8.0", - "debug": "^4.3.2", - "delegates": "^1.0.0", - "depd": "^2.0.0", - "destroy": "^1.0.4", - "encodeurl": "^1.0.2", - "escape-html": "^1.0.3", - "fresh": "~0.5.2", - "http-assert": "^1.3.0", - "http-errors": "^1.6.3", - "is-generator-function": "^1.0.7", - "koa-compose": "^4.1.0", - "koa-convert": "^2.0.0", - "on-finished": "^2.3.0", - "only": "~0.0.2", - "parseurl": "^1.3.2", - "statuses": "^1.5.0", - "type-is": "^1.6.16", - "vary": "^1.1.2" - }, - "engines": { - "node": "^4.8.4 || ^6.10.1 || ^7.10.1 || >= 8.1.4" - } - }, - "node_modules/koa-bodyparser": { - "version": "4.3.0", - "resolved": "https://registry.npmjs.org/koa-bodyparser/-/koa-bodyparser-4.3.0.tgz", - "integrity": "sha512-uyV8G29KAGwZc4q/0WUAjH+Tsmuv9ImfBUF2oZVyZtaeo0husInagyn/JH85xMSxM0hEk/mbCII5ubLDuqW/Rw==", - "dependencies": { - "co-body": "^6.0.0", - "copy-to": "^2.0.1" - }, - "engines": { - "node": ">=8.0.0" - } - }, - "node_modules/koa-compose": { - "version": "4.1.0", - "resolved": "https://registry.npmjs.org/koa-compose/-/koa-compose-4.1.0.tgz", - "integrity": "sha512-8ODW8TrDuMYvXRwra/Kh7/rJo9BtOfPc6qO8eAfC80CnCvSjSl0bkRM24X6/XBBEyj0v1nRUQ1LyOy3dbqOWXw==" - }, - "node_modules/koa-convert": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/koa-convert/-/koa-convert-2.0.0.tgz", - "integrity": "sha512-asOvN6bFlSnxewce2e/DK3p4tltyfC4VM7ZwuTuepI7dEQVcvpyFuBcEARu1+Hxg8DIwytce2n7jrZtRlPrARA==", - "dependencies": { - "co": "^4.6.0", - "koa-compose": "^4.1.0" - }, - "engines": { - "node": ">= 10" - } - }, - "node_modules/koa-qs": { - "version": "3.0.0", - "resolved": "https://registry.npmjs.org/koa-qs/-/koa-qs-3.0.0.tgz", - "integrity": "sha512-05IB5KirwMs3heWW26iTz46HuMAtrlrRMus/aNH1BRDocLyF/099EtCB0MIfQpRuT0TISvaTsWwSy2gctIWiGA==", - "dependencies": { - "merge-descriptors": "^1.0.1", - "qs": "^6.9.4" - }, - "engines": { - "node": ">= 8" - } - }, - "node_modules/koa/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/lasso": { - "version": "2.11.24", - "resolved": "https://registry.npmjs.org/lasso/-/lasso-2.11.24.tgz", - "integrity": "sha512-q3FixSAt5I4OeUUadKEWfR7fPivFWhPBwqSAYtda8PwVKivAZ1DFyNFgP3l/1dc4ZfGuZt8R8rcU0YrL11wVag==", - "dependencies": { - "app-module-path": "^1.1.0", - "app-root-dir": "^1.0.2", - "async": "^0.9.2", - "browser-refresh-client": "^1.1.4", - "glob": "^7.1.1", - "lasso-caching-fs": "^1.0.2", - "lasso-image": "^1.0.12", - "lasso-minify-css": "^1.1.4", - "lasso-minify-js": "^1.4.0", - "lasso-package-root": "^1.0.1", - "lasso-require": "^3.4.4", - "lasso-resolve-css-urls": "^2.0.2", - "lasso-resolve-from": "^1.2.0", - "marko": "^4.2.8", - "mime": "^1.2.11", - "mkdirp": "^0.5.1", - "property-handlers": "^1.1.1", - "raptor-async": "^1.1.3", - "raptor-cache": "^1.2.3", - "raptor-detect": "^1.0.1", - "raptor-logging": "^1.1.2", - "raptor-objects": "^1.0.2", - "raptor-polyfill": "^1.0.2", - "raptor-promises": "^1.0.3", - "raptor-regexp": "^1.0.1", - "raptor-strings": "^1.0.2", - "raptor-util": "^3.2.0", - "resolve-from": "^1.0.1", - "send": "^0.13.2", - "strip-json-comments": "^2.0.1", - "through": "^2.3.8" - } - }, - "node_modules/lasso-babel-transform": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/lasso-babel-transform/-/lasso-babel-transform-1.0.2.tgz", - "integrity": "sha512-8AUeZ22LC5onZ6lanBRrdJKYq2D8EVtUoEm3UfMV/lNHD/8NUQEITZ+uRgTMxmSmAV0y68j06hsEUe4lf0tVVQ==", - "dependencies": { - "babel-core": "^6.0.14", - "lasso-caching-fs": "^1.0.1", - "lasso-package-root": "^1.0.0", - "strip-json-comments": "^2.0.1" - } - }, - "node_modules/lasso-babel-transform/node_modules/strip-json-comments": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/strip-json-comments/-/strip-json-comments-2.0.1.tgz", - "integrity": "sha1-PFMZQukIwml8DsNEhYwobHygpgo=", - "engines": { - "node": ">=0.10.0" - } - }, - "node_modules/lasso-caching-fs": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/lasso-caching-fs/-/lasso-caching-fs-1.0.2.tgz", - "integrity": "sha1-m+TrHwaqwSYDRMrq70LC8AhusQ0=", - "dependencies": { - "raptor-async": "^1.1.2" - } - }, - "node_modules/lasso-image": { - "version": "1.0.13", - "resolved": "https://registry.npmjs.org/lasso-image/-/lasso-image-1.0.13.tgz", - "integrity": "sha1-ZZOAhS/AnTj5ZL8cEQTv/bzpYOE=", - "dependencies": { - "image-size": "^0.3.3", - "raptor-async": "^1.0.1" - } - }, - "node_modules/lasso-loader": { - "version": "3.0.2", - "resolved": "https://registry.npmjs.org/lasso-loader/-/lasso-loader-3.0.2.tgz", - "integrity": "sha1-29tV1fcu6zpbrnSn4xtrtf8t0JM=", - "dependencies": { - "events": "^1.0.2", - "raptor-util": "^1.0.0" - } - }, - "node_modules/lasso-loader/node_modules/events": { - "version": "1.1.1", - "resolved": "https://registry.npmjs.org/events/-/events-1.1.1.tgz", - "integrity": "sha1-nr23Y1rQmccNzEwqH1AEKI6L2SQ=", - "engines": { - "node": ">=0.4.x" - } - }, - "node_modules/lasso-loader/node_modules/raptor-util": { - "version": "1.1.2", - "resolved": "https://registry.npmjs.org/raptor-util/-/raptor-util-1.1.2.tgz", - "integrity": "sha1-8u6AdqmuPq4uZWcuRqIgB0+i3/M=" - }, - "node_modules/lasso-minify-css": { - "version": "1.1.4", - "resolved": "https://registry.npmjs.org/lasso-minify-css/-/lasso-minify-css-1.1.4.tgz", - "integrity": "sha1-mqlNuBeL8GshR0zDDKY0l10TwB8=", - "dependencies": { - "sqwish": "~0.2.1" - } - }, - "node_modules/lasso-minify-js": { - "version": "1.4.0", - "resolved": "https://registry.npmjs.org/lasso-minify-js/-/lasso-minify-js-1.4.0.tgz", - "integrity": "sha1-8ij0J7tkebSzdxQeN8Tp34Fznks=", - "dependencies": { - "uglify-js": "^2.7.3" - } - }, - "node_modules/lasso-minify-js/node_modules/camelcase": { - "version": "1.2.1", - "resolved": "https://registry.npmjs.org/camelcase/-/camelcase-1.2.1.tgz", - "integrity": "sha1-m7UwTS4LVmmLLHWLCKPqqdqlijk=", - "engines": { - "node": ">=0.10.0" - } - }, - "node_modules/lasso-minify-js/node_modules/cliui": { - "version": "2.1.0", - "resolved": "https://registry.npmjs.org/cliui/-/cliui-2.1.0.tgz", - "integrity": "sha1-S0dXYP+AJkx2LDoXGQMukcf+oNE=", - "dependencies": { - "center-align": "^0.1.1", - "right-align": "^0.1.1", - "wordwrap": "0.0.2" - } - }, - "node_modules/lasso-minify-js/node_modules/source-map": { - "version": "0.5.7", - "resolved": "https://registry.npmjs.org/source-map/-/source-map-0.5.7.tgz", - "integrity": "sha1-igOdLRAh0i0eoUyA2OpGi6LvP8w=", - "engines": { - "node": ">=0.10.0" - } - }, - "node_modules/lasso-minify-js/node_modules/uglify-js": { - "version": "2.8.29", - "resolved": "https://registry.npmjs.org/uglify-js/-/uglify-js-2.8.29.tgz", - "integrity": "sha1-KcVzMUgFe7Th913zW3qcty5qWd0=", - "dependencies": { - "source-map": "~0.5.1", - "yargs": "~3.10.0" - }, - "bin": { - "uglifyjs": "bin/uglifyjs" - }, - "engines": { - "node": ">=0.8.0" - }, - "optionalDependencies": { - "uglify-to-browserify": "~1.0.0" - } - }, - "node_modules/lasso-minify-js/node_modules/wordwrap": { - "version": "0.0.2", - "resolved": "https://registry.npmjs.org/wordwrap/-/wordwrap-0.0.2.tgz", - "integrity": "sha1-t5Zpu0LstAn4PVg8rVLKF+qhZD8=", - "engines": { - "node": ">=0.4.0" - } - }, - "node_modules/lasso-minify-js/node_modules/yargs": { - "version": "3.10.0", - "resolved": "https://registry.npmjs.org/yargs/-/yargs-3.10.0.tgz", - "integrity": "sha1-9+572FfdfB0tOMDnTvvWgdFDH9E=", - "dependencies": { - "camelcase": "^1.0.2", - "cliui": "^2.1.0", - "decamelize": "^1.0.0", - "window-size": "0.1.0" - } - }, - "node_modules/lasso-modules-client": { - "version": "2.0.7", - "resolved": "https://registry.npmjs.org/lasso-modules-client/-/lasso-modules-client-2.0.7.tgz", - "integrity": "sha512-yYqHNy5OnZGAtKiFIx+K9F6szWxZhRibA3PVi+P2eCfQb9uKCrZnDjea+s4s9M8UXWEm/Af2mrHdx1PMKTSMJQ==", - "dependencies": { - "lasso-package-root": "^1.0.0", - "raptor-polyfill": "^1.0.2" - } - }, - "node_modules/lasso-package-root": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/lasso-package-root/-/lasso-package-root-1.0.1.tgz", - "integrity": "sha1-mX0OcfQdA8Xw+gmlvCmNeW+LLCM=", - "dependencies": { - "lasso-caching-fs": "^1.0.0" - } - }, - "node_modules/lasso-require": { - "version": "3.5.0", - "resolved": "https://registry.npmjs.org/lasso-require/-/lasso-require-3.5.0.tgz", - "integrity": "sha512-qXBGpZMER5Gtuw3BCBPvfvEK3Vu9MR+ekPRGvKfpuLa+OYSHL6vvcmrQIZJqrCSwCutlge+JNKwCxp6gtbQatQ==", - "dependencies": { - "assert": "^1.4.1", - "babel-core": "^6.26.3", - "babel-preset-env": "^1.7.0", - "buffer": "^5.2.1", - "clone": "^2.1.2", - "escodegen": "^1.11.0", - "esprima": "^4.0.1", - "estraverse": "^4.2.0", - "events": "^3.0.0", - "ignore": "^5.0.2", - "lasso-caching-fs": "^1.0.2", - "lasso-loader": "^3.0.2", - "lasso-modules-client": "^2.0.5", - "lasso-package-root": "^1.0.1", - "lasso-resolve-from": "^1.2.0", - "mkdirp": "^0.5.1", - "path-browserify": "1.0.0", - "process": "^0.11.10", - "raptor-async": "^1.1.3", - "raptor-logging": "^1.1.3", - "raptor-polyfill": "^1.1.0", - "raptor-promises": "^1.0.3", - "raptor-util": "^1.1.2", - "resolve-from": "^4.0.0", - "stream-browserify": "^2.0.1", - "string_decoder": "^1.1.1", - "through": "^2.3.8", - "url": "^0.11.0", - "util": "^0.11.0" - } - }, - "node_modules/lasso-require/node_modules/clone": { - "version": "2.1.2", - "resolved": "https://registry.npmjs.org/clone/-/clone-2.1.2.tgz", - "integrity": "sha1-G39Ln1kfHo+DZwQBYANFoCiHQ18=", - "engines": { - "node": ">=0.8" - } - }, - "node_modules/lasso-require/node_modules/mkdirp": { - "version": "0.5.5", - "resolved": "https://registry.npmjs.org/mkdirp/-/mkdirp-0.5.5.tgz", - "integrity": "sha512-NKmAlESf6jMGym1++R0Ra7wvhV+wFW63FaSOFPwRahvea0gMUcGUhVeAg/0BC0wiv9ih5NYPB1Wn1UEI1/L+xQ==", - "dependencies": { - "minimist": "^1.2.5" - }, - "bin": { - "mkdirp": "bin/cmd.js" - } - }, - "node_modules/lasso-require/node_modules/raptor-util": { - "version": "1.1.2", - "resolved": "https://registry.npmjs.org/raptor-util/-/raptor-util-1.1.2.tgz", - "integrity": "sha1-8u6AdqmuPq4uZWcuRqIgB0+i3/M=" - }, - "node_modules/lasso-resolve-css-urls": { - "version": "2.0.2", - "resolved": "https://registry.npmjs.org/lasso-resolve-css-urls/-/lasso-resolve-css-urls-2.0.2.tgz", - "integrity": "sha1-VeWOTvLCu9nk7I+jliBv1KAVdME=", - "dependencies": { - "lasso-resolve-from": "^1.0.1", - "raptor-css-parser": "^1.0.2" - } - }, - "node_modules/lasso-resolve-from": { - "version": "1.2.0", - "resolved": "https://registry.npmjs.org/lasso-resolve-from/-/lasso-resolve-from-1.2.0.tgz", - "integrity": "sha1-v7I0Rnr7abUwn1aLpFnMgyBiHG4=", - "dependencies": { - "is-absolute": "^0.2.3", - "lasso-caching-fs": "^1.0.1", - "raptor-util": "^1.0.10", - "resolve-from": "^2.0.0" - } - }, - "node_modules/lasso-resolve-from/node_modules/raptor-util": { - "version": "1.1.2", - "resolved": "https://registry.npmjs.org/raptor-util/-/raptor-util-1.1.2.tgz", - "integrity": "sha1-8u6AdqmuPq4uZWcuRqIgB0+i3/M=" - }, - "node_modules/lasso-resolve-from/node_modules/resolve-from": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/resolve-from/-/resolve-from-2.0.0.tgz", - "integrity": "sha1-lICrIOlP+h2egKgEx+oUdhGWa1c=", - "engines": { - "node": ">=0.10.0" - } - }, - "node_modules/lasso/node_modules/async": { - "version": "0.9.2", - "resolved": "https://registry.npmjs.org/async/-/async-0.9.2.tgz", - "integrity": "sha1-rqdNXmHB+JlhO/ZL2mbUx48v0X0=" - }, - "node_modules/lasso/node_modules/debug": { - "version": "2.2.0", - "resolved": "https://registry.npmjs.org/debug/-/debug-2.2.0.tgz", - "integrity": "sha1-+HBX6ZWxofauaklgZkE3vFbwOdo=", - "dependencies": { - "ms": "0.7.1" - } - }, - "node_modules/lasso/node_modules/etag": { - "version": "1.7.0", - "resolved": "https://registry.npmjs.org/etag/-/etag-1.7.0.tgz", - "integrity": "sha1-A9MLX2fdbmMtKUXTDWZScxo01dg=", - "engines": { - "node": ">= 0.6" - } - }, - "node_modules/lasso/node_modules/fresh": { - "version": "0.3.0", - "resolved": "https://registry.npmjs.org/fresh/-/fresh-0.3.0.tgz", - "integrity": "sha1-ZR+DjiJCTnVm3hYdg1jKoZn4PU8=", - "engines": { - "node": ">= 0.6" - } - }, - "node_modules/lasso/node_modules/http-errors": { - "version": "1.3.1", - "resolved": "https://registry.npmjs.org/http-errors/-/http-errors-1.3.1.tgz", - "integrity": "sha1-GX4izevUGYWF6GlO9nhhl7ke2UI=", - "dependencies": { - "inherits": "~2.0.1", - "statuses": "1" - }, - "engines": { - "node": ">= 0.6" - } - }, - "node_modules/lasso/node_modules/mime": { - "version": "1.3.4", - "resolved": "https://registry.npmjs.org/mime/-/mime-1.3.4.tgz", - "integrity": "sha1-EV+eO2s9rylZmDyzjxSaLUDrXVM=", - "bin": { - "mime": "cli.js" - } - }, - "node_modules/lasso/node_modules/mkdirp": { - "version": "0.5.5", - "resolved": "https://registry.npmjs.org/mkdirp/-/mkdirp-0.5.5.tgz", - "integrity": "sha512-NKmAlESf6jMGym1++R0Ra7wvhV+wFW63FaSOFPwRahvea0gMUcGUhVeAg/0BC0wiv9ih5NYPB1Wn1UEI1/L+xQ==", - "dependencies": { - "minimist": "^1.2.5" - }, - "bin": { - "mkdirp": "bin/cmd.js" - } - }, - "node_modules/lasso/node_modules/ms": { - "version": "0.7.1", - "resolved": "https://registry.npmjs.org/ms/-/ms-0.7.1.tgz", - "integrity": "sha1-nNE8A62/8ltl7/3nzoZO6VIBcJg=" - }, - "node_modules/lasso/node_modules/range-parser": { - "version": "1.0.3", - "resolved": "https://registry.npmjs.org/range-parser/-/range-parser-1.0.3.tgz", - "integrity": "sha1-aHKCNTXGkuLCoBA4Jq/YLC4P8XU=", - "engines": { - "node": ">= 0.6" - } - }, - "node_modules/lasso/node_modules/resolve-from": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/resolve-from/-/resolve-from-1.0.1.tgz", - "integrity": "sha1-Jsv+k10a7uq7Kbw/5a6wHpPUQiY=", - "engines": { - "node": ">=0.10.0" - } - }, - "node_modules/lasso/node_modules/send": { - "version": "0.13.2", - "resolved": "https://registry.npmjs.org/send/-/send-0.13.2.tgz", - "integrity": "sha1-dl52B8gFVFK7pvCwUllTUJhgNt4=", - "dependencies": { - "debug": "~2.2.0", - "depd": "~1.1.0", - "destroy": "~1.0.4", - "escape-html": "~1.0.3", - "etag": "~1.7.0", - "fresh": "0.3.0", - "http-errors": "~1.3.1", - "mime": "1.3.4", - "ms": "0.7.1", - "on-finished": "~2.3.0", - "range-parser": "~1.0.3", - "statuses": "~1.2.1" - }, - "engines": { - "node": ">= 0.8.0" - } - }, - "node_modules/lasso/node_modules/statuses": { - "version": "1.2.1", - "resolved": "https://registry.npmjs.org/statuses/-/statuses-1.2.1.tgz", - "integrity": "sha1-3e1FzBglbVHtQK7BQkidXGECbSg=" - }, - "node_modules/lasso/node_modules/strip-json-comments": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/strip-json-comments/-/strip-json-comments-2.0.1.tgz", - "integrity": "sha1-PFMZQukIwml8DsNEhYwobHygpgo=", - "engines": { - "node": ">=0.10.0" - } - }, - "node_modules/latest-version": { - "version": "5.1.0", - "resolved": "https://registry.npmjs.org/latest-version/-/latest-version-5.1.0.tgz", - "integrity": "sha512-weT+r0kTkRQdCdYCNtkMwWXQTMEswKrFBkm4ckQOMVhhqhIMI1UT2hMj+1iigIhgSZm5gTmrRXBNoGUgaTY1xA==", - "dev": true, - "dependencies": { - "package-json": "^6.3.0" - }, - "engines": { - "node": ">=8" - } - }, - "node_modules/lazy-cache": { - "version": "1.0.4", - "resolved": "https://registry.npmjs.org/lazy-cache/-/lazy-cache-1.0.4.tgz", - "integrity": "sha1-odePw6UEdMuAhF07O24dpJpEbo4=", - "engines": { - "node": ">=0.10.0" - } - }, - "node_modules/lerna": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/lerna/-/lerna-4.0.0.tgz", - "integrity": "sha512-DD/i1znurfOmNJb0OBw66NmNqiM8kF6uIrzrJ0wGE3VNdzeOhz9ziWLYiRaZDGGwgbcjOo6eIfcx9O5Qynz+kg==", - "dev": true, - "dependencies": { - "@lerna/add": "4.0.0", - "@lerna/bootstrap": "4.0.0", - "@lerna/changed": "4.0.0", - "@lerna/clean": "4.0.0", - "@lerna/cli": "4.0.0", - "@lerna/create": "4.0.0", - "@lerna/diff": "4.0.0", - "@lerna/exec": "4.0.0", - "@lerna/import": "4.0.0", - "@lerna/info": "4.0.0", - "@lerna/init": "4.0.0", - "@lerna/link": "4.0.0", - "@lerna/list": "4.0.0", - "@lerna/publish": "4.0.0", - "@lerna/run": "4.0.0", - "@lerna/version": "4.0.0", - "import-local": "^3.0.2", - "npmlog": "^4.1.2" - }, - "bin": { - "lerna": "cli.js" - }, - "engines": { - "node": ">= 10.18.0" - } - }, - "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/libnpmaccess": { - "version": "4.0.3", - "resolved": "https://registry.npmjs.org/libnpmaccess/-/libnpmaccess-4.0.3.tgz", - "integrity": "sha512-sPeTSNImksm8O2b6/pf3ikv4N567ERYEpeKRPSmqlNt1dTZbvgpJIzg5vAhXHpw2ISBsELFRelk0jEahj1c6nQ==", - "dev": true, - "dependencies": { - "aproba": "^2.0.0", - "minipass": "^3.1.1", - "npm-package-arg": "^8.1.2", - "npm-registry-fetch": "^11.0.0" - }, - "engines": { - "node": ">=10" - } - }, - "node_modules/libnpmaccess/node_modules/make-fetch-happen": { - "version": "9.1.0", - "resolved": "https://registry.npmjs.org/make-fetch-happen/-/make-fetch-happen-9.1.0.tgz", - "integrity": "sha512-+zopwDy7DNknmwPQplem5lAZX/eCOzSvSNNcSKm5eVwTkOBzoktEfXsa9L23J/GIRhxRsaxzkPEhrJEpE2F4Gg==", - "dev": true, - "dependencies": { - "agentkeepalive": "^4.1.3", - "cacache": "^15.2.0", - "http-cache-semantics": "^4.1.0", - "http-proxy-agent": "^4.0.1", - "https-proxy-agent": "^5.0.0", - "is-lambda": "^1.0.1", - "lru-cache": "^6.0.0", - "minipass": "^3.1.3", - "minipass-collect": "^1.0.2", - "minipass-fetch": "^1.3.2", - "minipass-flush": "^1.0.5", - "minipass-pipeline": "^1.2.4", - "negotiator": "^0.6.2", - "promise-retry": "^2.0.1", - "socks-proxy-agent": "^6.0.0", - "ssri": "^8.0.0" - }, - "engines": { - "node": ">= 10" - } - }, - "node_modules/libnpmaccess/node_modules/npm-registry-fetch": { - "version": "11.0.0", - "resolved": "https://registry.npmjs.org/npm-registry-fetch/-/npm-registry-fetch-11.0.0.tgz", - "integrity": "sha512-jmlgSxoDNuhAtxUIG6pVwwtz840i994dL14FoNVZisrmZW5kWd63IUTNv1m/hyRSGSqWjCUp/YZlS1BJyNp9XA==", - "dev": true, - "dependencies": { - "make-fetch-happen": "^9.0.1", - "minipass": "^3.1.3", - "minipass-fetch": "^1.3.0", - "minipass-json-stream": "^1.0.1", - "minizlib": "^2.0.0", - "npm-package-arg": "^8.0.0" - }, - "engines": { - "node": ">=10" - } - }, - "node_modules/libnpmaccess/node_modules/socks-proxy-agent": { - "version": "6.1.1", - "resolved": "https://registry.npmjs.org/socks-proxy-agent/-/socks-proxy-agent-6.1.1.tgz", - "integrity": "sha512-t8J0kG3csjA4g6FTbsMOWws+7R7vuRC8aQ/wy3/1OWmsgwA68zs/+cExQ0koSitUDXqhufF/YJr9wtNMZHw5Ew==", - "dev": true, - "dependencies": { - "agent-base": "^6.0.2", - "debug": "^4.3.1", - "socks": "^2.6.1" - }, - "engines": { - "node": ">= 10" - } - }, - "node_modules/libnpmconfig": { - "version": "1.2.1", - "resolved": "https://registry.npmjs.org/libnpmconfig/-/libnpmconfig-1.2.1.tgz", - "integrity": "sha512-9esX8rTQAHqarx6qeZqmGQKBNZR5OIbl/Ayr0qQDy3oXja2iFVQQI81R6GZ2a02bSNZ9p3YOGX1O6HHCb1X7kA==", - "dev": true, - "dependencies": { - "figgy-pudding": "^3.5.1", - "find-up": "^3.0.0", - "ini": "^1.3.5" - } - }, - "node_modules/libnpmconfig/node_modules/find-up": { - "version": "3.0.0", - "resolved": "https://registry.npmjs.org/find-up/-/find-up-3.0.0.tgz", - "integrity": "sha512-1yD6RmLI1XBfxugvORwlck6f75tYL+iR0jqwsOrOxMZyGYqUuDhJ0l4AXdO1iX/FTs9cBAMEk1gWSEx1kSbylg==", - "dev": true, - "dependencies": { - "locate-path": "^3.0.0" - }, - "engines": { - "node": ">=6" - } - }, - "node_modules/libnpmconfig/node_modules/locate-path": { - "version": "3.0.0", - "resolved": "https://registry.npmjs.org/locate-path/-/locate-path-3.0.0.tgz", - "integrity": "sha512-7AO748wWnIhNqAuaty2ZWHkQHRSNfPVIsPIfwEOWO22AmaoVrWavlOcMR5nzTLNYvp36X220/maaRsrec1G65A==", - "dev": true, - "dependencies": { - "p-locate": "^3.0.0", - "path-exists": "^3.0.0" - }, - "engines": { - "node": ">=6" - } - }, - "node_modules/libnpmconfig/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/libnpmconfig/node_modules/p-locate": { - "version": "3.0.0", - "resolved": "https://registry.npmjs.org/p-locate/-/p-locate-3.0.0.tgz", - "integrity": "sha512-x+12w/To+4GFfgJhBEpiDcLozRJGegY+Ei7/z0tSLkMmxGZNybVMSfWj9aJn8Z5Fc7dBUNJOOVgPv2H7IwulSQ==", - "dev": true, - "dependencies": { - "p-limit": "^2.0.0" - }, - "engines": { - "node": ">=6" - } - }, - "node_modules/libnpmconfig/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/libnpmconfig/node_modules/path-exists": { - "version": "3.0.0", - "resolved": "https://registry.npmjs.org/path-exists/-/path-exists-3.0.0.tgz", - "integrity": "sha1-zg6+ql94yxiSXqfYENe1mwEP1RU=", - "dev": true, - "engines": { - "node": ">=4" - } - }, - "node_modules/libnpmpublish": { - "version": "4.0.2", - "resolved": "https://registry.npmjs.org/libnpmpublish/-/libnpmpublish-4.0.2.tgz", - "integrity": "sha512-+AD7A2zbVeGRCFI2aO//oUmapCwy7GHqPXFJh3qpToSRNU+tXKJ2YFUgjt04LPPAf2dlEH95s6EhIHM1J7bmOw==", - "dev": true, - "dependencies": { - "normalize-package-data": "^3.0.2", - "npm-package-arg": "^8.1.2", - "npm-registry-fetch": "^11.0.0", - "semver": "^7.1.3", - "ssri": "^8.0.1" - }, - "engines": { - "node": ">=10" - } - }, - "node_modules/libnpmpublish/node_modules/make-fetch-happen": { - "version": "9.1.0", - "resolved": "https://registry.npmjs.org/make-fetch-happen/-/make-fetch-happen-9.1.0.tgz", - "integrity": "sha512-+zopwDy7DNknmwPQplem5lAZX/eCOzSvSNNcSKm5eVwTkOBzoktEfXsa9L23J/GIRhxRsaxzkPEhrJEpE2F4Gg==", - "dev": true, - "dependencies": { - "agentkeepalive": "^4.1.3", - "cacache": "^15.2.0", - "http-cache-semantics": "^4.1.0", - "http-proxy-agent": "^4.0.1", - "https-proxy-agent": "^5.0.0", - "is-lambda": "^1.0.1", - "lru-cache": "^6.0.0", - "minipass": "^3.1.3", - "minipass-collect": "^1.0.2", - "minipass-fetch": "^1.3.2", - "minipass-flush": "^1.0.5", - "minipass-pipeline": "^1.2.4", - "negotiator": "^0.6.2", - "promise-retry": "^2.0.1", - "socks-proxy-agent": "^6.0.0", - "ssri": "^8.0.0" - }, - "engines": { - "node": ">= 10" - } - }, - "node_modules/libnpmpublish/node_modules/npm-registry-fetch": { - "version": "11.0.0", - "resolved": "https://registry.npmjs.org/npm-registry-fetch/-/npm-registry-fetch-11.0.0.tgz", - "integrity": "sha512-jmlgSxoDNuhAtxUIG6pVwwtz840i994dL14FoNVZisrmZW5kWd63IUTNv1m/hyRSGSqWjCUp/YZlS1BJyNp9XA==", - "dev": true, - "dependencies": { - "make-fetch-happen": "^9.0.1", - "minipass": "^3.1.3", - "minipass-fetch": "^1.3.0", - "minipass-json-stream": "^1.0.1", - "minizlib": "^2.0.0", - "npm-package-arg": "^8.0.0" - }, - "engines": { - "node": ">=10" - } - }, - "node_modules/libnpmpublish/node_modules/socks-proxy-agent": { - "version": "6.1.1", - "resolved": "https://registry.npmjs.org/socks-proxy-agent/-/socks-proxy-agent-6.1.1.tgz", - "integrity": "sha512-t8J0kG3csjA4g6FTbsMOWws+7R7vuRC8aQ/wy3/1OWmsgwA68zs/+cExQ0koSitUDXqhufF/YJr9wtNMZHw5Ew==", - "dev": true, - "dependencies": { - "agent-base": "^6.0.2", - "debug": "^4.3.1", - "socks": "^2.6.1" - }, - "engines": { - "node": ">= 10" - } - }, - "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/listener-tracker": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/listener-tracker/-/listener-tracker-2.0.0.tgz", - "integrity": "sha1-OWCLQ1wJAfpVECF8FFJyjWvBm18=" - }, - "node_modules/load-json-file": { - "version": "6.2.0", - "resolved": "https://registry.npmjs.org/load-json-file/-/load-json-file-6.2.0.tgz", - "integrity": "sha512-gUD/epcRms75Cw8RT1pUdHugZYM5ce64ucs2GEISABwkRsOQr0q2wm/MV2TKThycIe5e0ytRweW2RZxclogCdQ==", - "dev": true, - "dependencies": { - "graceful-fs": "^4.1.15", - "parse-json": "^5.0.0", - "strip-bom": "^4.0.0", - "type-fest": "^0.6.0" - }, - "engines": { - "node": ">=8" - } - }, - "node_modules/load-json-file/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/loader-runner": { - "version": "4.2.0", - "resolved": "https://registry.npmjs.org/loader-runner/-/loader-runner-4.2.0.tgz", - "integrity": "sha512-92+huvxMvYlMzMt0iIOukcwYBFpkYJdpl2xsZ7LrlayO7E8SOv+JJUEK17B/dJIHAOLMfh2dZZ/Y18WgmGtYNw==", - "engines": { - "node": ">=6.11.5" - } - }, - "node_modules/loader-utils": { - "version": "1.4.0", - "resolved": "https://registry.npmjs.org/loader-utils/-/loader-utils-1.4.0.tgz", - "integrity": "sha512-qH0WSMBtn/oHuwjy/NucEgbx5dbxxnxup9s4PVXJUDHZBQY+s0NWA9rJf53RBnQZxfch7euUui7hpoAPvALZdA==", - "dependencies": { - "big.js": "^5.2.2", - "emojis-list": "^3.0.0", - "json5": "^1.0.1" - }, - "engines": { - "node": ">=4.0.0" - } - }, - "node_modules/loader-utils/node_modules/json5": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/json5/-/json5-1.0.1.tgz", - "integrity": "sha512-aKS4WQjPenRxiQsC93MNfjx+nbF4PAdYzmd/1JIj8HYzqfbu86beTuNgXDzPknWk0n0uARlyewZo4s++ES36Ow==", - "dependencies": { - "minimist": "^1.2.0" - }, - "bin": { - "json5": "lib/cli.js" - } - }, - "node_modules/locate-path": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/locate-path/-/locate-path-2.0.0.tgz", - "integrity": "sha1-K1aLJl7slExtnA3pw9u7ygNUzY4=", - "dependencies": { - "p-locate": "^2.0.0", - "path-exists": "^3.0.0" - }, - "engines": { - "node": ">=4" - } - }, - "node_modules/locate-path/node_modules/path-exists": { - "version": "3.0.0", - "resolved": "https://registry.npmjs.org/path-exists/-/path-exists-3.0.0.tgz", - "integrity": "sha1-zg6+ql94yxiSXqfYENe1mwEP1RU=", - "engines": { - "node": ">=4" - } - }, - "node_modules/lodash": { - "version": "4.17.21", - "resolved": "https://registry.npmjs.org/lodash/-/lodash-4.17.21.tgz", - "integrity": "sha512-v2kDEe57lecTulaDIuNTPy3Ry4gLGJ6Z1O3vE1krgXZNrsQ+LFTGHVxVjcXPs17LhbZVGedAJv8XZ1tvj5FvSg==" - }, - "node_modules/lodash._baseassign": { - "version": "3.2.0", - "resolved": "https://registry.npmjs.org/lodash._baseassign/-/lodash._baseassign-3.2.0.tgz", - "integrity": "sha1-jDigmVAPIVrQnlnxci/QxSv+Ck4=", - "dependencies": { - "lodash._basecopy": "^3.0.0", - "lodash.keys": "^3.0.0" - } - }, - "node_modules/lodash._basecopy": { - "version": "3.0.1", - "resolved": "https://registry.npmjs.org/lodash._basecopy/-/lodash._basecopy-3.0.1.tgz", - "integrity": "sha1-jaDmqHbPNEwK2KVIghEd08XHyjY=" - }, - "node_modules/lodash._basecreate": { - "version": "3.0.3", - "resolved": "https://registry.npmjs.org/lodash._basecreate/-/lodash._basecreate-3.0.3.tgz", - "integrity": "sha1-G8ZhYU2qf8MRt9A78WgGoCE8+CE=" - }, - "node_modules/lodash._getnative": { - "version": "3.9.1", - "resolved": "https://registry.npmjs.org/lodash._getnative/-/lodash._getnative-3.9.1.tgz", - "integrity": "sha1-VwvH3t5G1hzc3mh9ZdPuy6o6r/U=" - }, - "node_modules/lodash._isiterateecall": { - "version": "3.0.9", - "resolved": "https://registry.npmjs.org/lodash._isiterateecall/-/lodash._isiterateecall-3.0.9.tgz", - "integrity": "sha1-UgOte6Ql+uhCRg5pbbnPPmqsBXw=" - }, - "node_modules/lodash._reinterpolate": { - "version": "3.0.0", - "resolved": "https://registry.npmjs.org/lodash._reinterpolate/-/lodash._reinterpolate-3.0.0.tgz", - "integrity": "sha1-DM8tiRZq8Ds2Y8eWU4t1rG4RTZ0=", - "dev": true - }, - "node_modules/lodash.create": { - "version": "3.1.1", - "resolved": "https://registry.npmjs.org/lodash.create/-/lodash.create-3.1.1.tgz", - "integrity": "sha1-1/KEnw29p+BGgruM1yqwIkYd6+c=", - "dependencies": { - "lodash._baseassign": "^3.0.0", - "lodash._basecreate": "^3.0.0", - "lodash._isiterateecall": "^3.0.0" - } - }, - "node_modules/lodash.debounce": { - "version": "4.0.8", - "resolved": "https://registry.npmjs.org/lodash.debounce/-/lodash.debounce-4.0.8.tgz", - "integrity": "sha1-gteb/zCmfEAF/9XiUVMArZyk168=" - }, - "node_modules/lodash.flattendeep": { - "version": "4.4.0", - "resolved": "https://registry.npmjs.org/lodash.flattendeep/-/lodash.flattendeep-4.4.0.tgz", - "integrity": "sha1-+wMJF/hqMTTlvJvsDWngAT3f7bI=", - "dev": true - }, - "node_modules/lodash.includes": { - "version": "4.3.0", - "resolved": "https://registry.npmjs.org/lodash.includes/-/lodash.includes-4.3.0.tgz", - "integrity": "sha1-YLuYqHy5I8aMoeUTJUgzFISfVT8=" - }, - "node_modules/lodash.isarguments": { - "version": "3.1.0", - "resolved": "https://registry.npmjs.org/lodash.isarguments/-/lodash.isarguments-3.1.0.tgz", - "integrity": "sha1-L1c9hcaiQon/AGY7SRwdM4/zRYo=" - }, - "node_modules/lodash.isarray": { - "version": "3.0.4", - "resolved": "https://registry.npmjs.org/lodash.isarray/-/lodash.isarray-3.0.4.tgz", - "integrity": "sha1-eeTriMNqgSKvhvhEqpvNhRtfu1U=" - }, - "node_modules/lodash.isboolean": { - "version": "3.0.3", - "resolved": "https://registry.npmjs.org/lodash.isboolean/-/lodash.isboolean-3.0.3.tgz", - "integrity": "sha1-bC4XHbKiV82WgC/UOwGyDV9YcPY=" - }, - "node_modules/lodash.isinteger": { - "version": "4.0.4", - "resolved": "https://registry.npmjs.org/lodash.isinteger/-/lodash.isinteger-4.0.4.tgz", - "integrity": "sha1-YZwK89A/iwTDH1iChAt3sRzWg0M=" - }, - "node_modules/lodash.ismatch": { - "version": "4.4.0", - "resolved": "https://registry.npmjs.org/lodash.ismatch/-/lodash.ismatch-4.4.0.tgz", - "integrity": "sha1-dWy1FQyjum8RCFp4hJZF8Yj4Xzc=", - "dev": true - }, - "node_modules/lodash.isnumber": { - "version": "3.0.3", - "resolved": "https://registry.npmjs.org/lodash.isnumber/-/lodash.isnumber-3.0.3.tgz", - "integrity": "sha1-POdoEMWSjQM1IwGsKHMX8RwLH/w=" - }, - "node_modules/lodash.isplainobject": { - "version": "4.0.6", - "resolved": "https://registry.npmjs.org/lodash.isplainobject/-/lodash.isplainobject-4.0.6.tgz", - "integrity": "sha1-fFJqUtibRcRcxpC4gWO+BJf1UMs=" - }, - "node_modules/lodash.isstring": { - "version": "4.0.1", - "resolved": "https://registry.npmjs.org/lodash.isstring/-/lodash.isstring-4.0.1.tgz", - "integrity": "sha1-1SfftUVuynzJu5XV2ur4i6VKVFE=" - }, - "node_modules/lodash.keys": { - "version": "3.1.2", - "resolved": "https://registry.npmjs.org/lodash.keys/-/lodash.keys-3.1.2.tgz", - "integrity": "sha1-TbwEcrFWvlCgsoaFXRvQsMZWCYo=", - "dependencies": { - "lodash._getnative": "^3.0.0", - "lodash.isarguments": "^3.0.0", - "lodash.isarray": "^3.0.0" - } - }, - "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/lodash.once": { - "version": "4.1.1", - "resolved": "https://registry.npmjs.org/lodash.once/-/lodash.once-4.1.1.tgz", - "integrity": "sha1-DdOXEhPHxW34gJd9UEyI+0cal6w=" - }, - "node_modules/lodash.template": { - "version": "4.5.0", - "resolved": "https://registry.npmjs.org/lodash.template/-/lodash.template-4.5.0.tgz", - "integrity": "sha512-84vYFxIkmidUiFxidA/KjjH9pAycqW+h980j7Fuz5qxRtO9pgB7MDFTdys1N7A5mcucRiDyEq4fusljItR1T/A==", - "dev": true, - "dependencies": { - "lodash._reinterpolate": "^3.0.0", - "lodash.templatesettings": "^4.0.0" - } - }, - "node_modules/lodash.templatesettings": { - "version": "4.2.0", - "resolved": "https://registry.npmjs.org/lodash.templatesettings/-/lodash.templatesettings-4.2.0.tgz", - "integrity": "sha512-stgLz+i3Aa9mZgnjr/O+v9ruKZsPsndy7qPZOchbqk2cnTU1ZaldKK+v7m54WoKIyxiuMZTKT2H81F8BeAc3ZQ==", - "dev": true, - "dependencies": { - "lodash._reinterpolate": "^3.0.0" - } - }, - "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==", - "dependencies": { - "chalk": "^4.1.0", - "is-unicode-supported": "^0.1.0" - }, - "engines": { - "node": ">=10" - }, - "funding": { - "url": "https://github.com/sponsors/sindresorhus" - } - }, - "node_modules/long-timeout": { - "version": "0.1.1", - "resolved": "https://registry.npmjs.org/long-timeout/-/long-timeout-0.1.1.tgz", - "integrity": "sha1-lyHXiLR+C8taJMLivuGg2lXatRQ=" - }, - "node_modules/longest": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/longest/-/longest-1.0.1.tgz", - "integrity": "sha1-MKCy2jj3N3DoKUoNIuZiXtd9AJc=", - "engines": { - "node": ">=0.10.0" - } - }, - "node_modules/loose-envify": { - "version": "1.4.0", - "resolved": "https://registry.npmjs.org/loose-envify/-/loose-envify-1.4.0.tgz", - "integrity": "sha512-lyuxPGr/Wfhrlem2CL/UcnUc1zcqKAImBDzukY7Y5F/yQiNdko6+fRLevlw1HgMySw7f611UIY408EtxRSoK3Q==", - "dependencies": { - "js-tokens": "^3.0.0 || ^4.0.0" - }, - "bin": { - "loose-envify": "cli.js" - } - }, - "node_modules/lowercase-keys": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/lowercase-keys/-/lowercase-keys-1.0.1.tgz", - "integrity": "sha512-G2Lj61tXDnVFFOi8VZds+SoQjtQC3dgokKdDG2mTm1tx4m50NUHBOZSBwQQHyy0V12A0JTG4icfZQH+xPyh8VA==", - "dev": true, - "engines": { - "node": ">=0.10.0" - } - }, - "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==", - "dependencies": { - "yallist": "^4.0.0" - }, - "engines": { - "node": ">=10" - } - }, - "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==", - "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==", - "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==" - }, - "node_modules/make-fetch-happen": { - "version": "8.0.14", - "resolved": "https://registry.npmjs.org/make-fetch-happen/-/make-fetch-happen-8.0.14.tgz", - "integrity": "sha512-EsS89h6l4vbfJEtBZnENTOFk8mCRpY5ru36Xe5bcX1KYIli2mkSHqoFsp5O1wMDvTJJzxe/4THpCTtygjeeGWQ==", - "dev": true, - "dependencies": { - "agentkeepalive": "^4.1.3", - "cacache": "^15.0.5", - "http-cache-semantics": "^4.1.0", - "http-proxy-agent": "^4.0.1", - "https-proxy-agent": "^5.0.0", - "is-lambda": "^1.0.1", - "lru-cache": "^6.0.0", - "minipass": "^3.1.3", - "minipass-collect": "^1.0.2", - "minipass-fetch": "^1.3.2", - "minipass-flush": "^1.0.5", - "minipass-pipeline": "^1.2.4", - "promise-retry": "^2.0.1", - "socks-proxy-agent": "^5.0.0", - "ssri": "^8.0.0" - }, - "engines": { - "node": ">= 10" - } - }, - "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/marko": { - "version": "4.24.2", - "resolved": "https://registry.npmjs.org/marko/-/marko-4.24.2.tgz", - "integrity": "sha512-SbrJXLLNPfi4arDOo9yOL1feuWLmm6t1k8pI2wu6rdEXzvUXeaiMfBOZ82d59ZQwPDLnziGqcScgmSk/ShdPEA==", - "dependencies": { - "acorn": "^7.4.0", - "app-module-path": "^2.2.0", - "argly": "^1.0.0", - "browser-refresh-client": "^1.0.0", - "camelcase": "^5.0.0", - "char-props": "~0.1.5", - "complain": "^1.6.0", - "deresolve": "^1.1.2", - "escodegen": "^1.8.1", - "espree": "^7.3.0", - "estraverse": "^4.3.0", - "events-light": "^1.0.0", - "he": "^1.1.0", - "htmljs-parser": "^2.11.1", - "lasso-caching-fs": "^1.0.1", - "lasso-modules-client": "^2.0.4", - "lasso-package-root": "^1.0.1", - "listener-tracker": "^2.0.0", - "minimatch": "^3.0.2", - "property-handlers": "^1.0.0", - "raptor-regexp": "^1.0.0", - "raptor-util": "^3.2.0", - "resolve-from": "^2.0.0", - "self-closing-tags": "^1.0.1", - "simple-sha1": "^2.1.0", - "strip-json-comments": "^2.0.1", - "warp10": "^2.0.1" - }, - "bin": { - "markoc": "bin/markoc" - } - }, - "node_modules/marko/node_modules/acorn": { - "version": "7.4.1", - "resolved": "https://registry.npmjs.org/acorn/-/acorn-7.4.1.tgz", - "integrity": "sha512-nQyp0o1/mNdbTO1PO6kHkwSrmgZ0MT/jCCpNiwbUjGoRN4dlBhqJtoQuCnEOKzgTVwg0ZWiCoQy6SxMebQVh8A==", - "bin": { - "acorn": "bin/acorn" - }, - "engines": { - "node": ">=0.4.0" - } - }, - "node_modules/marko/node_modules/app-module-path": { - "version": "2.2.0", - "resolved": "https://registry.npmjs.org/app-module-path/-/app-module-path-2.2.0.tgz", - "integrity": "sha1-ZBqlXft9am8KgUHEucCqULbCTdU=" - }, - "node_modules/marko/node_modules/eslint-visitor-keys": { - "version": "1.3.0", - "resolved": "https://registry.npmjs.org/eslint-visitor-keys/-/eslint-visitor-keys-1.3.0.tgz", - "integrity": "sha512-6J72N8UNa462wa/KFODt/PJ3IU60SDpC3QXC1Hjc1BXXpfL2C9R5+AU7jhe0F6GREqVMh4Juu+NY7xn+6dipUQ==", - "engines": { - "node": ">=4" - } - }, - "node_modules/marko/node_modules/espree": { - "version": "7.3.1", - "resolved": "https://registry.npmjs.org/espree/-/espree-7.3.1.tgz", - "integrity": "sha512-v3JCNCE64umkFpmkFGqzVKsOT0tN1Zr+ueqLZfpV1Ob8e+CEgPWa+OxCoGH3tnhimMKIaBm4m/vaRpJ/krRz2g==", - "dependencies": { - "acorn": "^7.4.0", - "acorn-jsx": "^5.3.1", - "eslint-visitor-keys": "^1.3.0" - }, - "engines": { - "node": "^10.12.0 || >=12.0.0" - } - }, - "node_modules/marko/node_modules/resolve-from": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/resolve-from/-/resolve-from-2.0.0.tgz", - "integrity": "sha1-lICrIOlP+h2egKgEx+oUdhGWa1c=", - "engines": { - "node": ">=0.10.0" - } - }, - "node_modules/marko/node_modules/strip-json-comments": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/strip-json-comments/-/strip-json-comments-2.0.1.tgz", - "integrity": "sha1-PFMZQukIwml8DsNEhYwobHygpgo=", - "engines": { - "node": ">=0.10.0" - } - }, - "node_modules/math-random": { - "version": "1.0.4", - "resolved": "https://registry.npmjs.org/math-random/-/math-random-1.0.4.tgz", - "integrity": "sha512-rUxjysqif/BZQH2yhd5Aaq7vXMSx9NdEsQcyA07uEzIvxgI7zIr33gGsh+RU0/XjmQpCW7RsVof1vlkvQVCK5A==" - }, - "node_modules/media-typer": { - "version": "0.3.0", - "resolved": "https://registry.npmjs.org/media-typer/-/media-typer-0.3.0.tgz", - "integrity": "sha1-hxDXrwqmJvj/+hzgAWhUUmMlV0g=", - "engines": { - "node": ">= 0.6" - } - }, - "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 - }, - "node_modules/meow": { - "version": "8.1.2", - "resolved": "https://registry.npmjs.org/meow/-/meow-8.1.2.tgz", - "integrity": "sha512-r85E3NdZ+mpYk1C6RjPFEMSE+s1iZMuHtsHAqY0DT3jZczl0diWUZ8g6oU7h0M9cD2EL+PzaYghhCLzR0ZNn5Q==", - "dev": true, - "dependencies": { - "@types/minimist": "^1.2.0", - "camelcase-keys": "^6.2.2", - "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/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/meow/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/meow/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/meow/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/meow/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/meow/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/meow/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/meow/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/meow/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/meow/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/meow/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/meow/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/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", - "integrity": "sha1-sAqqVW3YtEVoFQ7J0blT8/kMu2E=" - }, - "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==" - }, - "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": "sha1-VSmk1nZUE07cxSZmVoNbD4Ua/O4=", - "engines": { - "node": ">= 0.6" - } - }, - "node_modules/micromatch": { - "version": "4.0.4", - "resolved": "https://registry.npmjs.org/micromatch/-/micromatch-4.0.4.tgz", - "integrity": "sha512-pRmzw/XUcwXGpD9aI9q/0XOwLNygjETJ8y0ao0wdqprrzDa4YnxLcz7fQRZr8voh8V10kGhABbNcHVk5wHgWwg==", - "dependencies": { - "braces": "^3.0.1", - "picomatch": "^2.2.3" - }, - "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.51.0", - "resolved": "https://registry.npmjs.org/mime-db/-/mime-db-1.51.0.tgz", - "integrity": "sha512-5y8A56jg7XVQx2mbv1lu49NR4dokRnhZYTtL+KGfaa27uq4pSTXkwQkFJl4pkRMyNFz/EtYDSkiiEHx3F7UN6g==", - "engines": { - "node": ">= 0.6" - } - }, - "node_modules/mime-types": { - "version": "2.1.34", - "resolved": "https://registry.npmjs.org/mime-types/-/mime-types-2.1.34.tgz", - "integrity": "sha512-6cP692WwGIs9XXdOO4++N+7qjqv0rqxxVvJ3VHPh/Sc9mVZcQP+ZGhkKiTvWMQRr2tbHkJP/Yn7Y0npb3ZBs4A==", - "dependencies": { - "mime-db": "1.51.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==", - "engines": { - "node": ">=6" - } - }, - "node_modules/mimic-response": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/mimic-response/-/mimic-response-1.0.1.tgz", - "integrity": "sha512-j5EctnkH7amfV/q5Hgmoal1g2QHFJRraOtmx0JpIqkxhBhI/lJSl1nMpQ45hVarwNETOoWEimndZ4QK0RHxuxQ==", - "dev": true, - "engines": { - "node": ">=4" - } - }, - "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/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==", - "optional": true - }, - "node_modules/minimalistic-crypto-utils": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/minimalistic-crypto-utils/-/minimalistic-crypto-utils-1.0.1.tgz", - "integrity": "sha1-9sAMHAsIIkblxNmd+4x8CDsrWCo=", - "optional": true - }, - "node_modules/minimatch": { - "version": "3.0.4", - "resolved": "https://registry.npmjs.org/minimatch/-/minimatch-3.0.4.tgz", - "integrity": "sha512-yJHVQEhyqPLUTgt9B83PXu6W3rx4MvvHvSUvToogpwoGDOUQ+yDrR0HRot+yOCdCO7u4hX3pWft6kWBBcqh0UA==", - "dependencies": { - "brace-expansion": "^1.1.7" - }, - "engines": { - "node": "*" - } - }, - "node_modules/minimist": { - "version": "1.2.5", - "resolved": "https://registry.npmjs.org/minimist/-/minimist-1.2.5.tgz", - "integrity": "sha512-FM9nNUYrRBAELZQT3xeZQ7fmMOBg6nWNmJKTcgsJeaLstP/UODVpGsr5OhXhhXg6f+qtJ8uiZ+PUxkDWcgIXLw==" - }, - "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/minipass": { - "version": "3.1.6", - "resolved": "https://registry.npmjs.org/minipass/-/minipass-3.1.6.tgz", - "integrity": "sha512-rty5kpw9/z8SX9dmxblFA6edItUmwJgMeYDZRrwlIVN27i8gysGbznJwUggw2V/FVqFSDdWy040ZPS811DYAqQ==", - "dev": true, - "dependencies": { - "yallist": "^4.0.0" - }, - "engines": { - "node": ">=8" - } - }, - "node_modules/minipass-collect": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/minipass-collect/-/minipass-collect-1.0.2.tgz", - "integrity": "sha512-6T6lH0H8OG9kITm/Jm6tdooIbogG9e0tLgpY6mphXSm/A9u8Nq1ryBG+Qspiub9LjWlBPsPS3tWQ/Botq4FdxA==", - "dev": true, - "dependencies": { - "minipass": "^3.0.0" - }, - "engines": { - "node": ">= 8" - } - }, - "node_modules/minipass-fetch": { - "version": "1.4.1", - "resolved": "https://registry.npmjs.org/minipass-fetch/-/minipass-fetch-1.4.1.tgz", - "integrity": "sha512-CGH1eblLq26Y15+Azk7ey4xh0J/XfJfrCox5LDJiKqI2Q2iwOLOKrlmIaODiSQS8d18jalF6y2K2ePUm0CmShw==", - "dev": true, - "dependencies": { - "minipass": "^3.1.0", - "minipass-sized": "^1.0.3", - "minizlib": "^2.0.0" - }, - "engines": { - "node": ">=8" - }, - "optionalDependencies": { - "encoding": "^0.1.12" - } - }, - "node_modules/minipass-flush": { - "version": "1.0.5", - "resolved": "https://registry.npmjs.org/minipass-flush/-/minipass-flush-1.0.5.tgz", - "integrity": "sha512-JmQSYYpPUqX5Jyn1mXaRwOda1uQ8HP5KAT/oDSLCzt1BYRhQU0/hDtsB1ufZfEEzMZ9aAVmsBw8+FWsIXlClWw==", - "dev": true, - "dependencies": { - "minipass": "^3.0.0" - }, - "engines": { - "node": ">= 8" - } - }, - "node_modules/minipass-json-stream": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/minipass-json-stream/-/minipass-json-stream-1.0.1.tgz", - "integrity": "sha512-ODqY18UZt/I8k+b7rl2AENgbWE8IDYam+undIJONvigAz8KR5GWblsFTEfQs0WODsjbSXWlm+JHEv8Gr6Tfdbg==", - "dev": true, - "dependencies": { - "jsonparse": "^1.3.1", - "minipass": "^3.0.0" - } - }, - "node_modules/minipass-pipeline": { - "version": "1.2.4", - "resolved": "https://registry.npmjs.org/minipass-pipeline/-/minipass-pipeline-1.2.4.tgz", - "integrity": "sha512-xuIq7cIOt09RPRJ19gdi4b+RiNvDFYe5JH+ggNvBqGqpQXcru3PcRmOZuHBKWK1Txf9+cQ+HMVN4d6z46LZP7A==", - "dev": true, - "dependencies": { - "minipass": "^3.0.0" - }, - "engines": { - "node": ">=8" - } - }, - "node_modules/minipass-sized": { - "version": "1.0.3", - "resolved": "https://registry.npmjs.org/minipass-sized/-/minipass-sized-1.0.3.tgz", - "integrity": "sha512-MbkQQ2CTiBMlA2Dm/5cY+9SWFEN8pzzOXi6rlM5Xxq0Yqbda5ZQy9sU75a673FE9ZK0Zsbr6Y5iP6u9nktfg2g==", - "dev": true, - "dependencies": { - "minipass": "^3.0.0" - }, - "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==", - "dev": true, - "dependencies": { - "minipass": "^3.0.0", - "yallist": "^4.0.0" - }, - "engines": { - "node": ">= 8" - } - }, - "node_modules/mkdirp": { - "version": "1.0.4", - "resolved": "https://registry.npmjs.org/mkdirp/-/mkdirp-1.0.4.tgz", - "integrity": "sha512-vVqVZQyf3WLx2Shd0qJ9xuvqgAyKPLAiqITEtqW0oIUjzo3PePDd6fW9iFz30ef7Ysp/oiWqbhszeGWW2T6Gzw==", - "dev": true, - "bin": { - "mkdirp": "bin/cmd.js" - }, - "engines": { - "node": ">=10" - } - }, - "node_modules/mkdirp-infer-owner": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/mkdirp-infer-owner/-/mkdirp-infer-owner-2.0.0.tgz", - "integrity": "sha512-sdqtiFt3lkOaYvTXSRIUjkIdPTcxgv5+fgqYE/5qgwdw12cOrAuzzgzvVExIkH/ul1oeHN3bCLOWSG3XOqbKKw==", - "dev": true, - "dependencies": { - "chownr": "^2.0.0", - "infer-owner": "^1.0.4", - "mkdirp": "^1.0.3" - }, - "engines": { - "node": ">=10" - } - }, - "node_modules/mocha": { - "version": "9.1.3", - "resolved": "https://registry.npmjs.org/mocha/-/mocha-9.1.3.tgz", - "integrity": "sha512-Xcpl9FqXOAYqI3j79pEtHBBnQgVXIhpULjGQa7DVb0Po+VzmSIK9kanAiWLHoRR/dbZ2qpdPshuXr8l1VaHCzw==", - "dependencies": { - "@ungap/promise-all-settled": "1.1.2", - "ansi-colors": "4.1.1", - "browser-stdout": "1.3.1", - "chokidar": "3.5.2", - "debug": "4.3.2", - "diff": "5.0.0", - "escape-string-regexp": "4.0.0", - "find-up": "5.0.0", - "glob": "7.1.7", - "growl": "1.10.5", - "he": "1.2.0", - "js-yaml": "4.1.0", - "log-symbols": "4.1.0", - "minimatch": "3.0.4", - "ms": "2.1.3", - "nanoid": "3.1.25", - "serialize-javascript": "6.0.0", - "strip-json-comments": "3.1.1", - "supports-color": "8.1.1", - "which": "2.0.2", - "workerpool": "6.1.5", - "yargs": "16.2.0", - "yargs-parser": "20.2.4", - "yargs-unparser": "2.0.0" - }, - "bin": { - "_mocha": "bin/_mocha", - "mocha": "bin/mocha" - }, - "engines": { - "node": ">= 12.0.0" - }, - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/mochajs" - } - }, - "node_modules/mocha-puppeteer": { - "version": "0.14.0", - "resolved": "https://registry.npmjs.org/mocha-puppeteer/-/mocha-puppeteer-0.14.0.tgz", - "integrity": "sha512-wajn5TWDZkvBvlkf00ksfuvy3oJ87NWMzl2Hy7f8lJXWLfYcKt/6A/R8X2eNZS7T9iW1353OuxlDxre7gUCf7g==", - "dependencies": { - "argly": "^1.2.0", - "babel-plugin-istanbul": "^4.1.4", - "babel-polyfill": "^6.26.0", - "bluebird": "^3.5.0", - "body-parser": "^1.18.2", - "express": "^4.15.4", - "fs-walk": "0.0.1", - "lasso": "^2.11.16", - "lasso-babel-transform": "^1.0.1", - "marko": "^4.4.26", - "mocha": "^3.5.0", - "puppeteer": "^0.12.0", - "rimraf": "^2.6.1", - "superagent": "^3.6.0", - "uuid": "^3.1.0" - }, - "bin": { - "mocha-puppeteer": "bin/mocha-puppeteer" - } - }, - "node_modules/mocha-puppeteer/node_modules/browser-stdout": { - "version": "1.3.0", - "resolved": "https://registry.npmjs.org/browser-stdout/-/browser-stdout-1.3.0.tgz", - "integrity": "sha1-81HTKWnTL6XXpVZxVCY9korjvR8=" - }, - "node_modules/mocha-puppeteer/node_modules/commander": { - "version": "2.9.0", - "resolved": "https://registry.npmjs.org/commander/-/commander-2.9.0.tgz", - "integrity": "sha1-nJkJQXbhIkDLItbFFGCYQA/g99Q=", - "dependencies": { - "graceful-readlink": ">= 1.0.0" - }, - "engines": { - "node": ">= 0.6.x" - } - }, - "node_modules/mocha-puppeteer/node_modules/debug": { - "version": "2.6.8", - "resolved": "https://registry.npmjs.org/debug/-/debug-2.6.8.tgz", - "integrity": "sha1-5zFTHKLt4n0YgiJCfaF4IdaP9Pw=", - "dependencies": { - "ms": "2.0.0" - } - }, - "node_modules/mocha-puppeteer/node_modules/diff": { - "version": "3.2.0", - "resolved": "https://registry.npmjs.org/diff/-/diff-3.2.0.tgz", - "integrity": "sha1-yc45Okt8vQsFinJck98pkCeGj/k=", - "engines": { - "node": ">=0.3.1" - } - }, - "node_modules/mocha-puppeteer/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": "sha1-G2HAViGQqN/2rjuyzwIAyhMLhtQ=", - "engines": { - "node": ">=0.8.0" - } - }, - "node_modules/mocha-puppeteer/node_modules/growl": { - "version": "1.9.2", - "resolved": "https://registry.npmjs.org/growl/-/growl-1.9.2.tgz", - "integrity": "sha1-Dqd0NxXbjY3ixe3hd14bRayFwC8=" - }, - "node_modules/mocha-puppeteer/node_modules/has-flag": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/has-flag/-/has-flag-1.0.0.tgz", - "integrity": "sha1-nZ55MWXOAXoA8AQYxD+UKnsdEfo=", - "engines": { - "node": ">=0.10.0" - } - }, - "node_modules/mocha-puppeteer/node_modules/he": { - "version": "1.1.1", - "resolved": "https://registry.npmjs.org/he/-/he-1.1.1.tgz", - "integrity": "sha1-k0EP0hsAlzUVH4howvJx80J+I/0=", - "bin": { - "he": "bin/he" - } - }, - "node_modules/mocha-puppeteer/node_modules/minimist": { - "version": "0.0.8", - "resolved": "https://registry.npmjs.org/minimist/-/minimist-0.0.8.tgz", - "integrity": "sha1-hX/Kv8M5fSYluCKCYuhqp6ARsF0=" - }, - "node_modules/mocha-puppeteer/node_modules/mkdirp": { - "version": "0.5.1", - "resolved": "https://registry.npmjs.org/mkdirp/-/mkdirp-0.5.1.tgz", - "integrity": "sha1-MAV0OOrGz3+MR2fzhkjWaX11yQM=", - "deprecated": "Legacy versions of mkdirp are no longer supported. Please update to mkdirp 1.x. (Note that the API surface has changed to use Promises in 1.x.)", - "dependencies": { - "minimist": "0.0.8" - }, - "bin": { - "mkdirp": "bin/cmd.js" - } - }, - "node_modules/mocha-puppeteer/node_modules/mocha": { - "version": "3.5.3", - "resolved": "https://registry.npmjs.org/mocha/-/mocha-3.5.3.tgz", - "integrity": "sha512-/6na001MJWEtYxHOV1WLfsmR4YIynkUEhBwzsb+fk2qmQ3iqsi258l/Q2MWHJMImAcNpZ8DEdYAK72NHoIQ9Eg==", - "dependencies": { - "browser-stdout": "1.3.0", - "commander": "2.9.0", - "debug": "2.6.8", - "diff": "3.2.0", - "escape-string-regexp": "1.0.5", - "glob": "7.1.1", - "growl": "1.9.2", - "he": "1.1.1", - "json3": "3.3.2", - "lodash.create": "3.1.1", - "mkdirp": "0.5.1", - "supports-color": "3.1.2" - }, - "bin": { - "_mocha": "bin/_mocha", - "mocha": "bin/mocha" - }, - "engines": { - "node": ">= 0.10.x", - "npm": ">= 1.4.x" - } - }, - "node_modules/mocha-puppeteer/node_modules/mocha/node_modules/glob": { - "version": "7.1.1", - "resolved": "https://registry.npmjs.org/glob/-/glob-7.1.1.tgz", - "integrity": "sha1-gFIR3wT6rxxjo2ADBs31reULLsg=", - "dependencies": { - "fs.realpath": "^1.0.0", - "inflight": "^1.0.4", - "inherits": "2", - "minimatch": "^3.0.2", - "once": "^1.3.0", - "path-is-absolute": "^1.0.0" - }, - "engines": { - "node": "*" - } - }, - "node_modules/mocha-puppeteer/node_modules/ms": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/ms/-/ms-2.0.0.tgz", - "integrity": "sha1-VgiurfwAvmwpAd9fmGF4jeDVl8g=" - }, - "node_modules/mocha-puppeteer/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/mocha-puppeteer/node_modules/rimraf": { - "version": "2.7.1", - "resolved": "https://registry.npmjs.org/rimraf/-/rimraf-2.7.1.tgz", - "integrity": "sha512-uWjbaKIK3T1OSVptzX7Nl6PvQ3qAGtKEtVRjRuazjfL3Bx5eI409VZSqgND+4UNnmzLVdPj9FqFJNPqBZFve4w==", - "dependencies": { - "glob": "^7.1.3" - }, - "bin": { - "rimraf": "bin.js" - } - }, - "node_modules/mocha-puppeteer/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/mocha-puppeteer/node_modules/superagent": { - "version": "3.8.3", - "resolved": "https://registry.npmjs.org/superagent/-/superagent-3.8.3.tgz", - "integrity": "sha512-GLQtLMCoEIK4eDv6OGtkOoSMt3D+oq0y3dsxMuYuDvaNUvuT8eFBuLmfR0iYYzHC1e8hpzC6ZsxbuP6DIalMFA==", - "dependencies": { - "component-emitter": "^1.2.0", - "cookiejar": "^2.1.0", - "debug": "^3.1.0", - "extend": "^3.0.0", - "form-data": "^2.3.1", - "formidable": "^1.2.0", - "methods": "^1.1.1", - "mime": "^1.4.1", - "qs": "^6.5.1", - "readable-stream": "^2.3.5" - }, - "engines": { - "node": ">= 4.0" - } - }, - "node_modules/mocha-puppeteer/node_modules/superagent/node_modules/debug": { - "version": "3.2.7", - "resolved": "https://registry.npmjs.org/debug/-/debug-3.2.7.tgz", - "integrity": "sha512-CFjzYYAi4ThfiQvizrFQevTTXHtnCqWfe7x1AhgEscTz6ZbLbfoLRLPugTQyBth6f8ZERVUSyWHFD/7Wu4t1XQ==", - "dependencies": { - "ms": "^2.1.1" - } - }, - "node_modules/mocha-puppeteer/node_modules/superagent/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/mocha-puppeteer/node_modules/supports-color": { - "version": "3.1.2", - "resolved": "https://registry.npmjs.org/supports-color/-/supports-color-3.1.2.tgz", - "integrity": "sha1-cqJiiU2dQIuVbKBf83su2KbiotU=", - "dependencies": { - "has-flag": "^1.0.0" - }, - "engines": { - "node": ">=0.8.0" - } - }, - "node_modules/mocha-puppeteer/node_modules/uuid": { - "version": "3.4.0", - "resolved": "https://registry.npmjs.org/uuid/-/uuid-3.4.0.tgz", - "integrity": "sha512-HjSDRw6gZE5JMggctHBcjVak08+KEVhSIiDzFnT9S9aegmp85S/bReBVTb4QTFaRNptJ9kuYaNhnbNEOkbKb/A==", - "deprecated": "Please upgrade to version 7 or higher. Older versions may use Math.random() in certain circumstances, which is known to be problematic. See https://v8.dev/blog/math-random for details.", - "bin": { - "uuid": "bin/uuid" - } - }, - "node_modules/mocha/node_modules/debug": { - "version": "4.3.2", - "resolved": "https://registry.npmjs.org/debug/-/debug-4.3.2.tgz", - "integrity": "sha512-mOp8wKcvj7XxC78zLgw/ZA+6TSgkoE2C/ienthhRD298T7UNwAg9diBpLRxC0mOezLl4B0xV7M0cCO6P/O0Xhw==", - "dependencies": { - "ms": "2.1.2" - }, - "engines": { - "node": ">=6.0" - }, - "peerDependenciesMeta": { - "supports-color": { - "optional": true - } - } - }, - "node_modules/mocha/node_modules/debug/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==" - }, - "node_modules/mocha/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==", - "dependencies": { - "locate-path": "^6.0.0", - "path-exists": "^4.0.0" - }, - "engines": { - "node": ">=10" - }, - "funding": { - "url": "https://github.com/sponsors/sindresorhus" - } - }, - "node_modules/mocha/node_modules/glob": { - "version": "7.1.7", - "resolved": "https://registry.npmjs.org/glob/-/glob-7.1.7.tgz", - "integrity": "sha512-OvD9ENzPLbegENnYP5UUfJIirTg4+XwMWGaQfQTY0JenxNvvIKP3U3/tAQSPIu/lHxXYSZmpXlUHeqAIdKzBLQ==", - "dependencies": { - "fs.realpath": "^1.0.0", - "inflight": "^1.0.4", - "inherits": "2", - "minimatch": "^3.0.4", - "once": "^1.3.0", - "path-is-absolute": "^1.0.0" - }, - "engines": { - "node": "*" - }, - "funding": { - "url": "https://github.com/sponsors/isaacs" - } - }, - "node_modules/mocha/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==", - "dependencies": { - "p-locate": "^5.0.0" - }, - "engines": { - "node": ">=10" - }, - "funding": { - "url": "https://github.com/sponsors/sindresorhus" - } - }, - "node_modules/mocha/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/mocha/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==", - "dependencies": { - "yocto-queue": "^0.1.0" - }, - "engines": { - "node": ">=10" - }, - "funding": { - "url": "https://github.com/sponsors/sindresorhus" - } - }, - "node_modules/mocha/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==", - "dependencies": { - "p-limit": "^3.0.2" - }, - "engines": { - "node": ">=10" - }, - "funding": { - "url": "https://github.com/sponsors/sindresorhus" - } - }, - "node_modules/mocha/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==", - "dependencies": { - "has-flag": "^4.0.0" - }, - "engines": { - "node": ">=10" - }, - "funding": { - "url": "https://github.com/chalk/supports-color?sponsor=1" - } - }, - "node_modules/modify-values": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/modify-values/-/modify-values-1.0.1.tgz", - "integrity": "sha512-xV2bxeN6F7oYjZWTe/YPAy6MN2M+sL4u/Rlm2AHCIVGfo2p1yGmBHQ6vHehl4bRTZBdHu3TSkWdYgkwpYzAGSw==", - "dev": true, - "engines": { - "node": ">=0.10.0" - } - }, - "node_modules/mongodb": { - "version": "4.2.2", - "resolved": "https://registry.npmjs.org/mongodb/-/mongodb-4.2.2.tgz", - "integrity": "sha512-zt8rCTnTKyMQppyt63qMnrLM5dbADgUk18ORPF1XbtHLIYCyc9hattaYHi0pqMvNxDpgGgUofSVzS+UQErgTug==", - "dependencies": { - "bson": "^4.6.0", - "denque": "^2.0.1", - "mongodb-connection-string-url": "^2.3.2" - }, - "engines": { - "node": ">=12.9.0" - }, - "optionalDependencies": { - "saslprep": "^1.0.3" - } - }, - "node_modules/mongodb-connection-string-url": { - "version": "2.4.1", - "resolved": "https://registry.npmjs.org/mongodb-connection-string-url/-/mongodb-connection-string-url-2.4.1.tgz", - "integrity": "sha512-d5Kd2bVsKcSA7YI/yo57fSTtMwRQdFkvc5IZwod1RRxJtECeWPPSo7zqcUGJELifRA//Igs4spVtYAmvFCatug==", - "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==", - "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==", - "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==", - "dependencies": { - "tr46": "^3.0.0", - "webidl-conversions": "^7.0.0" - }, - "engines": { - "node": ">=12" - } - }, - "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==" - }, - "node_modules/multimatch": { - "version": "5.0.0", - "resolved": "https://registry.npmjs.org/multimatch/-/multimatch-5.0.0.tgz", - "integrity": "sha512-ypMKuglUrZUD99Tk2bUQ+xNQj43lPEfAeX2o9cTteAmShXy2VHDJpuwu1o0xqoKCt9jLVAvwyFKdLTPXKAfJyA==", - "dev": true, - "dependencies": { - "@types/minimatch": "^3.0.3", - "array-differ": "^3.0.0", - "array-union": "^2.1.0", - "arrify": "^2.0.1", - "minimatch": "^3.0.4" - }, - "engines": { - "node": ">=10" - }, - "funding": { - "url": "https://github.com/sponsors/sindresorhus" - } - }, - "node_modules/multimatch/node_modules/arrify": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/arrify/-/arrify-2.0.1.tgz", - "integrity": "sha512-3duEwti880xqi4eAMN8AyR4a0ByT90zoYdLlevfrvU43vb0YZwZVfxOgxWrLXXXpyugL0hNZc9G6BiB5B3nUug==", - "dev": true, - "engines": { - "node": ">=8" - } - }, - "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/nanoid": { - "version": "3.1.25", - "resolved": "https://registry.npmjs.org/nanoid/-/nanoid-3.1.25.tgz", - "integrity": "sha512-rdwtIXaXCLFAQbnfqDRnI6jaRHp9fTcYBjtFKE8eezcZ7LuLjhUaQGNeMXf1HmRoCH32CLz6XwX0TtxEOS/A3Q==", - "bin": { - "nanoid": "bin/nanoid.cjs" - }, - "engines": { - "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": "sha1-Sr6/7tdUHywnrPspvbvRXI1bpPc=", - "dev": true - }, - "node_modules/negotiator": { - "version": "0.6.2", - "resolved": "https://registry.npmjs.org/negotiator/-/negotiator-0.6.2.tgz", - "integrity": "sha512-hZXc7K2e+PgeI1eDBe/10Ard4ekbfrrqG8Ep+8Jmf4JID2bNg7NvCPOZN+kfF574pFQI7mum2AUqDidoKqcTOw==", - "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==" - }, - "node_modules/node-fetch": { - "version": "2.6.6", - "resolved": "https://registry.npmjs.org/node-fetch/-/node-fetch-2.6.6.tgz", - "integrity": "sha512-Z8/6vRlTUChSdIgMa51jxQ4lrw/Jy5SOW10ObaA47/RElsAN2c5Pn8bTgFGWn/ibwzXTE8qwr1Yzx28vsecXEA==", - "dependencies": { - "whatwg-url": "^5.0.0" - }, - "engines": { - "node": "4.x || >=6.0.0" - } - }, - "node_modules/node-fetch/node_modules/tr46": { - "version": "0.0.3", - "resolved": "https://registry.npmjs.org/tr46/-/tr46-0.0.3.tgz", - "integrity": "sha1-gYT9NH2snNwYWZLzpmIuFLnZq2o=" - }, - "node_modules/node-fetch/node_modules/webidl-conversions": { - "version": "3.0.1", - "resolved": "https://registry.npmjs.org/webidl-conversions/-/webidl-conversions-3.0.1.tgz", - "integrity": "sha1-JFNCdeKnvGvnvIZhHMFq4KVlSHE=" - }, - "node_modules/node-fetch/node_modules/whatwg-url": { - "version": "5.0.0", - "resolved": "https://registry.npmjs.org/whatwg-url/-/whatwg-url-5.0.0.tgz", - "integrity": "sha1-lmRU6HZUYuN2RNNib2dCzotwll0=", - "dependencies": { - "tr46": "~0.0.3", - "webidl-conversions": "^3.0.0" - } - }, - "node_modules/node-gyp": { - "version": "5.1.1", - "resolved": "https://registry.npmjs.org/node-gyp/-/node-gyp-5.1.1.tgz", - "integrity": "sha512-WH0WKGi+a4i4DUt2mHnvocex/xPLp9pYt5R6M2JdFB7pJ7Z34hveZ4nDTGTiLXCkitA9T8HFZjhinBCiVHYcWw==", - "dev": true, - "dependencies": { - "env-paths": "^2.2.0", - "glob": "^7.1.4", - "graceful-fs": "^4.2.2", - "mkdirp": "^0.5.1", - "nopt": "^4.0.1", - "npmlog": "^4.1.2", - "request": "^2.88.0", - "rimraf": "^2.6.3", - "semver": "^5.7.1", - "tar": "^4.4.12", - "which": "^1.3.1" - }, - "bin": { - "node-gyp": "bin/node-gyp.js" - }, - "engines": { - "node": ">= 6.0.0" - } - }, - "node_modules/node-gyp/node_modules/chownr": { - "version": "1.1.4", - "resolved": "https://registry.npmjs.org/chownr/-/chownr-1.1.4.tgz", - "integrity": "sha512-jJ0bqzaylmJtVnNgzTeSOs8DPavpbYgEr/b0YL8/2GO3xJEhInFmhKMUnEJQjZumK7KXGFhUy89PrsJWlakBVg==", - "dev": true - }, - "node_modules/node-gyp/node_modules/fs-minipass": { - "version": "1.2.7", - "resolved": "https://registry.npmjs.org/fs-minipass/-/fs-minipass-1.2.7.tgz", - "integrity": "sha512-GWSSJGFy4e9GUeCcbIkED+bgAoFyj7XF1mV8rma3QW4NIqX9Kyx79N/PF61H5udOV3aY1IaMLs6pGbH71nlCTA==", - "dev": true, - "dependencies": { - "minipass": "^2.6.0" - } - }, - "node_modules/node-gyp/node_modules/minipass": { - "version": "2.9.0", - "resolved": "https://registry.npmjs.org/minipass/-/minipass-2.9.0.tgz", - "integrity": "sha512-wxfUjg9WebH+CUDX/CdbRlh5SmfZiy/hpkxaRI16Y9W56Pa75sWgd/rvFilSgrauD9NyFymP/+JFV3KwzIsJeg==", - "dev": true, - "dependencies": { - "safe-buffer": "^5.1.2", - "yallist": "^3.0.0" - } - }, - "node_modules/node-gyp/node_modules/minizlib": { - "version": "1.3.3", - "resolved": "https://registry.npmjs.org/minizlib/-/minizlib-1.3.3.tgz", - "integrity": "sha512-6ZYMOEnmVsdCeTJVE0W9ZD+pVnE8h9Hma/iOwwRDsdQoePpoX56/8B6z3P9VNwppJuBKNRuFDRNRqRWexT9G9Q==", - "dev": true, - "dependencies": { - "minipass": "^2.9.0" - } - }, - "node_modules/node-gyp/node_modules/mkdirp": { - "version": "0.5.5", - "resolved": "https://registry.npmjs.org/mkdirp/-/mkdirp-0.5.5.tgz", - "integrity": "sha512-NKmAlESf6jMGym1++R0Ra7wvhV+wFW63FaSOFPwRahvea0gMUcGUhVeAg/0BC0wiv9ih5NYPB1Wn1UEI1/L+xQ==", - "dev": true, - "dependencies": { - "minimist": "^1.2.5" - }, - "bin": { - "mkdirp": "bin/cmd.js" - } - }, - "node_modules/node-gyp/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/node-gyp/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/node-gyp/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/node-gyp/node_modules/tar": { - "version": "4.4.19", - "resolved": "https://registry.npmjs.org/tar/-/tar-4.4.19.tgz", - "integrity": "sha512-a20gEsvHnWe0ygBY8JbxoM4w3SJdhc7ZAuxkLqh+nvNQN2IOt0B5lLgM490X5Hl8FF0dl0tOf2ewFYAlIFgzVA==", - "dev": true, - "dependencies": { - "chownr": "^1.1.4", - "fs-minipass": "^1.2.7", - "minipass": "^2.9.0", - "minizlib": "^1.3.3", - "mkdirp": "^0.5.5", - "safe-buffer": "^5.2.1", - "yallist": "^3.1.1" - }, - "engines": { - "node": ">=4.5" - } - }, - "node_modules/node-gyp/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/node-gyp/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/node-preload": { - "version": "0.2.1", - "resolved": "https://registry.npmjs.org/node-preload/-/node-preload-0.2.1.tgz", - "integrity": "sha512-RM5oyBy45cLEoHqCeh+MNuFAxO0vTFBLskvQbOKnEE7YTTSN4tbN8QWDIPQ6L+WvKsB/qLEGpYe2ZZ9d4W9OIQ==", - "dev": true, - "dependencies": { - "process-on-spawn": "^1.0.0" - }, - "engines": { - "node": ">=8" - } - }, - "node_modules/node-releases": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/node-releases/-/node-releases-2.0.1.tgz", - "integrity": "sha512-CqyzN6z7Q6aMeF/ktcMVTzhAHCEpf8SOarwpzpf8pNBY2k5/oM34UHldUwp8VKI7uxct2HxSRdJjBaZeESzcxA==" - }, - "node_modules/nopt": { - "version": "4.0.3", - "resolved": "https://registry.npmjs.org/nopt/-/nopt-4.0.3.tgz", - "integrity": "sha512-CvaGwVMztSMJLOeXPrez7fyfObdZqNUK1cPAEzLHrTybIua9pMdmmPR5YwtfNftIOMv3DPUhFaxsZMNTQO20Kg==", - "dev": true, - "dependencies": { - "abbrev": "1", - "osenv": "^0.1.4" - }, - "bin": { - "nopt": "bin/nopt.js" - } - }, - "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": ">=10" - } - }, - "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==", - "engines": { - "node": ">=0.10.0" - } - }, - "node_modules/normalize-url": { - "version": "6.1.0", - "resolved": "https://registry.npmjs.org/normalize-url/-/normalize-url-6.1.0.tgz", - "integrity": "sha512-DlL+XwOy3NxAQ8xuC0okPgK46iuVNAK01YN7RueYBqqFeGsBjV9XmCAzAdgt+667bCl5kPh9EqKKDwnaPG1I7A==", - "dev": true, - "engines": { - "node": ">=10" - }, - "funding": { - "url": "https://github.com/sponsors/sindresorhus" - } - }, - "node_modules/npm-bundled": { - "version": "1.1.2", - "resolved": "https://registry.npmjs.org/npm-bundled/-/npm-bundled-1.1.2.tgz", - "integrity": "sha512-x5DHup0SuyQcmL3s7Rx/YQ8sbw/Hzg0rj48eN0dV7hf5cmQq5PXIeioroH3raV1QC1yh3uTYuMThvEQF3iKgGQ==", - "dev": true, - "dependencies": { - "npm-normalize-package-bin": "^1.0.1" - } - }, - "node_modules/npm-check-updates": { - "version": "12.1.0", - "resolved": "https://registry.npmjs.org/npm-check-updates/-/npm-check-updates-12.1.0.tgz", - "integrity": "sha512-9GtSetBvcth7MuL+0MpOmWgdfiEgZcWRfnvoYnNZxbZpleHZCT0Z3HnbsL6/EAT2M+ye7FTZ+YjmDmZptt7Rkg==", - "dev": true, - "dependencies": { - "chalk": "^4.1.2", - "cint": "^8.2.1", - "cli-table": "^0.3.11", - "commander": "^8.3.0", - "fast-memoize": "^2.5.2", - "find-up": "5.0.0", - "fp-and-or": "^0.1.3", - "get-stdin": "^8.0.0", - "globby": "^11.0.4", - "hosted-git-info": "^4.0.2", - "json-parse-helpfulerror": "^1.0.3", - "jsonlines": "^0.1.1", - "libnpmconfig": "^1.2.1", - "lodash": "^4.17.21", - "minimatch": "^3.0.4", - "p-map": "^4.0.0", - "pacote": "^12.0.2", - "parse-github-url": "^1.0.2", - "progress": "^2.0.3", - "prompts": "^2.4.2", - "rc-config-loader": "^4.0.0", - "remote-git-tags": "^3.0.0", - "rimraf": "^3.0.2", - "semver": "^7.3.5", - "semver-utils": "^1.1.4", - "source-map-support": "^0.5.21", - "spawn-please": "^1.0.0", - "update-notifier": "^5.1.0" - }, - "bin": { - "ncu": "build/src/bin/cli.js", - "npm-check-updates": "build/src/bin/cli.js" - }, - "engines": { - "node": ">=12" - } - }, - "node_modules/npm-check-updates/node_modules/@npmcli/run-script": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/@npmcli/run-script/-/run-script-2.0.0.tgz", - "integrity": "sha512-fSan/Pu11xS/TdaTpTB0MRn9guwGU8dye+x56mEVgBEd/QsybBbYcAL0phPXi8SGWFEChkQd6M9qL4y6VOpFig==", - "dev": true, - "dependencies": { - "@npmcli/node-gyp": "^1.0.2", - "@npmcli/promise-spawn": "^1.3.2", - "node-gyp": "^8.2.0", - "read-package-json-fast": "^2.0.1" - } - }, - "node_modules/npm-check-updates/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==", - "dev": true, - "dependencies": { - "delegates": "^1.0.0", - "readable-stream": "^3.6.0" - }, - "engines": { - "node": ">=10" - } - }, - "node_modules/npm-check-updates/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/npm-check-updates/node_modules/gauge": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/gauge/-/gauge-4.0.0.tgz", - "integrity": "sha512-F8sU45yQpjQjxKkm1UOAhf0U/O0aFt//Fl7hsrNVto+patMHjs7dPI9mFOGUKbhrgKm0S3EjW3scMFuQmWSROw==", - "dev": true, - "dependencies": { - "ansi-regex": "^5.0.1", - "aproba": "^1.0.3 || ^2.0.0", - "color-support": "^1.1.2", - "console-control-strings": "^1.0.0", - "has-unicode": "^2.0.1", - "signal-exit": "^3.0.0", - "string-width": "^4.2.3", - "strip-ansi": "^6.0.1", - "wide-align": "^1.1.2" - }, - "engines": { - "node": "^12.13.0 || ^14.15.0 || >=16" - } - }, - "node_modules/npm-check-updates/node_modules/ignore-walk": { - "version": "4.0.1", - "resolved": "https://registry.npmjs.org/ignore-walk/-/ignore-walk-4.0.1.tgz", - "integrity": "sha512-rzDQLaW4jQbh2YrOFlJdCtX8qgJTehFRYiUB2r1osqTeDzV/3+Jh8fz1oAPzUThf3iku8Ds4IDqawI5d8mUiQw==", - "dev": true, - "dependencies": { - "minimatch": "^3.0.4" - }, - "engines": { - "node": ">=10" - } - }, - "node_modules/npm-check-updates/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/npm-check-updates/node_modules/make-fetch-happen": { - "version": "9.1.0", - "resolved": "https://registry.npmjs.org/make-fetch-happen/-/make-fetch-happen-9.1.0.tgz", - "integrity": "sha512-+zopwDy7DNknmwPQplem5lAZX/eCOzSvSNNcSKm5eVwTkOBzoktEfXsa9L23J/GIRhxRsaxzkPEhrJEpE2F4Gg==", - "dev": true, - "dependencies": { - "agentkeepalive": "^4.1.3", - "cacache": "^15.2.0", - "http-cache-semantics": "^4.1.0", - "http-proxy-agent": "^4.0.1", - "https-proxy-agent": "^5.0.0", - "is-lambda": "^1.0.1", - "lru-cache": "^6.0.0", - "minipass": "^3.1.3", - "minipass-collect": "^1.0.2", - "minipass-fetch": "^1.3.2", - "minipass-flush": "^1.0.5", - "minipass-pipeline": "^1.2.4", - "negotiator": "^0.6.2", - "promise-retry": "^2.0.1", - "socks-proxy-agent": "^6.0.0", - "ssri": "^8.0.0" - }, - "engines": { - "node": ">= 10" - } - }, - "node_modules/npm-check-updates/node_modules/node-gyp": { - "version": "8.4.1", - "resolved": "https://registry.npmjs.org/node-gyp/-/node-gyp-8.4.1.tgz", - "integrity": "sha512-olTJRgUtAb/hOXG0E93wZDs5YiJlgbXxTwQAFHyNlRsXQnYzUaF2aGgujZbw+hR8aF4ZG/rST57bWMWD16jr9w==", - "dev": true, - "dependencies": { - "env-paths": "^2.2.0", - "glob": "^7.1.4", - "graceful-fs": "^4.2.6", - "make-fetch-happen": "^9.1.0", - "nopt": "^5.0.0", - "npmlog": "^6.0.0", - "rimraf": "^3.0.2", - "semver": "^7.3.5", - "tar": "^6.1.2", - "which": "^2.0.2" - }, - "bin": { - "node-gyp": "bin/node-gyp.js" - }, - "engines": { - "node": ">= 10.12.0" - } - }, - "node_modules/npm-check-updates/node_modules/nopt": { - "version": "5.0.0", - "resolved": "https://registry.npmjs.org/nopt/-/nopt-5.0.0.tgz", - "integrity": "sha512-Tbj67rffqceeLpcRXrT7vKAN8CwfPeIBgM7E6iBkmKLV7bEMwpGgYLGv0jACUsECaa/vuxP0IjEont6umdMgtQ==", - "dev": true, - "dependencies": { - "abbrev": "1" - }, - "bin": { - "nopt": "bin/nopt.js" - }, - "engines": { - "node": ">=6" - } - }, - "node_modules/npm-check-updates/node_modules/npm-packlist": { - "version": "3.0.0", - "resolved": "https://registry.npmjs.org/npm-packlist/-/npm-packlist-3.0.0.tgz", - "integrity": "sha512-L/cbzmutAwII5glUcf2DBRNY/d0TFd4e/FnaZigJV6JD85RHZXJFGwCndjMWiiViiWSsWt3tiOLpI3ByTnIdFQ==", - "dev": true, - "dependencies": { - "glob": "^7.1.6", - "ignore-walk": "^4.0.1", - "npm-bundled": "^1.1.1", - "npm-normalize-package-bin": "^1.0.1" - }, - "bin": { - "npm-packlist": "bin/index.js" - }, - "engines": { - "node": ">=10" - } - }, - "node_modules/npm-check-updates/node_modules/npm-registry-fetch": { - "version": "11.0.0", - "resolved": "https://registry.npmjs.org/npm-registry-fetch/-/npm-registry-fetch-11.0.0.tgz", - "integrity": "sha512-jmlgSxoDNuhAtxUIG6pVwwtz840i994dL14FoNVZisrmZW5kWd63IUTNv1m/hyRSGSqWjCUp/YZlS1BJyNp9XA==", - "dev": true, - "dependencies": { - "make-fetch-happen": "^9.0.1", - "minipass": "^3.1.3", - "minipass-fetch": "^1.3.0", - "minipass-json-stream": "^1.0.1", - "minizlib": "^2.0.0", - "npm-package-arg": "^8.0.0" - }, - "engines": { - "node": ">=10" - } - }, - "node_modules/npm-check-updates/node_modules/npmlog": { - "version": "6.0.0", - "resolved": "https://registry.npmjs.org/npmlog/-/npmlog-6.0.0.tgz", - "integrity": "sha512-03ppFRGlsyUaQFbGC2C8QWJN/C/K7PsfyD9aQdhVKAQIH4sQBc8WASqFBP7O+Ut4d2oo5LoeoboB3cGdBZSp6Q==", - "dev": true, - "dependencies": { - "are-we-there-yet": "^2.0.0", - "console-control-strings": "^1.1.0", - "gauge": "^4.0.0", - "set-blocking": "^2.0.0" - }, - "engines": { - "node": "^12.13.0 || ^14.15.0 || >=16" - } - }, - "node_modules/npm-check-updates/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/npm-check-updates/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/npm-check-updates/node_modules/pacote": { - "version": "12.0.2", - "resolved": "https://registry.npmjs.org/pacote/-/pacote-12.0.2.tgz", - "integrity": "sha512-Ar3mhjcxhMzk+OVZ8pbnXdb0l8+pimvlsqBGRNkble2NVgyqOGE3yrCGi/lAYq7E7NRDMz89R1Wx5HIMCGgeYg==", - "dev": true, - "dependencies": { - "@npmcli/git": "^2.1.0", - "@npmcli/installed-package-contents": "^1.0.6", - "@npmcli/promise-spawn": "^1.2.0", - "@npmcli/run-script": "^2.0.0", - "cacache": "^15.0.5", - "chownr": "^2.0.0", - "fs-minipass": "^2.1.0", - "infer-owner": "^1.0.4", - "minipass": "^3.1.3", - "mkdirp": "^1.0.3", - "npm-package-arg": "^8.0.1", - "npm-packlist": "^3.0.0", - "npm-pick-manifest": "^6.0.0", - "npm-registry-fetch": "^11.0.0", - "promise-retry": "^2.0.1", - "read-package-json-fast": "^2.0.1", - "rimraf": "^3.0.2", - "ssri": "^8.0.1", - "tar": "^6.1.0" - }, - "bin": { - "pacote": "lib/bin.js" - }, - "engines": { - "node": "^12.13.0 || ^14.15.0 || >=16" - } - }, - "node_modules/npm-check-updates/node_modules/socks-proxy-agent": { - "version": "6.1.1", - "resolved": "https://registry.npmjs.org/socks-proxy-agent/-/socks-proxy-agent-6.1.1.tgz", - "integrity": "sha512-t8J0kG3csjA4g6FTbsMOWws+7R7vuRC8aQ/wy3/1OWmsgwA68zs/+cExQ0koSitUDXqhufF/YJr9wtNMZHw5Ew==", - "dev": true, - "dependencies": { - "agent-base": "^6.0.2", - "debug": "^4.3.1", - "socks": "^2.6.1" - }, - "engines": { - "node": ">= 10" - } - }, - "node_modules/npm-install-checks": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/npm-install-checks/-/npm-install-checks-4.0.0.tgz", - "integrity": "sha512-09OmyDkNLYwqKPOnbI8exiOZU2GVVmQp7tgez2BPi5OZC8M82elDAps7sxC4l//uSUtotWqoEIDwjRvWH4qz8w==", - "dev": true, - "dependencies": { - "semver": "^7.1.1" - }, - "engines": { - "node": ">=10" - } - }, - "node_modules/npm-lifecycle": { - "version": "3.1.5", - "resolved": "https://registry.npmjs.org/npm-lifecycle/-/npm-lifecycle-3.1.5.tgz", - "integrity": "sha512-lDLVkjfZmvmfvpvBzA4vzee9cn+Me4orq0QF8glbswJVEbIcSNWib7qGOffolysc3teCqbbPZZkzbr3GQZTL1g==", - "dev": true, - "dependencies": { - "byline": "^5.0.0", - "graceful-fs": "^4.1.15", - "node-gyp": "^5.0.2", - "resolve-from": "^4.0.0", - "slide": "^1.1.6", - "uid-number": "0.0.6", - "umask": "^1.1.0", - "which": "^1.3.1" - } - }, - "node_modules/npm-lifecycle/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/npm-normalize-package-bin": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/npm-normalize-package-bin/-/npm-normalize-package-bin-1.0.1.tgz", - "integrity": "sha512-EPfafl6JL5/rU+ot6P3gRSCpPDW5VmIzX959Ob1+ySFUuuYHWHekXpwdUZcKP5C+DS4GEtdJluwBjnsNDl+fSA==", - "dev": true - }, - "node_modules/npm-package-arg": { - "version": "8.1.5", - "resolved": "https://registry.npmjs.org/npm-package-arg/-/npm-package-arg-8.1.5.tgz", - "integrity": "sha512-LhgZrg0n0VgvzVdSm1oiZworPbTxYHUJCgtsJW8mGvlDpxTM1vSJc3m5QZeUkhAHIzbz3VCHd/R4osi1L1Tg/Q==", - "dev": true, - "dependencies": { - "hosted-git-info": "^4.0.1", - "semver": "^7.3.4", - "validate-npm-package-name": "^3.0.0" - }, - "engines": { - "node": ">=10" - } - }, - "node_modules/npm-packlist": { - "version": "2.2.2", - "resolved": "https://registry.npmjs.org/npm-packlist/-/npm-packlist-2.2.2.tgz", - "integrity": "sha512-Jt01acDvJRhJGthnUJVF/w6gumWOZxO7IkpY/lsX9//zqQgnF7OJaxgQXcerd4uQOLu7W5bkb4mChL9mdfm+Zg==", - "dev": true, - "dependencies": { - "glob": "^7.1.6", - "ignore-walk": "^3.0.3", - "npm-bundled": "^1.1.1", - "npm-normalize-package-bin": "^1.0.1" - }, - "bin": { - "npm-packlist": "bin/index.js" - }, - "engines": { - "node": ">=10" - } - }, - "node_modules/npm-pick-manifest": { - "version": "6.1.1", - "resolved": "https://registry.npmjs.org/npm-pick-manifest/-/npm-pick-manifest-6.1.1.tgz", - "integrity": "sha512-dBsdBtORT84S8V8UTad1WlUyKIY9iMsAmqxHbLdeEeBNMLQDlDWWra3wYUx9EBEIiG/YwAy0XyNHDd2goAsfuA==", - "dev": true, - "dependencies": { - "npm-install-checks": "^4.0.0", - "npm-normalize-package-bin": "^1.0.1", - "npm-package-arg": "^8.1.2", - "semver": "^7.3.4" - } - }, - "node_modules/npm-registry-fetch": { - "version": "9.0.0", - "resolved": "https://registry.npmjs.org/npm-registry-fetch/-/npm-registry-fetch-9.0.0.tgz", - "integrity": "sha512-PuFYYtnQ8IyVl6ib9d3PepeehcUeHN9IO5N/iCRhyg9tStQcqGQBRVHmfmMWPDERU3KwZoHFvbJ4FPXPspvzbA==", - "dev": true, - "dependencies": { - "@npmcli/ci-detect": "^1.0.0", - "lru-cache": "^6.0.0", - "make-fetch-happen": "^8.0.9", - "minipass": "^3.1.3", - "minipass-fetch": "^1.3.0", - "minipass-json-stream": "^1.0.1", - "minizlib": "^2.0.0", - "npm-package-arg": "^8.0.0" - }, - "engines": { - "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==", - "dependencies": { - "path-key": "^3.0.0" - }, - "engines": { - "node": ">=8" - } - }, - "node_modules/npmlog": { - "version": "4.1.2", - "resolved": "https://registry.npmjs.org/npmlog/-/npmlog-4.1.2.tgz", - "integrity": "sha512-2uUqazuKlTaSI/dC8AzicUck7+IrEaOnN/e0jd3Xtt1KcGpwx30v50mL7oPyr/h9bL3E4aZccVwpwP+5W9Vjkg==", - "dev": true, - "dependencies": { - "are-we-there-yet": "~1.1.2", - "console-control-strings": "~1.1.0", - "gauge": "~2.7.3", - "set-blocking": "~2.0.0" - } - }, - "node_modules/number-is-nan": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/number-is-nan/-/number-is-nan-1.0.1.tgz", - "integrity": "sha1-CXtgK1NCKlIsGvuHkDGDNpQaAR0=", - "dev": true, - "engines": { - "node": ">=0.10.0" - } - }, - "node_modules/nyc": { - "version": "15.1.0", - "resolved": "https://registry.npmjs.org/nyc/-/nyc-15.1.0.tgz", - "integrity": "sha512-jMW04n9SxKdKi1ZMGhvUTHBN0EICCRkHemEoE5jm6mTYcqcdas0ATzgUgejlQUHMvpnOZqGB5Xxsv9KxJW1j8A==", - "dev": true, - "dependencies": { - "@istanbuljs/load-nyc-config": "^1.0.0", - "@istanbuljs/schema": "^0.1.2", - "caching-transform": "^4.0.0", - "convert-source-map": "^1.7.0", - "decamelize": "^1.2.0", - "find-cache-dir": "^3.2.0", - "find-up": "^4.1.0", - "foreground-child": "^2.0.0", - "get-package-type": "^0.1.0", - "glob": "^7.1.6", - "istanbul-lib-coverage": "^3.0.0", - "istanbul-lib-hook": "^3.0.0", - "istanbul-lib-instrument": "^4.0.0", - "istanbul-lib-processinfo": "^2.0.2", - "istanbul-lib-report": "^3.0.0", - "istanbul-lib-source-maps": "^4.0.0", - "istanbul-reports": "^3.0.2", - "make-dir": "^3.0.0", - "node-preload": "^0.2.1", - "p-map": "^3.0.0", - "process-on-spawn": "^1.0.0", - "resolve-from": "^5.0.0", - "rimraf": "^3.0.0", - "signal-exit": "^3.0.2", - "spawn-wrap": "^2.0.0", - "test-exclude": "^6.0.0", - "yargs": "^15.0.2" - }, - "bin": { - "nyc": "bin/nyc.js" - }, - "engines": { - "node": ">=8.9" - } - }, - "node_modules/nyc/node_modules/cliui": { - "version": "6.0.0", - "resolved": "https://registry.npmjs.org/cliui/-/cliui-6.0.0.tgz", - "integrity": "sha512-t6wbgtoCXvAzst7QgXxJYqPt0usEfbgQdftEPbLL/cvv6HPE5VgvqCuAIDR0NgU52ds6rFwqrgakNLrHEjCbrQ==", - "dev": true, - "dependencies": { - "string-width": "^4.2.0", - "strip-ansi": "^6.0.0", - "wrap-ansi": "^6.2.0" - } - }, - "node_modules/nyc/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/nyc/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/nyc/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/nyc/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/nyc/node_modules/p-map": { - "version": "3.0.0", - "resolved": "https://registry.npmjs.org/p-map/-/p-map-3.0.0.tgz", - "integrity": "sha512-d3qXVTF/s+W+CdJ5A29wywV2n8CQQYahlgz2bFiA+4eVNJbHJodPZ+/gXwPGh0bOqA+j8S+6+ckmvLGPk1QpxQ==", - "dev": true, - "dependencies": { - "aggregate-error": "^3.0.0" - }, - "engines": { - "node": ">=8" - } - }, - "node_modules/nyc/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/nyc/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/nyc/node_modules/wrap-ansi": { - "version": "6.2.0", - "resolved": "https://registry.npmjs.org/wrap-ansi/-/wrap-ansi-6.2.0.tgz", - "integrity": "sha512-r6lPcBGxZXlIcymEu7InxDMhdW0KDxpLgoFLcguasxCaJ/SOIZwINatK9KY/tf+ZrlywOKU0UDj3ATXUBfxJXA==", - "dev": true, - "dependencies": { - "ansi-styles": "^4.0.0", - "string-width": "^4.1.0", - "strip-ansi": "^6.0.0" - }, - "engines": { - "node": ">=8" - } - }, - "node_modules/nyc/node_modules/y18n": { - "version": "4.0.3", - "resolved": "https://registry.npmjs.org/y18n/-/y18n-4.0.3.tgz", - "integrity": "sha512-JKhqTOwSrqNA1NY5lSztJ1GrBiUodLMmIZuLiDaMRJ+itFd+ABVE8XBjOvIWL+rSqNDC74LCSFmlb/U4UZ4hJQ==", - "dev": true - }, - "node_modules/nyc/node_modules/yargs": { - "version": "15.4.1", - "resolved": "https://registry.npmjs.org/yargs/-/yargs-15.4.1.tgz", - "integrity": "sha512-aePbxDmcYW++PaqBsJ+HYUFwCdv4LVvdnhBy78E57PIor8/OVvhMrADFFEDh8DHDFRv/O9i3lPhsENjO7QX0+A==", - "dev": true, - "dependencies": { - "cliui": "^6.0.0", - "decamelize": "^1.2.0", - "find-up": "^4.1.0", - "get-caller-file": "^2.0.1", - "require-directory": "^2.1.1", - "require-main-filename": "^2.0.0", - "set-blocking": "^2.0.0", - "string-width": "^4.2.0", - "which-module": "^2.0.0", - "y18n": "^4.0.0", - "yargs-parser": "^18.1.2" - }, - "engines": { - "node": ">=8" - } - }, - "node_modules/nyc/node_modules/yargs-parser": { - "version": "18.1.3", - "resolved": "https://registry.npmjs.org/yargs-parser/-/yargs-parser-18.1.3.tgz", - "integrity": "sha512-o50j0JeToy/4K6OZcaQmW6lyXXKhq7csREXcDwk2omFPJEwUNOVtJKvmDr9EI1fAJZUyZcRF7kxGBWmRXudrCQ==", - "dev": true, - "dependencies": { - "camelcase": "^5.0.0", - "decamelize": "^1.2.0" - }, - "engines": { - "node": ">=6" - } - }, - "node_modules/oauth-sign": { - "version": "0.9.0", - "resolved": "https://registry.npmjs.org/oauth-sign/-/oauth-sign-0.9.0.tgz", - "integrity": "sha512-fexhUFFPTGV8ybAtSIGbV6gOkSv8UtRbDBnAyLQw4QPKkgNlsH2ByPGtMUqdWkos6YCRmAqViwgZrJc/mRDzZQ==", - "engines": { - "node": "*" - } - }, - "node_modules/object-assign": { - "version": "4.1.1", - "resolved": "https://registry.npmjs.org/object-assign/-/object-assign-4.1.1.tgz", - "integrity": "sha1-IQmtx5ZYh8/AXLvUQsrIv7s2CGM=", - "engines": { - "node": ">=0.10.0" - } - }, - "node_modules/object-inspect": { - "version": "1.12.0", - "resolved": "https://registry.npmjs.org/object-inspect/-/object-inspect-1.12.0.tgz", - "integrity": "sha512-Ho2z80bVIvJloH+YzRmpZVQe87+qASmBUKZDWgx9cu+KDrX2ZDH/3tMy+gXbZETVGs2M8YdxObOh7XAtim9Y0g==", - "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==", - "engines": { - "node": ">= 0.4" - } - }, - "node_modules/object.assign": { - "version": "4.1.2", - "resolved": "https://registry.npmjs.org/object.assign/-/object.assign-4.1.2.tgz", - "integrity": "sha512-ixT2L5THXsApyiUPYKmW+2EHpXXe5Ii3M+f4e+aJFAHao5amFRW6J0OO6c/LU8Be47utCx2GL89hxGB6XSmKuQ==", - "dependencies": { - "call-bind": "^1.0.0", - "define-properties": "^1.1.3", - "has-symbols": "^1.0.1", - "object-keys": "^1.1.1" - }, - "engines": { - "node": ">= 0.4" - }, - "funding": { - "url": "https://github.com/sponsors/ljharb" - } - }, - "node_modules/object.getownpropertydescriptors": { - "version": "2.1.3", - "resolved": "https://registry.npmjs.org/object.getownpropertydescriptors/-/object.getownpropertydescriptors-2.1.3.tgz", - "integrity": "sha512-VdDoCwvJI4QdC6ndjpqFmoL3/+HxffFBbcJzKi5hwLLqqx3mdbedRpfZDdK0SrOSauj8X4GzBvnDZl4vTN7dOw==", - "dev": true, - "dependencies": { - "call-bind": "^1.0.2", - "define-properties": "^1.1.3", - "es-abstract": "^1.19.1" - }, - "engines": { - "node": ">= 0.8" - }, - "funding": { - "url": "https://github.com/sponsors/ljharb" - } - }, - "node_modules/object.omit": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/object.omit/-/object.omit-2.0.1.tgz", - "integrity": "sha1-Gpx0SCnznbuFjHbKNXmuKlTr0fo=", - "dependencies": { - "for-own": "^0.1.4", - "is-extendable": "^0.1.1" - }, - "engines": { - "node": ">=0.10.0" - } - }, - "node_modules/object.values": { - "version": "1.1.5", - "resolved": "https://registry.npmjs.org/object.values/-/object.values-1.1.5.tgz", - "integrity": "sha512-QUZRW0ilQ3PnPpbNtgdNV1PDbEqLIiSFB3l+EnGtBQ/8SUTLj1PZwtQHABZtLgwpJZTSZhuGLOGk57Drx2IvYg==", - "dev": true, - "dependencies": { - "call-bind": "^1.0.2", - "define-properties": "^1.1.3", - "es-abstract": "^1.19.1" - }, - "engines": { - "node": ">= 0.4" - }, - "funding": { - "url": "https://github.com/sponsors/ljharb" - } - }, - "node_modules/on-finished": { - "version": "2.3.0", - "resolved": "https://registry.npmjs.org/on-finished/-/on-finished-2.3.0.tgz", - "integrity": "sha1-IPEzZIGwg811M3mSoWlxqi2QaUc=", - "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==", - "engines": { - "node": ">= 0.8" - } - }, - "node_modules/once": { - "version": "1.4.0", - "resolved": "https://registry.npmjs.org/once/-/once-1.4.0.tgz", - "integrity": "sha1-WDsap3WWHUsROsF9nFC6753Xa9E=", - "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==", - "dependencies": { - "mimic-fn": "^2.1.0" - }, - "engines": { - "node": ">=6" - }, - "funding": { - "url": "https://github.com/sponsors/sindresorhus" - } - }, - "node_modules/only": { - "version": "0.0.2", - "resolved": "https://registry.npmjs.org/only/-/only-0.0.2.tgz", - "integrity": "sha1-Kv3oTQPlC5qO3EROMGEKcCle37Q=" - }, - "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/os-homedir": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/os-homedir/-/os-homedir-1.0.2.tgz", - "integrity": "sha1-/7xJiDNuDoM94MFox+8VISGqf7M=", - "engines": { - "node": ">=0.10.0" - } - }, - "node_modules/os-tmpdir": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/os-tmpdir/-/os-tmpdir-1.0.2.tgz", - "integrity": "sha1-u+Z0BseaqFxc/sdm/lc0VV36EnQ=", - "engines": { - "node": ">=0.10.0" - } - }, - "node_modules/osenv": { - "version": "0.1.5", - "resolved": "https://registry.npmjs.org/osenv/-/osenv-0.1.5.tgz", - "integrity": "sha512-0CWcCECdMVc2Rw3U5w9ZjqX6ga6ubk1xDVKxtBQPK7wis/0F2r9T6k4ydGYhecl7YUBxBVxhL5oisPsNxAPe2g==", - "dev": true, - "dependencies": { - "os-homedir": "^1.0.0", - "os-tmpdir": "^1.0.0" - } - }, - "node_modules/p-cancelable": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/p-cancelable/-/p-cancelable-1.1.0.tgz", - "integrity": "sha512-s73XxOZ4zpt1edZYZzvhqFa6uvQc1vwUa0K0BdtIZgQMAJj9IbebH+JkgKZc9h+B05PKHLOTl4ajG1BmNrVZlw==", - "dev": true, - "engines": { - "node": ">=6" - } - }, - "node_modules/p-finally": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/p-finally/-/p-finally-1.0.0.tgz", - "integrity": "sha1-P7z7FbiZpEEjs0ttzBi3JDNqLK4=", - "dev": true, - "engines": { - "node": ">=4" - } - }, - "node_modules/p-limit": { - "version": "1.3.0", - "resolved": "https://registry.npmjs.org/p-limit/-/p-limit-1.3.0.tgz", - "integrity": "sha512-vvcXsLAJ9Dr5rQOPk7toZQZJApBl2K4J6dANSsEuh6QI41JYcsS/qhTGa9ErIUUgK3WNQoJYvylxvjqmiqEA9Q==", - "dependencies": { - "p-try": "^1.0.0" - }, - "engines": { - "node": ">=4" - } - }, - "node_modules/p-locate": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/p-locate/-/p-locate-2.0.0.tgz", - "integrity": "sha1-IKAQOyIqcMj9OcwuWAaA893l7EM=", - "dependencies": { - "p-limit": "^1.1.0" - }, - "engines": { - "node": ">=4" - } - }, - "node_modules/p-map": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/p-map/-/p-map-4.0.0.tgz", - "integrity": "sha512-/bjOqmgETBYB5BoEeGVea8dmvHb2m9GLy1E9W43yeyfP6QQCZGFNa+XRceJEuDB6zqr+gKpIAmlLebMpykw/MQ==", - "dev": true, - "dependencies": { - "aggregate-error": "^3.0.0" - }, - "engines": { - "node": ">=10" - }, - "funding": { - "url": "https://github.com/sponsors/sindresorhus" - } - }, - "node_modules/p-map-series": { - "version": "2.1.0", - "resolved": "https://registry.npmjs.org/p-map-series/-/p-map-series-2.1.0.tgz", - "integrity": "sha512-RpYIIK1zXSNEOdwxcfe7FdvGcs7+y5n8rifMhMNWvaxRNMPINJHF5GDeuVxWqnfrcHPSCnp7Oo5yNXHId9Av2Q==", - "dev": true, - "engines": { - "node": ">=8" - } - }, - "node_modules/p-pipe": { - "version": "3.1.0", - "resolved": "https://registry.npmjs.org/p-pipe/-/p-pipe-3.1.0.tgz", - "integrity": "sha512-08pj8ATpzMR0Y80x50yJHn37NF6vjrqHutASaX5LiH5npS9XPvrUmscd9MF5R4fuYRHOxQR1FfMIlF7AzwoPqw==", - "dev": true, - "engines": { - "node": ">=8" - }, - "funding": { - "url": "https://github.com/sponsors/sindresorhus" - } - }, - "node_modules/p-queue": { - "version": "6.6.2", - "resolved": "https://registry.npmjs.org/p-queue/-/p-queue-6.6.2.tgz", - "integrity": "sha512-RwFpb72c/BhQLEXIZ5K2e+AhgNVmIejGlTgiB9MzZ0e93GRvqZ7uSi0dvRF7/XIXDeNkra2fNHBxTyPDGySpjQ==", - "dev": true, - "dependencies": { - "eventemitter3": "^4.0.4", - "p-timeout": "^3.2.0" - }, - "engines": { - "node": ">=8" - }, - "funding": { - "url": "https://github.com/sponsors/sindresorhus" - } - }, - "node_modules/p-reduce": { - "version": "2.1.0", - "resolved": "https://registry.npmjs.org/p-reduce/-/p-reduce-2.1.0.tgz", - "integrity": "sha512-2USApvnsutq8uoxZBGbbWM0JIYLiEMJ9RlaN7fAzVNb9OZN0SHjjTTfIcb667XynS5Y1VhwDJVDa72TnPzAYWw==", - "dev": true, - "engines": { - "node": ">=8" - } - }, - "node_modules/p-timeout": { - "version": "3.2.0", - "resolved": "https://registry.npmjs.org/p-timeout/-/p-timeout-3.2.0.tgz", - "integrity": "sha512-rhIwUycgwwKcP9yTOOFK/AKsAopjjCakVqLHePO3CC6Mir1Z99xT+R63jZxAT5lFZLa2inS5h+ZS2GvR99/FBg==", - "dev": true, - "dependencies": { - "p-finally": "^1.0.0" - }, - "engines": { - "node": ">=8" - } - }, - "node_modules/p-try": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/p-try/-/p-try-1.0.0.tgz", - "integrity": "sha1-y8ec26+P1CKOE/Yh8rGiN8GyB7M=", - "engines": { - "node": ">=4" - } - }, - "node_modules/p-waterfall": { - "version": "2.1.1", - "resolved": "https://registry.npmjs.org/p-waterfall/-/p-waterfall-2.1.1.tgz", - "integrity": "sha512-RRTnDb2TBG/epPRI2yYXsimO0v3BXC8Yd3ogr1545IaqKK17VGhbWVeGGN+XfCm/08OK8635nH31c8bATkHuSw==", - "dev": true, - "dependencies": { - "p-reduce": "^2.0.0" - }, - "engines": { - "node": ">=8" - }, - "funding": { - "url": "https://github.com/sponsors/sindresorhus" - } - }, - "node_modules/package-hash": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/package-hash/-/package-hash-4.0.0.tgz", - "integrity": "sha512-whdkPIooSu/bASggZ96BWVvZTRMOFxnyUG5PnTSGKoJE2gd5mbVNmR2Nj20QFzxYYgAXpoqC+AiXzl+UMRh7zQ==", - "dev": true, - "dependencies": { - "graceful-fs": "^4.1.15", - "hasha": "^5.0.0", - "lodash.flattendeep": "^4.4.0", - "release-zalgo": "^1.0.0" - }, - "engines": { - "node": ">=8" - } - }, - "node_modules/package-json": { - "version": "6.5.0", - "resolved": "https://registry.npmjs.org/package-json/-/package-json-6.5.0.tgz", - "integrity": "sha512-k3bdm2n25tkyxcjSKzB5x8kfVxlMdgsbPr0GkZcwHsLpba6cBjqCt1KlcChKEvxHIcTB1FVMuwoijZ26xex5MQ==", - "dev": true, - "dependencies": { - "got": "^9.6.0", - "registry-auth-token": "^4.0.0", - "registry-url": "^5.0.0", - "semver": "^6.2.0" - }, - "engines": { - "node": ">=8" - } - }, - "node_modules/package-json/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/pacote": { - "version": "11.3.5", - "resolved": "https://registry.npmjs.org/pacote/-/pacote-11.3.5.tgz", - "integrity": "sha512-fT375Yczn4zi+6Hkk2TBe1x1sP8FgFsEIZ2/iWaXY2r/NkhDJfxbcn5paz1+RTFCyNf+dPnaoBDJoAxXSU8Bkg==", - "dev": true, - "dependencies": { - "@npmcli/git": "^2.1.0", - "@npmcli/installed-package-contents": "^1.0.6", - "@npmcli/promise-spawn": "^1.2.0", - "@npmcli/run-script": "^1.8.2", - "cacache": "^15.0.5", - "chownr": "^2.0.0", - "fs-minipass": "^2.1.0", - "infer-owner": "^1.0.4", - "minipass": "^3.1.3", - "mkdirp": "^1.0.3", - "npm-package-arg": "^8.0.1", - "npm-packlist": "^2.1.4", - "npm-pick-manifest": "^6.0.0", - "npm-registry-fetch": "^11.0.0", - "promise-retry": "^2.0.1", - "read-package-json-fast": "^2.0.1", - "rimraf": "^3.0.2", - "ssri": "^8.0.1", - "tar": "^6.1.0" - }, - "bin": { - "pacote": "lib/bin.js" - }, - "engines": { - "node": ">=10" - } - }, - "node_modules/pacote/node_modules/make-fetch-happen": { - "version": "9.1.0", - "resolved": "https://registry.npmjs.org/make-fetch-happen/-/make-fetch-happen-9.1.0.tgz", - "integrity": "sha512-+zopwDy7DNknmwPQplem5lAZX/eCOzSvSNNcSKm5eVwTkOBzoktEfXsa9L23J/GIRhxRsaxzkPEhrJEpE2F4Gg==", - "dev": true, - "dependencies": { - "agentkeepalive": "^4.1.3", - "cacache": "^15.2.0", - "http-cache-semantics": "^4.1.0", - "http-proxy-agent": "^4.0.1", - "https-proxy-agent": "^5.0.0", - "is-lambda": "^1.0.1", - "lru-cache": "^6.0.0", - "minipass": "^3.1.3", - "minipass-collect": "^1.0.2", - "minipass-fetch": "^1.3.2", - "minipass-flush": "^1.0.5", - "minipass-pipeline": "^1.2.4", - "negotiator": "^0.6.2", - "promise-retry": "^2.0.1", - "socks-proxy-agent": "^6.0.0", - "ssri": "^8.0.0" - }, - "engines": { - "node": ">= 10" - } - }, - "node_modules/pacote/node_modules/npm-registry-fetch": { - "version": "11.0.0", - "resolved": "https://registry.npmjs.org/npm-registry-fetch/-/npm-registry-fetch-11.0.0.tgz", - "integrity": "sha512-jmlgSxoDNuhAtxUIG6pVwwtz840i994dL14FoNVZisrmZW5kWd63IUTNv1m/hyRSGSqWjCUp/YZlS1BJyNp9XA==", - "dev": true, - "dependencies": { - "make-fetch-happen": "^9.0.1", - "minipass": "^3.1.3", - "minipass-fetch": "^1.3.0", - "minipass-json-stream": "^1.0.1", - "minizlib": "^2.0.0", - "npm-package-arg": "^8.0.0" - }, - "engines": { - "node": ">=10" - } - }, - "node_modules/pacote/node_modules/socks-proxy-agent": { - "version": "6.1.1", - "resolved": "https://registry.npmjs.org/socks-proxy-agent/-/socks-proxy-agent-6.1.1.tgz", - "integrity": "sha512-t8J0kG3csjA4g6FTbsMOWws+7R7vuRC8aQ/wy3/1OWmsgwA68zs/+cExQ0koSitUDXqhufF/YJr9wtNMZHw5Ew==", - "dev": true, - "dependencies": { - "agent-base": "^6.0.2", - "debug": "^4.3.1", - "socks": "^2.6.1" - }, - "engines": { - "node": ">= 10" - } - }, - "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-github-url": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/parse-github-url/-/parse-github-url-1.0.2.tgz", - "integrity": "sha512-kgBf6avCbO3Cn6+RnzRGLkUsv4ZVqv/VfAYkRsyBcgkshNvVBkRn1FEZcW0Jb+npXQWm2vHPnnOqFteZxRRGNw==", - "dev": true, - "bin": { - "parse-github-url": "cli.js" - }, - "engines": { - "node": ">=0.10.0" - } - }, - "node_modules/parse-glob": { - "version": "3.0.4", - "resolved": "https://registry.npmjs.org/parse-glob/-/parse-glob-3.0.4.tgz", - "integrity": "sha1-ssN2z7EfNVE7rdFz7wu246OIORw=", - "dependencies": { - "glob-base": "^0.3.0", - "is-dotfile": "^1.0.0", - "is-extglob": "^1.0.0", - "is-glob": "^2.0.0" - }, - "engines": { - "node": ">=0.10.0" - } - }, - "node_modules/parse-glob/node_modules/is-extglob": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/is-extglob/-/is-extglob-1.0.0.tgz", - "integrity": "sha1-rEaBd8SUNAWgkvyPKXYMb/xiBsA=", - "engines": { - "node": ">=0.10.0" - } - }, - "node_modules/parse-glob/node_modules/is-glob": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/is-glob/-/is-glob-2.0.1.tgz", - "integrity": "sha1-0Jb5JqPe1WAPP9/ZEZjLCIjC2GM=", - "dependencies": { - "is-extglob": "^1.0.0" - }, - "engines": { - "node": ">=0.10.0" - } - }, - "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/parse-path": { - "version": "4.0.3", - "resolved": "https://registry.npmjs.org/parse-path/-/parse-path-4.0.3.tgz", - "integrity": "sha512-9Cepbp2asKnWTJ9x2kpw6Fe8y9JDbqwahGCTvklzd/cEq5C5JC59x2Xb0Kx+x0QZ8bvNquGO8/BWP0cwBHzSAA==", - "dev": true, - "dependencies": { - "is-ssh": "^1.3.0", - "protocols": "^1.4.0", - "qs": "^6.9.4", - "query-string": "^6.13.8" - } - }, - "node_modules/parse-url": { - "version": "6.0.0", - "resolved": "https://registry.npmjs.org/parse-url/-/parse-url-6.0.0.tgz", - "integrity": "sha512-cYyojeX7yIIwuJzledIHeLUBVJ6COVLeT4eF+2P6aKVzwvgKQPndCBv3+yQ7pcWjqToYwaligxzSYNNmGoMAvw==", - "dev": true, - "dependencies": { - "is-ssh": "^1.3.0", - "normalize-url": "^6.1.0", - "parse-path": "^4.0.0", - "protocols": "^1.4.0" - } - }, - "node_modules/parseqs": { - "version": "0.0.6", - "resolved": "https://registry.npmjs.org/parseqs/-/parseqs-0.0.6.tgz", - "integrity": "sha512-jeAGzMDbfSHHA091hr0r31eYfTig+29g3GKKE/PPbEQ65X0lmMwlEoqmhzu0iztID5uJpZsFlUPDP8ThPL7M8w==" - }, - "node_modules/parseuri": { - "version": "0.0.6", - "resolved": "https://registry.npmjs.org/parseuri/-/parseuri-0.0.6.tgz", - "integrity": "sha512-AUjen8sAkGgao7UyCX6Ahv0gIK2fABKmYjvP4xmy5JaKvcbTRueIqIPHLAfq30xJddqSE033IOMUSOMCcK3Sow==" - }, - "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-browserify": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/path-browserify/-/path-browserify-1.0.0.tgz", - "integrity": "sha512-Hkavx/nY4/plImrZPHRk2CL9vpOymZLgEbMNX1U0bjcBL7QN9wODxyx0yaMZURSQaUtSEvDrfAvxa9oPb0at9g==" - }, - "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==", - "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": "sha1-F0uSaHNVNP+8es5r9TpanhtcX18=", - "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==", - "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==" - }, - "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": "sha1-32BBeABfUi8V60SQ5yR6G/qmf4w=" - }, - "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/pend": { - "version": "1.2.0", - "resolved": "https://registry.npmjs.org/pend/-/pend-1.2.0.tgz", - "integrity": "sha1-elfrVQpng/kRUzH89GY9XI4AelA=" - }, - "node_modules/performance-now": { - "version": "2.1.0", - "resolved": "https://registry.npmjs.org/performance-now/-/performance-now-2.1.0.tgz", - "integrity": "sha1-Ywn04OX6kT7BxpMHrjZLSzd8nns=", - "dev": true - }, - "node_modules/picocolors": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/picocolors/-/picocolors-1.0.0.tgz", - "integrity": "sha512-1fygroTLlHu66zi26VoTDv8yRgm0Fccecssto+MhsZ0D/DGW2sm8E8AjW7NU5VVTRt5GxbeZ5qBuJr+HyLYkjQ==" - }, - "node_modules/picomatch": { - "version": "2.3.1", - "resolved": "https://registry.npmjs.org/picomatch/-/picomatch-2.3.1.tgz", - "integrity": "sha512-JU3teHTNjmE2VCGFzuY8EXzCDVwEqB2a8fsIvwaStHhAWJEeVd1o1QD80CU6+ZdEXXSLbSsuLwJjkCBWqRQUVA==", - "engines": { - "node": ">=8.6" - }, - "funding": { - "url": "https://github.com/sponsors/jonschlinkert" - } - }, - "node_modules/pify": { - "version": "5.0.0", - "resolved": "https://registry.npmjs.org/pify/-/pify-5.0.0.tgz", - "integrity": "sha512-eW/gHNMlxdSP6dmG6uJip6FXN0EQBwm2clYYd8Wul42Cwu/DK8HEftzsapcNdYe2MfLiIwZqsDk2RDEsTE79hA==", - "dev": true, - "engines": { - "node": ">=10" - }, - "funding": { - "url": "https://github.com/sponsors/sindresorhus" - } - }, - "node_modules/pinkie": { - "version": "2.0.4", - "resolved": "https://registry.npmjs.org/pinkie/-/pinkie-2.0.4.tgz", - "integrity": "sha1-clVrgM+g1IqXToDnckjoDtT3+HA=", - "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": "sha1-ITXW36ejWMBprJsXh3YogihFD/o=", - "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==", - "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==", - "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==", - "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==", - "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==", - "dependencies": { - "p-limit": "^2.2.0" - }, - "engines": { - "node": ">=8" - } - }, - "node_modules/pkg-dir/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==", - "engines": { - "node": ">=6" - } - }, - "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/prepend-http": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/prepend-http/-/prepend-http-2.0.0.tgz", - "integrity": "sha1-6SQ0v6XqjBn0HN/UAddBo8gZ2Jc=", - "dev": true, - "engines": { - "node": ">=4" - } - }, - "node_modules/preserve": { - "version": "0.2.0", - "resolved": "https://registry.npmjs.org/preserve/-/preserve-0.2.0.tgz", - "integrity": "sha1-gV7R9uvGWSb4ZbMQwHE7yzMVzks=", - "engines": { - "node": ">=0.10.0" - } - }, - "node_modules/private": { - "version": "0.1.8", - "resolved": "https://registry.npmjs.org/private/-/private-0.1.8.tgz", - "integrity": "sha512-VvivMrbvd2nKkiG38qjULzlc+4Vx4wm/whI9pQD35YrARNnhxeiRktSOhSukRLFNlzg6Br/cJPet5J/u19r/mg==", - "engines": { - "node": ">= 0.6" - } - }, - "node_modules/process": { - "version": "0.11.10", - "resolved": "https://registry.npmjs.org/process/-/process-0.11.10.tgz", - "integrity": "sha1-czIwDoQBYb2j5podHZGn1LwW8YI=", - "engines": { - "node": ">= 0.6.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==" - }, - "node_modules/process-on-spawn": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/process-on-spawn/-/process-on-spawn-1.0.0.tgz", - "integrity": "sha512-1WsPDsUSMmZH5LeMLegqkPDrsGgsWwk1Exipy2hvB0o/F0ASzbpIctSCcZIK1ykJvtTJULEH+20WOFjMvGnCTg==", - "dev": true, - "dependencies": { - "fromentries": "^1.2.0" - }, - "engines": { - "node": ">=8" - } - }, - "node_modules/progress": { - "version": "2.0.3", - "resolved": "https://registry.npmjs.org/progress/-/progress-2.0.3.tgz", - "integrity": "sha512-7PiHtLll5LdnKIMw100I+8xJXR5gW2QwWYkT6iJva0bXitZKa/XMrSbdmg3r2Xnaidz9Qumd0VPaMrZlF9V9sA==", - "engines": { - "node": ">=0.4.0" - } - }, - "node_modules/promise-inflight": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/promise-inflight/-/promise-inflight-1.0.1.tgz", - "integrity": "sha1-mEcocL8igTL8vdhoEputEsPAKeM=", - "dev": true - }, - "node_modules/promise-retry": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/promise-retry/-/promise-retry-2.0.1.tgz", - "integrity": "sha512-y+WKFlBR8BGXnsNlIHFGPZmyDf3DFMoLhaflAnyZgV6rG6xu+JwesTo2Q9R6XwYmtmwAFCkAk3e35jEdoeh/3g==", - "dev": true, - "dependencies": { - "err-code": "^2.0.2", - "retry": "^0.12.0" - }, - "engines": { - "node": ">=10" - } - }, - "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/promzard": { - "version": "0.3.0", - "resolved": "https://registry.npmjs.org/promzard/-/promzard-0.3.0.tgz", - "integrity": "sha1-JqXW7ox97kyxIggwWs+5O6OCqe4=", - "dev": true, - "dependencies": { - "read": "1" - } - }, - "node_modules/property-handlers": { - "version": "1.1.1", - "resolved": "https://registry.npmjs.org/property-handlers/-/property-handlers-1.1.1.tgz", - "integrity": "sha1-yyDTIqq32U//rCj0bJGGvVlHtLQ=" - }, - "node_modules/proto-list": { - "version": "1.2.4", - "resolved": "https://registry.npmjs.org/proto-list/-/proto-list-1.2.4.tgz", - "integrity": "sha1-IS1b/hMYMGpCD2QCuOJv85ZHqEk=", - "dev": true - }, - "node_modules/protocols": { - "version": "1.4.8", - "resolved": "https://registry.npmjs.org/protocols/-/protocols-1.4.8.tgz", - "integrity": "sha512-IgjKyaUSjsROSO8/D49Ab7hP8mJgTYcqApOqdPhLoPxAplXmkp+zRvsrSQjFn5by0rhm4VH0GAUELIPpx7B1yg==", - "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==", - "dependencies": { - "forwarded": "0.2.0", - "ipaddr.js": "1.9.1" - }, - "engines": { - "node": ">= 0.10" - } - }, - "node_modules/proxy-from-env": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/proxy-from-env/-/proxy-from-env-1.1.0.tgz", - "integrity": "sha512-D+zkORCbA9f1tdWRK0RaCR3GPv50cMxcrz4X8k5LTSUD1Dkw47mKJEZQNunItRTkWwgtaUSo1RVFRIG9ZXiFYg==" - }, - "node_modules/psl": { - "version": "1.8.0", - "resolved": "https://registry.npmjs.org/psl/-/psl-1.8.0.tgz", - "integrity": "sha512-RIdOzyoavK+hA18OGGWDqUTsCLhtA7IcZ/6NCs4fFJaHBDab+pDDmDIByWFRQJq2Cd7r1OoQxBGKOaztq+hjIQ==", - "dev": true - }, - "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.1.1", - "resolved": "https://registry.npmjs.org/punycode/-/punycode-2.1.1.tgz", - "integrity": "sha512-XRsRjdf+j5ml+y/6GKHPZbrF/8p2Yga0JPtdqTIY2Xe5ohJPD9saDJJLPvp9+NSBprVvevdXZybnj2cv8OEd0A==", - "engines": { - "node": ">=6" - } - }, - "node_modules/pupa": { - "version": "2.1.1", - "resolved": "https://registry.npmjs.org/pupa/-/pupa-2.1.1.tgz", - "integrity": "sha512-l1jNAspIBSFqbT+y+5FosojNpVpF94nlI+wDUpqP9enwOTfHx9f0gh5nB96vl+6yTpsJsypeNrwfzPrKuHB41A==", - "dev": true, - "dependencies": { - "escape-goat": "^2.0.0" - }, - "engines": { - "node": ">=8" - } - }, - "node_modules/puppeteer": { - "version": "0.12.0", - "resolved": "https://registry.npmjs.org/puppeteer/-/puppeteer-0.12.0.tgz", - "integrity": "sha512-H/bylN7FccwbN7JZoSP+xRozxgJEDNy4uC4p727cyttKUVNXYjFuEMueJYHW0pblnrfLEH341SyFJVWhJMLxKQ==", - "hasInstallScript": true, - "dependencies": { - "debug": "^2.6.8", - "extract-zip": "^1.6.5", - "https-proxy-agent": "^2.1.0", - "mime": "^1.3.4", - "progress": "^2.0.0", - "proxy-from-env": "^1.0.0", - "rimraf": "^2.6.1", - "ws": "^3.0.0" - }, - "engines": { - "node": ">=6.4.0" - } - }, - "node_modules/puppeteer/node_modules/agent-base": { - "version": "4.3.0", - "resolved": "https://registry.npmjs.org/agent-base/-/agent-base-4.3.0.tgz", - "integrity": "sha512-salcGninV0nPrwpGNn4VTXBb1SOuXQBiqbrNXoeizJsHrsL6ERFM2Ne3JUSBWRE6aeNJI2ROP/WEEIDUiDe3cg==", - "dependencies": { - "es6-promisify": "^5.0.0" - }, - "engines": { - "node": ">= 4.0.0" - } - }, - "node_modules/puppeteer/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/puppeteer/node_modules/https-proxy-agent": { - "version": "2.2.4", - "resolved": "https://registry.npmjs.org/https-proxy-agent/-/https-proxy-agent-2.2.4.tgz", - "integrity": "sha512-OmvfoQ53WLjtA9HeYP9RNrWMJzzAz1JGaSFr1nijg0PVR1JaD/xbJq1mdEIIlxGpXp9eSe/O2LgU9DJmTPd0Eg==", - "dependencies": { - "agent-base": "^4.3.0", - "debug": "^3.1.0" - }, - "engines": { - "node": ">= 4.5.0" - } - }, - "node_modules/puppeteer/node_modules/https-proxy-agent/node_modules/debug": { - "version": "3.2.7", - "resolved": "https://registry.npmjs.org/debug/-/debug-3.2.7.tgz", - "integrity": "sha512-CFjzYYAi4ThfiQvizrFQevTTXHtnCqWfe7x1AhgEscTz6ZbLbfoLRLPugTQyBth6f8ZERVUSyWHFD/7Wu4t1XQ==", - "dependencies": { - "ms": "^2.1.1" - } - }, - "node_modules/puppeteer/node_modules/https-proxy-agent/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/puppeteer/node_modules/ms": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/ms/-/ms-2.0.0.tgz", - "integrity": "sha1-VgiurfwAvmwpAd9fmGF4jeDVl8g=" - }, - "node_modules/puppeteer/node_modules/rimraf": { - "version": "2.7.1", - "resolved": "https://registry.npmjs.org/rimraf/-/rimraf-2.7.1.tgz", - "integrity": "sha512-uWjbaKIK3T1OSVptzX7Nl6PvQ3qAGtKEtVRjRuazjfL3Bx5eI409VZSqgND+4UNnmzLVdPj9FqFJNPqBZFve4w==", - "dependencies": { - "glob": "^7.1.3" - }, - "bin": { - "rimraf": "bin.js" - } - }, - "node_modules/q": { - "version": "1.5.1", - "resolved": "https://registry.npmjs.org/q/-/q-1.5.1.tgz", - "integrity": "sha1-fjL3W0E4EpHQRhHxvxQQmsAGUdc=", - "engines": { - "node": ">=0.6.0", - "teleport": ">=0.2.0" - } - }, - "node_modules/qs": { - "version": "6.10.2", - "resolved": "https://registry.npmjs.org/qs/-/qs-6.10.2.tgz", - "integrity": "sha512-mSIdjzqznWgfd4pMii7sHtaYF8rx8861hBO80SraY5GT0XQibWZWJSid0avzHGkDIZLImux2S5mXO0Hfct2QCw==", - "dependencies": { - "side-channel": "^1.0.4" - }, - "engines": { - "node": ">=0.6" - }, - "funding": { - "url": "https://github.com/sponsors/ljharb" - } - }, - "node_modules/query-string": { - "version": "6.14.1", - "resolved": "https://registry.npmjs.org/query-string/-/query-string-6.14.1.tgz", - "integrity": "sha512-XDxAeVmpfu1/6IjyT/gXHOl+S0vQ9owggJ30hhWKdHAsNPOcasn5o9BW0eejZqL2e4vMjhAxoW3jVHcD6mbcYw==", - "dev": true, - "dependencies": { - "decode-uri-component": "^0.2.0", - "filter-obj": "^1.1.0", - "split-on-first": "^1.0.0", - "strict-uri-encode": "^2.0.0" - }, - "engines": { - "node": ">=6" - }, - "funding": { - "url": "https://github.com/sponsors/sindresorhus" - } - }, - "node_modules/querystring": { - "version": "0.2.0", - "resolved": "https://registry.npmjs.org/querystring/-/querystring-0.2.0.tgz", - "integrity": "sha1-sgmEkgO7Jd+CDadW50cAWHhSFiA=", - "deprecated": "The querystring API is considered Legacy. new code should use the URLSearchParams API instead.", - "engines": { - "node": ">=0.4.x" - } - }, - "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/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/random-bytes": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/random-bytes/-/random-bytes-1.0.0.tgz", - "integrity": "sha1-T2ih3Arli9P7lYSMMDJNt11kNgs=", - "engines": { - "node": ">= 0.8" - } - }, - "node_modules/randomatic": { - "version": "3.1.1", - "resolved": "https://registry.npmjs.org/randomatic/-/randomatic-3.1.1.tgz", - "integrity": "sha512-TuDE5KxZ0J461RVjrJZCJc+J+zCkTb1MbH9AQUq68sMhOMcy9jLcb3BrZKgp9q9Ncltdg4QVqWrH02W2EFFVYw==", - "dependencies": { - "is-number": "^4.0.0", - "kind-of": "^6.0.0", - "math-random": "^1.0.1" - }, - "engines": { - "node": ">= 0.10.0" - } - }, - "node_modules/randomatic/node_modules/is-number": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/is-number/-/is-number-4.0.0.tgz", - "integrity": "sha512-rSklcAIlf1OmFdyAqbnWTLVelsQ58uvZ66S/ZyawjWqIviTWCjg2PzVGw8WUA+nNuPTqb4wgA+NszrJ+08LlgQ==", - "engines": { - "node": ">=0.10.0" - } - }, - "node_modules/randombytes": { - "version": "2.1.0", - "resolved": "https://registry.npmjs.org/randombytes/-/randombytes-2.1.0.tgz", - "integrity": "sha512-vYl3iOX+4CKUWuxGi9Ukhie6fsqXqS9FE2Zaic4tNFD2N2QQaXOMFbuKK4QmDHC0JO6B1Zp41J0LpT0oR68amQ==", - "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/raptor-async": { - "version": "1.1.3", - "resolved": "https://registry.npmjs.org/raptor-async/-/raptor-async-1.1.3.tgz", - "integrity": "sha1-uDw8m2A9yYXCw6n3jStAc+b2Akw=" - }, - "node_modules/raptor-cache": { - "version": "1.2.3", - "resolved": "https://registry.npmjs.org/raptor-cache/-/raptor-cache-1.2.3.tgz", - "integrity": "sha1-woEmegoff6bRpURzEfZ06uYbTDM=", - "dependencies": { - "dissolve": "^0.3.3", - "mkdirp": "^0.5.0", - "property-handlers": "^1.0.0", - "raptor-async": "^1.0.0", - "raptor-logging": "^1.0.1", - "raptor-util": "^1.0.0", - "through": "^2.3.4", - "uuid": "^3.0.0" - } - }, - "node_modules/raptor-cache/node_modules/mkdirp": { - "version": "0.5.5", - "resolved": "https://registry.npmjs.org/mkdirp/-/mkdirp-0.5.5.tgz", - "integrity": "sha512-NKmAlESf6jMGym1++R0Ra7wvhV+wFW63FaSOFPwRahvea0gMUcGUhVeAg/0BC0wiv9ih5NYPB1Wn1UEI1/L+xQ==", - "dependencies": { - "minimist": "^1.2.5" - }, - "bin": { - "mkdirp": "bin/cmd.js" - } - }, - "node_modules/raptor-cache/node_modules/raptor-util": { - "version": "1.1.2", - "resolved": "https://registry.npmjs.org/raptor-util/-/raptor-util-1.1.2.tgz", - "integrity": "sha1-8u6AdqmuPq4uZWcuRqIgB0+i3/M=" - }, - "node_modules/raptor-cache/node_modules/uuid": { - "version": "3.4.0", - "resolved": "https://registry.npmjs.org/uuid/-/uuid-3.4.0.tgz", - "integrity": "sha512-HjSDRw6gZE5JMggctHBcjVak08+KEVhSIiDzFnT9S9aegmp85S/bReBVTb4QTFaRNptJ9kuYaNhnbNEOkbKb/A==", - "deprecated": "Please upgrade to version 7 or higher. Older versions may use Math.random() in certain circumstances, which is known to be problematic. See https://v8.dev/blog/math-random for details.", - "bin": { - "uuid": "bin/uuid" - } - }, - "node_modules/raptor-css-parser": { - "version": "1.1.5", - "resolved": "https://registry.npmjs.org/raptor-css-parser/-/raptor-css-parser-1.1.5.tgz", - "integrity": "sha1-HeAY2WEhyNwfHDRoZUmv9xZJ0Dc=", - "dependencies": { - "raptor-async": "^1.0.0", - "raptor-promises": "^1.0.1" - } - }, - "node_modules/raptor-detect": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/raptor-detect/-/raptor-detect-1.0.1.tgz", - "integrity": "sha1-ClTGOQVu9m39Ur45RfoizG0UZvM=" - }, - "node_modules/raptor-logging": { - "version": "1.1.3", - "resolved": "https://registry.npmjs.org/raptor-logging/-/raptor-logging-1.1.3.tgz", - "integrity": "sha512-eklLyQmG5Y2oyIrSsvkFjBkjRYvwjemUQpQhjG757KKaNPxIPX9wu34bfQkIcS7OG495CP28CjX9baABLfOzIw==", - "dependencies": { - "raptor-polyfill": "^1.0.0", - "raptor-stacktraces": "^1.0.0" - } - }, - "node_modules/raptor-objects": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/raptor-objects/-/raptor-objects-1.0.2.tgz", - "integrity": "sha1-mQ3ONgQTsHni5K8RTy5zRKcc7hE=", - "dependencies": { - "raptor-util": "^1.0.0" - } - }, - "node_modules/raptor-objects/node_modules/raptor-util": { - "version": "1.1.2", - "resolved": "https://registry.npmjs.org/raptor-util/-/raptor-util-1.1.2.tgz", - "integrity": "sha1-8u6AdqmuPq4uZWcuRqIgB0+i3/M=" - }, - "node_modules/raptor-polyfill": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/raptor-polyfill/-/raptor-polyfill-1.1.0.tgz", - "integrity": "sha512-VhFc5e6EuNGdax7FQ2QWlCdXFi5OBBsclDh0kzZtgBI7lauc8aFs7+htdi5Q3qCRoYXfsucSBsRKf7a3s+YGmA==" - }, - "node_modules/raptor-promises": { - "version": "1.0.3", - "resolved": "https://registry.npmjs.org/raptor-promises/-/raptor-promises-1.0.3.tgz", - "integrity": "sha1-1XaxEOBCNlT3/fFyHijULk3DwOs=", - "dependencies": { - "q": "^1.0.1", - "raptor-util": "^1.0.0" - } - }, - "node_modules/raptor-promises/node_modules/raptor-util": { - "version": "1.1.2", - "resolved": "https://registry.npmjs.org/raptor-util/-/raptor-util-1.1.2.tgz", - "integrity": "sha1-8u6AdqmuPq4uZWcuRqIgB0+i3/M=" - }, - "node_modules/raptor-regexp": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/raptor-regexp/-/raptor-regexp-1.0.1.tgz", - "integrity": "sha1-7PD2bGZxwM2fXkjDcFAmxVCZlcA=" - }, - "node_modules/raptor-stacktraces": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/raptor-stacktraces/-/raptor-stacktraces-1.0.1.tgz", - "integrity": "sha1-f5+ycafdza4pHGprFd3v+8wAinY=" - }, - "node_modules/raptor-strings": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/raptor-strings/-/raptor-strings-1.0.2.tgz", - "integrity": "sha1-ks4ssBU6/pBHDYA5oCVbTPM6tfw=", - "dependencies": { - "raptor-polyfill": "^1.0.1" - } - }, - "node_modules/raptor-util": { - "version": "3.2.0", - "resolved": "https://registry.npmjs.org/raptor-util/-/raptor-util-3.2.0.tgz", - "integrity": "sha1-I7DIA8jxrIocrmfZpjiLSRYcl1g=" - }, - "node_modules/raw-body": { - "version": "2.4.2", - "resolved": "https://registry.npmjs.org/raw-body/-/raw-body-2.4.2.tgz", - "integrity": "sha512-RPMAFUJP19WIet/99ngh6Iv8fzAbqum4Li7AD6DtGaW2RpMB/11xDoalPiJMTbu6I3hkbMVkATvZrqb9EEqeeQ==", - "dependencies": { - "bytes": "3.1.1", - "http-errors": "1.8.1", - "iconv-lite": "0.4.24", - "unpipe": "1.0.0" - }, - "engines": { - "node": ">= 0.8" - } - }, - "node_modules/rc": { - "version": "1.2.8", - "resolved": "https://registry.npmjs.org/rc/-/rc-1.2.8.tgz", - "integrity": "sha512-y3bGgqKj3QBdxLbLkomlohkvsA8gdAiUQlSBJnBhfn+BPxg4bc62d8TcBW15wavDfgexCgccckhcZvywyQYPOw==", - "dev": true, - "dependencies": { - "deep-extend": "^0.6.0", - "ini": "~1.3.0", - "minimist": "^1.2.0", - "strip-json-comments": "~2.0.1" - }, - "bin": { - "rc": "cli.js" - } - }, - "node_modules/rc-config-loader": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/rc-config-loader/-/rc-config-loader-4.0.0.tgz", - "integrity": "sha512-//LRTblJEcqbmmro1GCmZ39qZXD+JqzuD8Y5/IZU3Dhp3A1Yr0Xn68ks8MQ6qKfKvYCWDveUmRDKDA40c+sCXw==", - "dev": true, - "dependencies": { - "debug": "^4.1.1", - "js-yaml": "^4.0.0", - "json5": "^2.1.2", - "require-from-string": "^2.0.2" - } - }, - "node_modules/rc/node_modules/strip-json-comments": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/strip-json-comments/-/strip-json-comments-2.0.1.tgz", - "integrity": "sha1-PFMZQukIwml8DsNEhYwobHygpgo=", - "dev": true, - "engines": { - "node": ">=0.10.0" - } - }, - "node_modules/read": { - "version": "1.0.7", - "resolved": "https://registry.npmjs.org/read/-/read-1.0.7.tgz", - "integrity": "sha1-s9oZvQUkMal2cdRKQmNK33ELQMQ=", - "dev": true, - "dependencies": { - "mute-stream": "~0.0.4" - }, - "engines": { - "node": ">=0.8" - } - }, - "node_modules/read-cmd-shim": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/read-cmd-shim/-/read-cmd-shim-2.0.0.tgz", - "integrity": "sha512-HJpV9bQpkl6KwjxlJcBoqu9Ba0PQg8TqSNIOrulGt54a0uup0HtevreFHzYzkm0lpnleRdNBzXznKrgxglEHQw==", - "dev": true - }, - "node_modules/read-package-json": { - "version": "3.0.1", - "resolved": "https://registry.npmjs.org/read-package-json/-/read-package-json-3.0.1.tgz", - "integrity": "sha512-aLcPqxovhJTVJcsnROuuzQvv6oziQx4zd3JvG0vGCL5MjTONUc4uJ90zCBC6R7W7oUKBNoR/F8pkyfVwlbxqng==", - "dev": true, - "dependencies": { - "glob": "^7.1.1", - "json-parse-even-better-errors": "^2.3.0", - "normalize-package-data": "^3.0.0", - "npm-normalize-package-bin": "^1.0.0" - }, - "engines": { - "node": ">=10" - } - }, - "node_modules/read-package-json-fast": { - "version": "2.0.3", - "resolved": "https://registry.npmjs.org/read-package-json-fast/-/read-package-json-fast-2.0.3.tgz", - "integrity": "sha512-W/BKtbL+dUjTuRL2vziuYhp76s5HZ9qQhd/dKfWIZveD0O40453QNyZhC0e63lqZrAQ4jiOapVoeJ7JrszenQQ==", - "dev": true, - "dependencies": { - "json-parse-even-better-errors": "^2.3.0", - "npm-normalize-package-bin": "^1.0.1" - }, - "engines": { - "node": ">=10" - } - }, - "node_modules/read-package-tree": { - "version": "5.3.1", - "resolved": "https://registry.npmjs.org/read-package-tree/-/read-package-tree-5.3.1.tgz", - "integrity": "sha512-mLUDsD5JVtlZxjSlPPx1RETkNjjvQYuweKwNVt1Sn8kP5Jh44pvYuUHCp6xSVDZWbNxVxG5lyZJ921aJH61sTw==", - "dev": true, - "dependencies": { - "read-package-json": "^2.0.0", - "readdir-scoped-modules": "^1.0.0", - "util-promisify": "^2.1.0" - } - }, - "node_modules/read-package-tree/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-package-tree/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-package-tree/node_modules/read-package-json": { - "version": "2.1.2", - "resolved": "https://registry.npmjs.org/read-package-json/-/read-package-json-2.1.2.tgz", - "integrity": "sha512-D1KmuLQr6ZSJS0tW8hf3WGpRlwszJOXZ3E8Yd/DNRaM5d+1wVRZdHlpGBLAuovjr28LbWvjpWkBHMxpRGGjzNA==", - "dev": true, - "dependencies": { - "glob": "^7.1.1", - "json-parse-even-better-errors": "^2.3.0", - "normalize-package-data": "^2.0.0", - "npm-normalize-package-bin": "^1.0.0" - } - }, - "node_modules/read-package-tree/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": { - "version": "3.0.0", - "resolved": "https://registry.npmjs.org/read-pkg/-/read-pkg-3.0.0.tgz", - "integrity": "sha1-nLxoaXj+5l0WwA4rGcI3/Pbjg4k=", - "dev": true, - "dependencies": { - "load-json-file": "^4.0.0", - "normalize-package-data": "^2.3.2", - "path-type": "^3.0.0" - }, - "engines": { - "node": ">=4" - } - }, - "node_modules/read-pkg-up": { - "version": "3.0.0", - "resolved": "https://registry.npmjs.org/read-pkg-up/-/read-pkg-up-3.0.0.tgz", - "integrity": "sha1-PtSWaF26D4/hGNBpHcUfSh/5bwc=", - "dev": true, - "dependencies": { - "find-up": "^2.0.0", - "read-pkg": "^3.0.0" - }, - "engines": { - "node": ">=4" - } - }, - "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/load-json-file": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/load-json-file/-/load-json-file-4.0.0.tgz", - "integrity": "sha1-L19Fq5HjMhYjT9U62rZo607AmTs=", - "dev": true, - "dependencies": { - "graceful-fs": "^4.1.2", - "parse-json": "^4.0.0", - "pify": "^3.0.0", - "strip-bom": "^3.0.0" - }, - "engines": { - "node": ">=4" - } - }, - "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/parse-json": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/parse-json/-/parse-json-4.0.0.tgz", - "integrity": "sha1-vjX1Qlvh9/bHRxhPmKeIy5lHfuA=", - "dev": true, - "dependencies": { - "error-ex": "^1.3.1", - "json-parse-better-errors": "^1.0.1" - }, - "engines": { - "node": ">=4" - } - }, - "node_modules/read-pkg/node_modules/path-type": { - "version": "3.0.0", - "resolved": "https://registry.npmjs.org/path-type/-/path-type-3.0.0.tgz", - "integrity": "sha512-T2ZUsdZFHgA3u4e5PfPbjd7HDDpxPnQb5jN0SrDsjNSuVXHJqtwTnWqG0B1jZrgmJ/7lj1EmVIByWt1gxGkWvg==", - "dev": true, - "dependencies": { - "pify": "^3.0.0" - }, - "engines": { - "node": ">=4" - } - }, - "node_modules/read-pkg/node_modules/pify": { - "version": "3.0.0", - "resolved": "https://registry.npmjs.org/pify/-/pify-3.0.0.tgz", - "integrity": "sha1-5aSs0sEB/fPZpNB/DbxNtJ3SgXY=", - "dev": true, - "engines": { - "node": ">=4" - } - }, - "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/strip-bom": { - "version": "3.0.0", - "resolved": "https://registry.npmjs.org/strip-bom/-/strip-bom-3.0.0.tgz", - "integrity": "sha1-IzTBjpx1n3vdVv3vfprj1YjmjtM=", - "dev": true, - "engines": { - "node": ">=4" - } - }, - "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/readdir-scoped-modules": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/readdir-scoped-modules/-/readdir-scoped-modules-1.1.0.tgz", - "integrity": "sha512-asaikDeqAQg7JifRsZn1NJZXo9E+VwlyCfbkZhwyISinqk5zNS6266HS5kah6P0SaQKGF6SkNnZVHUzHFYxYDw==", - "dev": true, - "dependencies": { - "debuglog": "^1.0.1", - "dezalgo": "^1.0.0", - "graceful-fs": "^4.1.2", - "once": "^1.3.0" - } - }, - "node_modules/readdirp": { - "version": "3.6.0", - "resolved": "https://registry.npmjs.org/readdirp/-/readdirp-3.6.0.tgz", - "integrity": "sha512-hOS089on8RduqdbhvQ5Z37A0ESjsqz6qnRcffsMU3495FuTdqSm+7bhJ29JvIOsBDEEnan5DPu9t3To9VRlMzA==", - "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": "sha1-hSBLVNuoLVdC4oyWdW70OvUOM4Q=", - "dependencies": { - "resolve": "^1.1.6" - }, - "engines": { - "node": ">= 0.10" - } - }, - "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", - "integrity": "sha512-zrceR/XhGYU/d/opr2EKO7aRHUeiBI8qjtfHqADTwZd6Szfy16la6kqD0MIUs5z5hx6AaKa+PixpPrR289+I0A==" - }, - "node_modules/regenerate-unicode-properties": { - "version": "9.0.0", - "resolved": "https://registry.npmjs.org/regenerate-unicode-properties/-/regenerate-unicode-properties-9.0.0.tgz", - "integrity": "sha512-3E12UeNSPfjrgwjkR81m5J7Aw/T55Tu7nUyZVQYCKEOs+2dkxEY+DpPtZzO4YruuiPb7NkYLVcyJC4+zCbk5pA==", - "dependencies": { - "regenerate": "^1.4.2" - }, - "engines": { - "node": ">=4" - } - }, - "node_modules/regenerator-runtime": { - "version": "0.10.5", - "resolved": "https://registry.npmjs.org/regenerator-runtime/-/regenerator-runtime-0.10.5.tgz", - "integrity": "sha1-M2w+/BIgrc7dosn6tntaeVWjNlg=" - }, - "node_modules/regenerator-transform": { - "version": "0.14.5", - "resolved": "https://registry.npmjs.org/regenerator-transform/-/regenerator-transform-0.14.5.tgz", - "integrity": "sha512-eOf6vka5IO151Jfsw2NO9WpGX58W6wWmefK3I1zEGr0lOD0u8rwPaNqQL1aRxUaxLeKO3ArNh3VYg1KbaD+FFw==", - "dependencies": { - "@babel/runtime": "^7.8.4" - } - }, - "node_modules/regex-cache": { - "version": "0.4.4", - "resolved": "https://registry.npmjs.org/regex-cache/-/regex-cache-0.4.4.tgz", - "integrity": "sha512-nVIZwtCjkC9YgvWkpM55B5rBhBYRZhAaJbgcFYXXsHnbZ9UZI9nnVWYZpBlCqv9ho2eZryPnWrZGsOdPwVWXWQ==", - "dependencies": { - "is-equal-shallow": "^0.1.3" - }, - "engines": { - "node": ">=0.10.0" - } - }, - "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": "4.8.0", - "resolved": "https://registry.npmjs.org/regexpu-core/-/regexpu-core-4.8.0.tgz", - "integrity": "sha512-1F6bYsoYiz6is+oz70NWur2Vlh9KWtswuRuzJOfeYUrfPX2o8n74AnUVaOGDbUqVGO9fNHu48/pjJO4sNVwsOg==", - "dependencies": { - "regenerate": "^1.4.2", - "regenerate-unicode-properties": "^9.0.0", - "regjsgen": "^0.5.2", - "regjsparser": "^0.7.0", - "unicode-match-property-ecmascript": "^2.0.0", - "unicode-match-property-value-ecmascript": "^2.0.0" - }, - "engines": { - "node": ">=4" - } - }, - "node_modules/registry-auth-token": { - "version": "4.2.1", - "resolved": "https://registry.npmjs.org/registry-auth-token/-/registry-auth-token-4.2.1.tgz", - "integrity": "sha512-6gkSb4U6aWJB4SF2ZvLb76yCBjcvufXBqvvEx1HbmKPkutswjW1xNVRY0+daljIYRbogN7O0etYSlbiaEQyMyw==", - "dev": true, - "dependencies": { - "rc": "^1.2.8" - }, - "engines": { - "node": ">=6.0.0" - } - }, - "node_modules/registry-url": { - "version": "5.1.0", - "resolved": "https://registry.npmjs.org/registry-url/-/registry-url-5.1.0.tgz", - "integrity": "sha512-8acYXXTI0AkQv6RAOjE3vOaIXZkT9wo4LOFbBKYQEEnnMNBpKqdUrI6S4NT0KPIo/WVvJ5tE/X5LF/TQUf0ekw==", - "dev": true, - "dependencies": { - "rc": "^1.2.8" - }, - "engines": { - "node": ">=8" - } - }, - "node_modules/regjsgen": { - "version": "0.5.2", - "resolved": "https://registry.npmjs.org/regjsgen/-/regjsgen-0.5.2.tgz", - "integrity": "sha512-OFFT3MfrH90xIW8OOSyUrk6QHD5E9JOTeGodiJeBS3J6IwlgzJMNE/1bZklWz5oTg+9dCMyEetclvCVXOPoN3A==" - }, - "node_modules/regjsparser": { - "version": "0.7.0", - "resolved": "https://registry.npmjs.org/regjsparser/-/regjsparser-0.7.0.tgz", - "integrity": "sha512-A4pcaORqmNMDVwUjWoTzuhwMGpP+NykpfqAsEgI1FSH/EzC7lrN5TMd+kN8YCovX+jMpu8eaqXgXPCa0g8FQNQ==", - "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": "sha1-597mbjXW/Bb3EP6R1c9p9w8IkR0=", - "bin": { - "jsesc": "bin/jsesc" - } - }, - "node_modules/release-zalgo": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/release-zalgo/-/release-zalgo-1.0.0.tgz", - "integrity": "sha1-CXALflB0Mpc5Mw5TXFqQ+2eFFzA=", - "dev": true, - "dependencies": { - "es6-error": "^4.0.1" - }, - "engines": { - "node": ">=4" - } - }, - "node_modules/remote-git-tags": { - "version": "3.0.0", - "resolved": "https://registry.npmjs.org/remote-git-tags/-/remote-git-tags-3.0.0.tgz", - "integrity": "sha512-C9hAO4eoEsX+OXA4rla66pXZQ+TLQ8T9dttgQj18yuKlPMTVkIkdYXvlMC55IuUsIkV6DpmQYi10JKFLaU+l7w==", - "dev": true, - "engines": { - "node": ">=8" - } - }, - "node_modules/remove-trailing-separator": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/remove-trailing-separator/-/remove-trailing-separator-1.1.0.tgz", - "integrity": "sha1-wkvOKig62tW8P1jg1IJJuSN52O8=" - }, - "node_modules/repeat-element": { - "version": "1.1.4", - "resolved": "https://registry.npmjs.org/repeat-element/-/repeat-element-1.1.4.tgz", - "integrity": "sha512-LFiNfRcSu7KK3evMyYOuCzv3L10TW7yC1G2/+StMjK8Y6Vqd2MG7r/Qjw4ghtuCOjFvlnms/iMmLqpvW/ES/WQ==", - "engines": { - "node": ">=0.10.0" - } - }, - "node_modules/repeat-string": { - "version": "1.6.1", - "resolved": "https://registry.npmjs.org/repeat-string/-/repeat-string-1.6.1.tgz", - "integrity": "sha1-jcrkcOHIirwtYA//Sndihtp15jc=", - "engines": { - "node": ">=0.10" - } - }, - "node_modules/repeating": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/repeating/-/repeating-2.0.1.tgz", - "integrity": "sha1-UhTFOpJtNVJwdSf7q0FdvAjQbdo=", - "dependencies": { - "is-finite": "^1.0.0" - }, - "engines": { - "node": ">=0.10.0" - } - }, - "node_modules/request": { - "version": "2.88.2", - "resolved": "https://registry.npmjs.org/request/-/request-2.88.2.tgz", - "integrity": "sha512-MsvtOrfG9ZcrOwAW+Qi+F6HbD0CWXEh9ou77uOb7FM2WPhwT7smM833PzanhJLsgXjN89Ir6V2PczXNnMpwKhw==", - "deprecated": "request has been deprecated, see https://github.com/request/request/issues/3142", - "dev": true, - "dependencies": { - "aws-sign2": "~0.7.0", - "aws4": "^1.8.0", - "caseless": "~0.12.0", - "combined-stream": "~1.0.6", - "extend": "~3.0.2", - "forever-agent": "~0.6.1", - "form-data": "~2.3.2", - "har-validator": "~5.1.3", - "http-signature": "~1.2.0", - "is-typedarray": "~1.0.0", - "isstream": "~0.1.2", - "json-stringify-safe": "~5.0.1", - "mime-types": "~2.1.19", - "oauth-sign": "~0.9.0", - "performance-now": "^2.1.0", - "qs": "~6.5.2", - "safe-buffer": "^5.1.2", - "tough-cookie": "~2.5.0", - "tunnel-agent": "^0.6.0", - "uuid": "^3.3.2" - }, - "engines": { - "node": ">= 6" - } - }, - "node_modules/request-compose": { - "version": "2.1.4", - "resolved": "https://registry.npmjs.org/request-compose/-/request-compose-2.1.4.tgz", - "integrity": "sha512-F8xik9Dxd5i2aHZ0/L/oIrCM1kKSgvp9BKYxGXk91lSWF9TbicWpnuxdOchxIhEWwvLdSBWZIAbCOeXfGfqaqA==", - "engines": { - "node": ">=12.0.0" - } - }, - "node_modules/request-oauth": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/request-oauth/-/request-oauth-1.0.1.tgz", - "integrity": "sha512-85THTg1RgOYtqQw42JON6AqvHLptlj1biw265Tsq4fD4cPdUvhDB2Qh9NTv17yCD322ROuO9aOmpc4GyayGVBA==", - "dependencies": { - "oauth-sign": "^0.9.0", - "qs": "^6.9.6", - "uuid": "^8.3.2" - }, - "engines": { - "node": ">=8.0.0" - } - }, - "node_modules/request/node_modules/qs": { - "version": "6.5.2", - "resolved": "https://registry.npmjs.org/qs/-/qs-6.5.2.tgz", - "integrity": "sha512-N5ZAX4/LxJmF+7wN74pUD6qAh9/wnvdQcjq9TZjevvXzSUo7bfmw91saqMjzGS2xq91/odN2dW/WOl7qQHNDGA==", - "dev": true, - "engines": { - "node": ">=0.6" - } - }, - "node_modules/request/node_modules/uuid": { - "version": "3.4.0", - "resolved": "https://registry.npmjs.org/uuid/-/uuid-3.4.0.tgz", - "integrity": "sha512-HjSDRw6gZE5JMggctHBcjVak08+KEVhSIiDzFnT9S9aegmp85S/bReBVTb4QTFaRNptJ9kuYaNhnbNEOkbKb/A==", - "deprecated": "Please upgrade to version 7 or higher. Older versions may use Math.random() in certain circumstances, which is known to be problematic. See https://v8.dev/blog/math-random for details.", - "dev": true, - "bin": { - "uuid": "bin/uuid" - } - }, - "node_modules/require-directory": { - "version": "2.1.1", - "resolved": "https://registry.npmjs.org/require-directory/-/require-directory-2.1.1.tgz", - "integrity": "sha1-jGStX9MNqxyXbiNE/+f3kqam30I=", - "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==", - "engines": { - "node": ">=0.10.0" - } - }, - "node_modules/require-main-filename": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/require-main-filename/-/require-main-filename-2.0.0.tgz", - "integrity": "sha512-NKN5kMDylKuldxYLSUfrbo5Tuzh4hd+2E8NPPX02mZtn1VuREQToYe/ZdlJy+J3uCpfaiGF05e7B8W0iXbQHmg==", - "dev": true - }, - "node_modules/resolve": { - "version": "1.21.0", - "resolved": "https://registry.npmjs.org/resolve/-/resolve-1.21.0.tgz", - "integrity": "sha512-3wCbTpk5WJlyE4mSOtDLhqQmGFi0/TD9VPwmiolnk8U0wRgMEktqCXd3vy5buTO3tljvalNvKrjHEfrd2WpEKA==", - "dependencies": { - "is-core-module": "^2.8.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==", - "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==", - "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==", - "engines": { - "node": ">=4" - } - }, - "node_modules/responselike": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/responselike/-/responselike-1.0.2.tgz", - "integrity": "sha1-kYcg7ztjHFZCvgaPFa3lpG9Loec=", - "dev": true, - "dependencies": { - "lowercase-keys": "^1.0.0" - } - }, - "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/retry": { - "version": "0.12.0", - "resolved": "https://registry.npmjs.org/retry/-/retry-0.12.0.tgz", - "integrity": "sha1-G0KmJmoh8HQh0bC1S33BZ7AcATs=", - "dev": true, - "engines": { - "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/right-align": { - "version": "0.1.3", - "resolved": "https://registry.npmjs.org/right-align/-/right-align-0.1.3.tgz", - "integrity": "sha1-YTObci/mo1FWiSENJOFMlhSGE+8=", - "dependencies": { - "align-text": "^0.1.1" - }, - "engines": { - "node": ">=0.10.0" - } - }, - "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/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/rusha": { - "version": "0.8.14", - "resolved": "https://registry.npmjs.org/rusha/-/rusha-0.8.14.tgz", - "integrity": "sha512-cLgakCUf6PedEu15t8kbsjnwIFFR2D4RfL+W3iWFJ4iac7z4B0ZI8fxy4R3J956kAI68HclCFGL8MPoUVC3qVA==" - }, - "node_modules/rxjs": { - "version": "7.5.1", - "resolved": "https://registry.npmjs.org/rxjs/-/rxjs-7.5.1.tgz", - "integrity": "sha512-KExVEeZWxMZnZhUZtsJcFwz8IvPvgu4G2Z2QyqjZQzUGr32KDYuSxrEYO4w3tFFNbfLozcrKUTvTPi+E9ywJkQ==", - "dependencies": { - "tslib": "^2.1.0" - } - }, - "node_modules/rxjs/node_modules/tslib": { - "version": "2.3.1", - "resolved": "https://registry.npmjs.org/tslib/-/tslib-2.3.1.tgz", - "integrity": "sha512-77EbyPPpMz+FRFRuAFlWMtmgUWGe9UOG2Z25NqCwiIjRhOf5iKGuzSe5P2w1laq+FkRy4p+PCuVkJSGkzTEKVw==" - }, - "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/safer-buffer": { - "version": "2.1.2", - "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, - "dependencies": { - "sparse-bitfield": "^3.0.3" - }, - "engines": { - "node": ">=6" - } - }, - "node_modules/schema-utils": { - "version": "2.7.1", - "resolved": "https://registry.npmjs.org/schema-utils/-/schema-utils-2.7.1.tgz", - "integrity": "sha512-SHiNtMOUGWBQJwzISiVYKu82GiV4QYGePp3odlY1tuKO7gPtphAT5R/py0fA6xtbgLL/RvtJZnU9b8s0F1q0Xg==", - "dependencies": { - "@types/json-schema": "^7.0.5", - "ajv": "^6.12.4", - "ajv-keywords": "^3.5.2" - }, - "engines": { - "node": ">= 8.9.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==", - "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==", - "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==" - }, - "node_modules/self-closing-tags": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/self-closing-tags/-/self-closing-tags-1.0.1.tgz", - "integrity": "sha512-7t6hNbYMxM+VHXTgJmxwgZgLGktuXtVVD5AivWzNTdJBM4DBjnDKDzkf2SrNjihaArpeJYNjxkELBu1evI4lQA==", - "engines": { - "node": ">=0.12.0" - } - }, - "node_modules/semver": { - "version": "7.3.5", - "resolved": "https://registry.npmjs.org/semver/-/semver-7.3.5.tgz", - "integrity": "sha512-PoeGJYh8HK4BTO/a9Tf6ZG3veo/A7ZVsYrSA6J8ny9nb3B1VrpkuN+z9OE5wfE5p6H4LchYZsegiQgbJD94ZFQ==", - "dependencies": { - "lru-cache": "^6.0.0" - }, - "bin": { - "semver": "bin/semver.js" - }, - "engines": { - "node": ">=10" - } - }, - "node_modules/semver-diff": { - "version": "3.1.1", - "resolved": "https://registry.npmjs.org/semver-diff/-/semver-diff-3.1.1.tgz", - "integrity": "sha512-GX0Ix/CJcHyB8c4ykpHGIAvLyOwOobtM/8d+TQkAd81/bEjgPHrfba41Vpesr7jX/t8Uh+R3EX9eAS5be+jQYg==", - "dev": true, - "dependencies": { - "semver": "^6.3.0" - }, - "engines": { - "node": ">=8" - } - }, - "node_modules/semver-diff/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/semver-utils": { - "version": "1.1.4", - "resolved": "https://registry.npmjs.org/semver-utils/-/semver-utils-1.1.4.tgz", - "integrity": "sha512-EjnoLE5OGmDAVV/8YDoN5KiajNadjzIp9BAHOhYeQHt7j0UWxjmgsx4YD48wp4Ue1Qogq38F1GNUJNqF1kKKxA==", - "dev": true - }, - "node_modules/send": { - "version": "0.17.2", - "resolved": "https://registry.npmjs.org/send/-/send-0.17.2.tgz", - "integrity": "sha512-UJYB6wFSJE3G00nEivR5rgWp8c2xXvJ3OPWPhmuteU0IKj8nKbG3DrjiOmLwpnHGYWAVwA69zmTm++YG0Hmwww==", - "dependencies": { - "debug": "2.6.9", - "depd": "~1.1.2", - "destroy": "~1.0.4", - "encodeurl": "~1.0.2", - "escape-html": "~1.0.3", - "etag": "~1.8.1", - "fresh": "0.5.2", - "http-errors": "1.8.1", - "mime": "1.6.0", - "ms": "2.1.3", - "on-finished": "~2.3.0", - "range-parser": "~1.2.1", - "statuses": "~1.5.0" - }, - "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": "sha1-VgiurfwAvmwpAd9fmGF4jeDVl8g=" - }, - "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.0", - "resolved": "https://registry.npmjs.org/serialize-javascript/-/serialize-javascript-6.0.0.tgz", - "integrity": "sha512-Qr3TosvguFt8ePWqsvRfrKyQXIiW+nGbYpy8XK24NQHE83caxWt+mIymTT19DGFbNWNLfEwsrkSmN64lVWB9ag==", - "dependencies": { - "randombytes": "^2.1.0" - } - }, - "node_modules/serve-static": { - "version": "1.14.2", - "resolved": "https://registry.npmjs.org/serve-static/-/serve-static-1.14.2.tgz", - "integrity": "sha512-+TMNA9AFxUEGuC0z2mevogSnn9MXKb4fa7ngeRMJaaGv8vTwnIEkKi+QGvPt33HSnf8pRS+WGM0EbMtCJLKMBQ==", - "dependencies": { - "encodeurl": "~1.0.2", - "escape-html": "~1.0.3", - "parseurl": "~1.3.3", - "send": "0.17.2" - }, - "engines": { - "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": "sha1-BF+XgtARrppoA93TgrJDkrPYkPc=", - "dev": true - }, - "node_modules/setprototypeof": { - "version": "1.2.0", - "resolved": "https://registry.npmjs.org/setprototypeof/-/setprototypeof-1.2.0.tgz", - "integrity": "sha512-E5LDX7Wrp85Kil5bhZv46j8jOeboKq5JMmYM3gVGdGH8xFpPWXUMsNrlODCrkoxMEeNi/XZIwuRvY4XNwYMJpw==" - }, - "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==", - "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==", - "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==", - "engines": { - "node": ">=8" - } - }, - "node_modules/shelljs": { - "version": "0.8.4", - "resolved": "https://registry.npmjs.org/shelljs/-/shelljs-0.8.4.tgz", - "integrity": "sha512-7gk3UZ9kOfPLIAbslLzyWeGiEqx9e3rxwZM0KE6EL8GlGwjym9Mrlx5/p33bWTu9YG6vcS4MBxYZDHYr5lr8BQ==", - "dependencies": { - "glob": "^7.0.0", - "interpret": "^1.0.0", - "rechoir": "^0.6.2" - }, - "bin": { - "shjs": "bin/shjs" - }, - "engines": { - "node": ">=4" - } - }, - "node_modules/shx": { - "version": "0.3.3", - "resolved": "https://registry.npmjs.org/shx/-/shx-0.3.3.tgz", - "integrity": "sha512-nZJ3HFWVoTSyyB+evEKjJ1STiixGztlqwKLTUNV5KqMWtGey9fTd4KU1gdZ1X9BV6215pswQ/Jew9NsuS/fNDA==", - "dependencies": { - "minimist": "^1.2.3", - "shelljs": "^0.8.4" - }, - "bin": { - "shx": "lib/cli.js" - }, - "engines": { - "node": ">=6" - } - }, - "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/sift": { - "version": "15.1.3", - "resolved": "https://registry.npmjs.org/sift/-/sift-15.1.3.tgz", - "integrity": "sha512-/JZRQtE1pe4t93jKvAKDCgpOSfFX/tFNoYn5hUB4nuVyihGFp5pS5mQu6p7XOo0oQvj+jrgVyIteAI6lO+EE8A==" - }, - "node_modules/signal-exit": { - "version": "3.0.6", - "resolved": "https://registry.npmjs.org/signal-exit/-/signal-exit-3.0.6.tgz", - "integrity": "sha512-sDl4qMFpijcGw22U5w63KmD3cZJfBuFlVNbVMKje2keoKML7X2UzWbc4XrmEbDwg0NXJc3yv4/ox7b+JWb57kQ==" - }, - "node_modules/simple-sha1": { - "version": "2.1.2", - "resolved": "https://registry.npmjs.org/simple-sha1/-/simple-sha1-2.1.2.tgz", - "integrity": "sha512-TQl9rm4rdKAVmhO++sXAb8TNN0D6JAD5iyI1mqEPNpxUzTRrtm4aOG1pDf/5W/qCFihiaoK6uuL9rvQz1x1VKw==", - "dependencies": { - "rusha": "^0.8.1" - } - }, - "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/slide": { - "version": "1.1.6", - "resolved": "https://registry.npmjs.org/slide/-/slide-1.1.6.tgz", - "integrity": "sha1-VusCfWW00tzmyy4tMsTUr8nh1wc=", - "dev": true, - "engines": { - "node": "*" - } - }, - "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==", - "dev": true, - "engines": { - "node": ">= 6.0.0", - "npm": ">= 3.0.0" - } - }, - "node_modules/socket.io": { - "version": "4.4.0", - "resolved": "https://registry.npmjs.org/socket.io/-/socket.io-4.4.0.tgz", - "integrity": "sha512-bnpJxswR9ov0Bw6ilhCvO38/1WPtE3eA2dtxi2Iq4/sFebiDJQzgKNYA7AuVVdGW09nrESXd90NbZqtDd9dzRQ==", - "dependencies": { - "accepts": "~1.3.4", - "base64id": "~2.0.0", - "debug": "~4.3.2", - "engine.io": "~6.1.0", - "socket.io-adapter": "~2.3.3", - "socket.io-parser": "~4.0.4" - }, - "engines": { - "node": ">=10.0.0" - } - }, - "node_modules/socket.io-adapter": { - "version": "2.3.3", - "resolved": "https://registry.npmjs.org/socket.io-adapter/-/socket.io-adapter-2.3.3.tgz", - "integrity": "sha512-Qd/iwn3VskrpNO60BeRyCyr8ZWw9CPZyitW4AQwmRZ8zCiyDiL+znRnWX6tDHXnWn1sJrM1+b6Mn6wEDJJ4aYQ==" - }, - "node_modules/socket.io-client": { - "version": "4.4.0", - "resolved": "https://registry.npmjs.org/socket.io-client/-/socket.io-client-4.4.0.tgz", - "integrity": "sha512-g7riSEJXi7qCFImPow98oT8X++MSsHz6MMFRXkWNJ6uEROSHOa3kxdrsYWMq85dO+09CFMkcqlpjvbVXQl4z6g==", - "dependencies": { - "@socket.io/component-emitter": "~3.0.0", - "backo2": "~1.0.2", - "debug": "~4.3.2", - "engine.io-client": "~6.1.1", - "parseuri": "0.0.6", - "socket.io-parser": "~4.1.1" - }, - "engines": { - "node": ">=10.0.0" - } - }, - "node_modules/socket.io-client/node_modules/socket.io-parser": { - "version": "4.1.1", - "resolved": "https://registry.npmjs.org/socket.io-parser/-/socket.io-parser-4.1.1.tgz", - "integrity": "sha512-USQVLSkDWE5nbcY760ExdKaJxCE65kcsG/8k5FDGZVVxpD1pA7hABYXYkCUvxUuYYh/+uQw0N/fvBzfT8o07KA==", - "dependencies": { - "@socket.io/component-emitter": "~3.0.0", - "debug": "~4.3.1" - }, - "engines": { - "node": ">=10.0.0" - } - }, - "node_modules/socket.io-parser": { - "version": "4.0.4", - "resolved": "https://registry.npmjs.org/socket.io-parser/-/socket.io-parser-4.0.4.tgz", - "integrity": "sha512-t+b0SS+IxG7Rxzda2EVvyBZbvFPBCjJoyHuE0P//7OAsN23GItzDRdWa6ALxZI/8R5ygK7jAR6t028/z+7295g==", - "dependencies": { - "@types/component-emitter": "^1.2.10", - "component-emitter": "~1.3.0", - "debug": "~4.3.1" - }, - "engines": { - "node": ">=10.0.0" - } - }, - "node_modules/socks": { - "version": "2.6.1", - "resolved": "https://registry.npmjs.org/socks/-/socks-2.6.1.tgz", - "integrity": "sha512-kLQ9N5ucj8uIcxrDwjm0Jsqk06xdpBjGNQtpXy4Q8/QY2k+fY7nZH8CARy+hkbG+SGAovmzzuauCpBlb8FrnBA==", - "dev": true, - "dependencies": { - "ip": "^1.1.5", - "smart-buffer": "^4.1.0" - }, - "engines": { - "node": ">= 10.13.0", - "npm": ">= 3.0.0" - } - }, - "node_modules/socks-proxy-agent": { - "version": "5.0.1", - "resolved": "https://registry.npmjs.org/socks-proxy-agent/-/socks-proxy-agent-5.0.1.tgz", - "integrity": "sha512-vZdmnjb9a2Tz6WEQVIurybSwElwPxMZaIc7PzqbJTrezcKNznv6giT7J7tZDZ1BojVaa1jvO/UiUdhDVB0ACoQ==", - "dev": true, - "dependencies": { - "agent-base": "^6.0.2", - "debug": "4", - "socks": "^2.3.3" - }, - "engines": { - "node": ">= 6" - } - }, - "node_modules/sort-keys": { - "version": "4.2.0", - "resolved": "https://registry.npmjs.org/sort-keys/-/sort-keys-4.2.0.tgz", - "integrity": "sha512-aUYIEU/UviqPgc8mHR6IW1EGxkAXpeRETYcrzg8cLAvUPZcpAlleSXHV2mY7G12GphSH6Gzv+4MMVSSkbdteHg==", - "dev": true, - "dependencies": { - "is-plain-obj": "^2.0.0" - }, - "engines": { - "node": ">=8" - }, - "funding": { - "url": "https://github.com/sponsors/sindresorhus" - } - }, - "node_modules/sort-keys/node_modules/is-plain-obj": { - "version": "2.1.0", - "resolved": "https://registry.npmjs.org/is-plain-obj/-/is-plain-obj-2.1.0.tgz", - "integrity": "sha512-YWnfyRwxL/+SsrWYfOpUtz5b3YD+nyfkHvjbcanzk8zgyO4ASD67uVMRt8k5bM4lLMDnXfriRhOpemw+NfT1eA==", - "dev": true, - "engines": { - "node": ">=8" - } - }, - "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==", - "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==", - "dependencies": { - "buffer-from": "^1.0.0", - "source-map": "^0.6.0" - } - }, - "node_modules/sparse-bitfield": { - "version": "3.0.3", - "resolved": "https://registry.npmjs.org/sparse-bitfield/-/sparse-bitfield-3.0.3.tgz", - "integrity": "sha1-/0rm5oZWBWuks+eSqzM004JzyhE=", - "optional": true, - "dependencies": { - "memory-pager": "^1.0.2" - } - }, - "node_modules/spawn-please": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/spawn-please/-/spawn-please-1.0.0.tgz", - "integrity": "sha512-Kz33ip6NRNKuyTRo3aDWyWxeGeM0ORDO552Fs6E1nj4pLWPkl37SrRtTnq+MEopVaqgmaO6bAvVS+v64BJ5M/A==", - "dev": true, - "engines": { - "node": ">=10" - } - }, - "node_modules/spawn-wrap": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/spawn-wrap/-/spawn-wrap-2.0.0.tgz", - "integrity": "sha512-EeajNjfN9zMnULLwhZZQU3GWBoFNkbngTUPfaawT4RkMiviTxcX0qfhVbGey39mfctfDHkWtuecgQ8NJcyQWHg==", - "dev": true, - "dependencies": { - "foreground-child": "^2.0.0", - "is-windows": "^1.0.2", - "make-dir": "^3.0.0", - "rimraf": "^3.0.0", - "signal-exit": "^3.0.2", - "which": "^2.0.1" - }, - "engines": { - "node": ">=8" - } - }, - "node_modules/spdx-correct": { - "version": "3.1.1", - "resolved": "https://registry.npmjs.org/spdx-correct/-/spdx-correct-3.1.1.tgz", - "integrity": "sha512-cOYcUWwhCuHCXi49RhFRCyJEK3iPj1Ziz9DpViV3tbZOwXD49QzIN3MpOLJNxh2qwq2lJJZaKMVw9qNi4jTC0w==", - "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==" - }, - "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==", - "dependencies": { - "spdx-exceptions": "^2.1.0", - "spdx-license-ids": "^3.0.0" - } - }, - "node_modules/spdx-license-ids": { - "version": "3.0.11", - "resolved": "https://registry.npmjs.org/spdx-license-ids/-/spdx-license-ids-3.0.11.tgz", - "integrity": "sha512-Ctl2BrFiM0X3MANYgj3CkygxhRmr9mi6xhejbdO960nF6EDJApTYpn0BQnDKlnNBULKiCN1n3w9EBkHK8ZWg+g==" - }, - "node_modules/split": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/split/-/split-1.0.1.tgz", - "integrity": "sha512-mTyOoPbrivtXnwnIxZRFYRrPNtEFKlpB2fvjSnCQUiAA6qAZzqwna5envK4uk6OIeP17CsdF3rSBGYVBsU0Tkg==", - "dev": true, - "dependencies": { - "through": "2" - }, - "engines": { - "node": "*" - } - }, - "node_modules/split-on-first": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/split-on-first/-/split-on-first-1.1.0.tgz", - "integrity": "sha512-43ZssAJaMusuKWL8sKUBQXHWOpq8d6CfN/u1p4gUzfJkM05C8rxTmYrkIPTXapZpORA6LkkzcUulJ8FqA7Uudw==", - "dev": true, - "engines": { - "node": ">=6" - } - }, - "node_modules/split2": { - "version": "3.2.2", - "resolved": "https://registry.npmjs.org/split2/-/split2-3.2.2.tgz", - "integrity": "sha512-9NThjpgZnifTkJpzTZ7Eue85S49QwpNhZTq6GRJwObb6jnLFNGB7Qm73V5HewTROPyxD0C29xqmaI68bQtV+hg==", - "dev": true, - "dependencies": { - "readable-stream": "^3.0.0" - } - }, - "node_modules/sprintf-js": { - "version": "1.0.3", - "resolved": "https://registry.npmjs.org/sprintf-js/-/sprintf-js-1.0.3.tgz", - "integrity": "sha1-BOaSb2YolTVPPdAVIDYzuFcpfiw=", - "dev": true - }, - "node_modules/sqwish": { - "version": "0.2.2", - "resolved": "https://registry.npmjs.org/sqwish/-/sqwish-0.2.2.tgz", - "integrity": "sha1-AP4maBBPEii1u37nOe9gEhu8sFc=", - "bin": { - "sqwish": "bin/sqwish" - }, - "engines": { - "node": ">= 0.4.1" - } - }, - "node_modules/sshpk": { - "version": "1.16.1", - "resolved": "https://registry.npmjs.org/sshpk/-/sshpk-1.16.1.tgz", - "integrity": "sha512-HXXqVUq7+pcKeLqqZj6mHFUMvXtOJt1uoUx09pFW6011inTMxqI8BA8PM95myrIyyKwdnzjdFjLiE6KBPVtJIg==", - "dev": true, - "dependencies": { - "asn1": "~0.2.3", - "assert-plus": "^1.0.0", - "bcrypt-pbkdf": "^1.0.0", - "dashdash": "^1.12.0", - "ecc-jsbn": "~0.1.1", - "getpass": "^0.1.1", - "jsbn": "~0.1.0", - "safer-buffer": "^2.0.2", - "tweetnacl": "~0.14.0" - }, - "bin": { - "sshpk-conv": "bin/sshpk-conv", - "sshpk-sign": "bin/sshpk-sign", - "sshpk-verify": "bin/sshpk-verify" - }, - "engines": { - "node": ">=0.10.0" - } - }, - "node_modules/ssri": { - "version": "8.0.1", - "resolved": "https://registry.npmjs.org/ssri/-/ssri-8.0.1.tgz", - "integrity": "sha512-97qShzy1AiyxvPNIkLWoGua7xoQzzPjQ0HAH4B0rWKo7SZ6USuPcrUiAFrws0UH8RrbWmgq3LMTObhPIHbbBeQ==", - "dev": true, - "dependencies": { - "minipass": "^3.1.1" - }, - "engines": { - "node": ">= 8" - } - }, - "node_modules/stackframe": { - "version": "1.2.0", - "resolved": "https://registry.npmjs.org/stackframe/-/stackframe-1.2.0.tgz", - "integrity": "sha512-GrdeshiRmS1YLMYgzF16olf2jJ/IzxXY9lhKOskuVziubpTYcYqyOwYeJKzQkwy7uN0fYSsbsC4RQaXf9LCrYA==" - }, - "node_modules/statuses": { - "version": "1.5.0", - "resolved": "https://registry.npmjs.org/statuses/-/statuses-1.5.0.tgz", - "integrity": "sha1-Fhx9rBd2Wf2YEfQ3cfqZOBR4Yow=", - "engines": { - "node": ">= 0.6" - } - }, - "node_modules/stream-browserify": { - "version": "2.0.2", - "resolved": "https://registry.npmjs.org/stream-browserify/-/stream-browserify-2.0.2.tgz", - "integrity": "sha512-nX6hmklHs/gr2FuxYDltq8fJA1GDlxKQCz8O/IM4atRqBH8OORmBNgfvW5gG10GT/qQ9u0CzIvr2X5Pkt6ntqg==", - "dependencies": { - "inherits": "~2.0.1", - "readable-stream": "^2.0.2" - } - }, - "node_modules/stream-browserify/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/stream-browserify/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/strict-uri-encode": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/strict-uri-encode/-/strict-uri-encode-2.0.0.tgz", - "integrity": "sha1-ucczDHBChi9rFC3CdLvMWGbONUY=", - "dev": true, - "engines": { - "node": ">=4" - } - }, - "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==", - "dependencies": { - "safe-buffer": "~5.2.0" - } - }, - "node_modules/string_decoder/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/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==", - "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.4", - "resolved": "https://registry.npmjs.org/string.prototype.trimend/-/string.prototype.trimend-1.0.4.tgz", - "integrity": "sha512-y9xCjw1P23Awk8EvTpcyL2NIr1j7wJ39f+k6lvRnSMz+mz9CGz9NYPelDk42kOz6+ql8xjfK8oYzy3jAP5QU5A==", - "dev": true, - "dependencies": { - "call-bind": "^1.0.2", - "define-properties": "^1.1.3" - }, - "funding": { - "url": "https://github.com/sponsors/ljharb" - } - }, - "node_modules/string.prototype.trimstart": { - "version": "1.0.4", - "resolved": "https://registry.npmjs.org/string.prototype.trimstart/-/string.prototype.trimstart-1.0.4.tgz", - "integrity": "sha512-jh6e984OBfvxS50tdY2nRZnoC5/mLFKOREQfw8t5yytkoUsJRNxvI/E39qu1sD0OtWI3OC0XgKSmcWwziwYuZw==", - "dev": true, - "dependencies": { - "call-bind": "^1.0.2", - "define-properties": "^1.1.3" - }, - "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==", - "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==", - "engines": { - "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", - "integrity": "sha512-6fPc+R4ihwqP6N/aIv2f1gMH8lOVtWQHoqC4yK6oSDVVocumAsfCqjkXnqiYMhmMwS/mEHLp7Vehlt3ql6lEig==", - "engines": { - "node": ">=8" - }, - "funding": { - "url": "https://github.com/sponsors/sindresorhus" - } - }, - "node_modules/strong-log-transformer": { - "version": "2.1.0", - "resolved": "https://registry.npmjs.org/strong-log-transformer/-/strong-log-transformer-2.1.0.tgz", - "integrity": "sha512-B3Hgul+z0L9a236FAUC9iZsL+nVHgoCJnqCbN588DjYxvGXaXaaFbfmQ/JhvKjZwsOukuR72XbHv71Qkug0HxA==", - "dev": true, - "dependencies": { - "duplexer": "^0.1.1", - "minimist": "^1.2.0", - "through": "^2.3.4" - }, - "bin": { - "sl-log-transformer": "bin/sl-log-transformer.js" - }, - "engines": { - "node": ">=4" - } - }, - "node_modules/superagent": { - "version": "6.1.0", - "resolved": "https://registry.npmjs.org/superagent/-/superagent-6.1.0.tgz", - "integrity": "sha512-OUDHEssirmplo3F+1HWKUrUjvnQuA+nZI6i/JJBdXb5eq9IyEQwPyPpqND+SSsxf6TygpBEkUjISVRN4/VOpeg==", - "dependencies": { - "component-emitter": "^1.3.0", - "cookiejar": "^2.1.2", - "debug": "^4.1.1", - "fast-safe-stringify": "^2.0.7", - "form-data": "^3.0.0", - "formidable": "^1.2.2", - "methods": "^1.1.2", - "mime": "^2.4.6", - "qs": "^6.9.4", - "readable-stream": "^3.6.0", - "semver": "^7.3.2" - }, - "engines": { - "node": ">= 7.0.0" - } - }, - "node_modules/superagent/node_modules/form-data": { - "version": "3.0.1", - "resolved": "https://registry.npmjs.org/form-data/-/form-data-3.0.1.tgz", - "integrity": "sha512-RHkBKtLWUVwd7SqRIvCZMEvAMoGUp0XU+seQiZejj0COz3RI3hWP4sCv3gZWWLjJTd7rGwcsF5eKZGii0r/hbg==", - "dependencies": { - "asynckit": "^0.4.0", - "combined-stream": "^1.0.8", - "mime-types": "^2.1.12" - }, - "engines": { - "node": ">= 6" - } - }, - "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==", - "bin": { - "mime": "cli.js" - }, - "engines": { - "node": ">=4.0.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==", - "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==", - "engines": { - "node": ">=6" - } - }, - "node_modules/tar": { - "version": "6.1.11", - "resolved": "https://registry.npmjs.org/tar/-/tar-6.1.11.tgz", - "integrity": "sha512-an/KZQzQUkZCkuoAA64hM92X0Urb6VpRhAFllDzz44U2mcD5scmT3zBc4VgVpkugF580+DQn8eAFSyoQt0tznA==", - "dev": true, - "dependencies": { - "chownr": "^2.0.0", - "fs-minipass": "^2.0.0", - "minipass": "^3.0.0", - "minizlib": "^2.1.1", - "mkdirp": "^1.0.3", - "yallist": "^4.0.0" - }, - "engines": { - "node": ">= 10" - } - }, - "node_modules/temp-dir": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/temp-dir/-/temp-dir-1.0.0.tgz", - "integrity": "sha1-CnwOom06Oa+n4OvqnB/AvE2qAR0=", - "dev": true, - "engines": { - "node": ">=4" - } - }, - "node_modules/temp-write": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/temp-write/-/temp-write-4.0.0.tgz", - "integrity": "sha512-HIeWmj77uOOHb0QX7siN3OtwV3CTntquin6TNVg6SHOqCP3hYKmox90eeFOGaY1MqJ9WYDDjkyZrW6qS5AWpbw==", - "dev": true, - "dependencies": { - "graceful-fs": "^4.1.15", - "is-stream": "^2.0.0", - "make-dir": "^3.0.0", - "temp-dir": "^1.0.0", - "uuid": "^3.3.2" - }, - "engines": { - "node": ">=8" - } - }, - "node_modules/temp-write/node_modules/uuid": { - "version": "3.4.0", - "resolved": "https://registry.npmjs.org/uuid/-/uuid-3.4.0.tgz", - "integrity": "sha512-HjSDRw6gZE5JMggctHBcjVak08+KEVhSIiDzFnT9S9aegmp85S/bReBVTb4QTFaRNptJ9kuYaNhnbNEOkbKb/A==", - "deprecated": "Please upgrade to version 7 or higher. Older versions may use Math.random() in certain circumstances, which is known to be problematic. See https://v8.dev/blog/math-random for details.", - "dev": true, - "bin": { - "uuid": "bin/uuid" - } - }, - "node_modules/terser": { - "version": "5.10.0", - "resolved": "https://registry.npmjs.org/terser/-/terser-5.10.0.tgz", - "integrity": "sha512-AMmF99DMfEDiRJfxfY5jj5wNH/bYO09cniSqhfoyxc8sFoYIgkJy86G04UoZU5VjlpnplVu0K6Tx6E9b5+DlHA==", - "dependencies": { - "commander": "^2.20.0", - "source-map": "~0.7.2", - "source-map-support": "~0.5.20" - }, - "bin": { - "terser": "bin/terser" - }, - "engines": { - "node": ">=10" - }, - "peerDependencies": { - "acorn": "^8.5.0" - }, - "peerDependenciesMeta": { - "acorn": { - "optional": true - } - } - }, - "node_modules/terser-webpack-plugin": { - "version": "5.3.0", - "resolved": "https://registry.npmjs.org/terser-webpack-plugin/-/terser-webpack-plugin-5.3.0.tgz", - "integrity": "sha512-LPIisi3Ol4chwAaPP8toUJ3L4qCM1G0wao7L3qNv57Drezxj6+VEyySpPw4B1HSO2Eg/hDY/MNF5XihCAoqnsQ==", - "dependencies": { - "jest-worker": "^27.4.1", - "schema-utils": "^3.1.1", - "serialize-javascript": "^6.0.0", - "source-map": "^0.6.1", - "terser": "^5.7.2" - }, - "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==", - "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==", - "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==" - }, - "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==", - "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==" - }, - "node_modules/terser/node_modules/source-map": { - "version": "0.7.3", - "resolved": "https://registry.npmjs.org/source-map/-/source-map-0.7.3.tgz", - "integrity": "sha512-CkCj6giN3S+n9qrYiBTX5gystlENnRW5jZeNLHpe6aue+SrHcG5VYwujhW9s4dY31mEGsxBDrHR6oI69fTXsaQ==", - "engines": { - "node": ">= 8" - } - }, - "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-extensions": { - "version": "1.9.0", - "resolved": "https://registry.npmjs.org/text-extensions/-/text-extensions-1.9.0.tgz", - "integrity": "sha512-wiBrwC1EhBelW12Zy26JeOUkQ5mRu+5o8rpsJk5+2t+Y5vE7e842qtZDQ2g1NpX/29HdyFeJ4nSIhI47ENSxlQ==", - "dev": true, - "engines": { - "node": ">=0.10" - } - }, - "node_modules/text-table": { - "version": "0.2.0", - "resolved": "https://registry.npmjs.org/text-table/-/text-table-0.2.0.tgz", - "integrity": "sha1-f17oI66AUgfACvLfSoTsP8+lcLQ=", - "dev": true - }, - "node_modules/through": { - "version": "2.3.8", - "resolved": "https://registry.npmjs.org/through/-/through-2.3.8.tgz", - "integrity": "sha1-DdTJ/6q8NXlgsbckEV1+Doai4fU=" - }, - "node_modules/through2": { - "version": "4.0.2", - "resolved": "https://registry.npmjs.org/through2/-/through2-4.0.2.tgz", - "integrity": "sha512-iOqSav00cVxEEICeD7TjLB1sueEL+81Wpzp2bY17uZjZN0pWZPuo4suZ/61VujxmqSGFfgOcNuTZ85QJwNZQpw==", - "dev": true, - "dependencies": { - "readable-stream": "3" - } - }, - "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/to-fast-properties": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/to-fast-properties/-/to-fast-properties-2.0.0.tgz", - "integrity": "sha1-3F5pjL0HkmW8c+A3doGk5Og/YW4=", - "engines": { - "node": ">=4" - } - }, - "node_modules/to-readable-stream": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/to-readable-stream/-/to-readable-stream-1.0.0.tgz", - "integrity": "sha512-Iq25XBt6zD5npPhlLVXGFN3/gyR2/qODcKNNyTMd4vbm39HUaOiAM4PMq0eMVC/Tkxz+Zjdsc55g9yyz+Yq00Q==", - "dev": true, - "engines": { - "node": ">=6" - } - }, - "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==", - "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/tough-cookie": { - "version": "2.5.0", - "resolved": "https://registry.npmjs.org/tough-cookie/-/tough-cookie-2.5.0.tgz", - "integrity": "sha512-nlLsUzgm1kfLXSXfRZMc1KLAugd4hqJHDTvc2hDIwS3mZAfMEuMbc03SujMF+GEcpaX/qboeycw6iO8JwVv2+g==", - "dev": true, - "dependencies": { - "psl": "^1.1.28", - "punycode": "^2.1.1" - }, - "engines": { - "node": ">=0.8" - } - }, - "node_modules/tr46": { - "version": "2.1.0", - "resolved": "https://registry.npmjs.org/tr46/-/tr46-2.1.0.tgz", - "integrity": "sha512-15Ih7phfcdP5YxqiB+iDtLoaTz4Nd35+IiAv0kQ5FNKHzXgdWqPoTIqEDDJmXceQt4JZk6lVPT8lnDlPpGDppw==", - "dev": true, - "dependencies": { - "punycode": "^2.1.1" - }, - "engines": { - "node": ">=8" - } - }, - "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/trim-right": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/trim-right/-/trim-right-1.0.1.tgz", - "integrity": "sha1-yy4SAwZ+DI3h9hQJS5/kVwTqYAM=", - "engines": { - "node": ">=0.10.0" - } - }, - "node_modules/ts-loader": { - "version": "9.2.6", - "resolved": "https://registry.npmjs.org/ts-loader/-/ts-loader-9.2.6.tgz", - "integrity": "sha512-QMTC4UFzHmu9wU2VHZEmWWE9cUajjfcdcws+Gh7FhiO+Dy0RnR1bNz0YCHqhI0yRowCE9arVnNxYHqELOy9Hjw==", - "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-node": { - "version": "10.4.0", - "resolved": "https://registry.npmjs.org/ts-node/-/ts-node-10.4.0.tgz", - "integrity": "sha512-g0FlPvvCXSIO1JDF6S232P5jPYqBkRL9qly81ZgAOSU7rwI0stphCgd2kLiCrU9DjQCrJMWEqcNSjQL02s6d8A==", - "dependencies": { - "@cspotcode/source-map-support": "0.7.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", - "yn": "3.1.1" - }, - "bin": { - "ts-node": "dist/bin.js", - "ts-node-cwd": "dist/bin-cwd.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/ts-node/node_modules/diff": { - "version": "4.0.2", - "resolved": "https://registry.npmjs.org/diff/-/diff-4.0.2.tgz", - "integrity": "sha512-58lmxKSA4BNyLz+HHMUzlOEpg09FV+ev6ZMe3vJihgdxzgcwZ8VoEEPmALCZG9LmqfVoNMMKpttIYTVG6uDY7A==", - "engines": { - "node": ">=0.3.1" - } - }, - "node_modules/ts-toolbelt": { - "version": "6.15.5", - "resolved": "https://registry.npmjs.org/ts-toolbelt/-/ts-toolbelt-6.15.5.tgz", - "integrity": "sha512-FZIXf1ksVyLcfr7M317jbB67XFJhOO1YqdTcuGaq9q5jLUoTikukZ+98TPjKiP2jC5CgmYdWWYs0s2nLSU0/1A==" - }, - "node_modules/tsconfig-paths": { - "version": "3.12.0", - "resolved": "https://registry.npmjs.org/tsconfig-paths/-/tsconfig-paths-3.12.0.tgz", - "integrity": "sha512-e5adrnOYT6zqVnWqZu7i/BQ3BnhzvGbjEjejFXO20lKIKpwTaupkCPgEfv4GZK1IBciJUEhYs3J3p75FdaTFVg==", - "dev": true, - "dependencies": { - "@types/json5": "^0.0.29", - "json5": "^1.0.1", - "minimist": "^1.2.0", - "strip-bom": "^3.0.0" - } - }, - "node_modules/tsconfig-paths/node_modules/json5": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/json5/-/json5-1.0.1.tgz", - "integrity": "sha512-aKS4WQjPenRxiQsC93MNfjx+nbF4PAdYzmd/1JIj8HYzqfbu86beTuNgXDzPknWk0n0uARlyewZo4s++ES36Ow==", - "dev": true, - "dependencies": { - "minimist": "^1.2.0" - }, - "bin": { - "json5": "lib/cli.js" - } - }, - "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": "sha1-IzTBjpx1n3vdVv3vfprj1YjmjtM=", - "dev": true, - "engines": { - "node": ">=4" - } - }, - "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/tsscmp": { - "version": "1.0.6", - "resolved": "https://registry.npmjs.org/tsscmp/-/tsscmp-1.0.6.tgz", - "integrity": "sha512-LxhtAkPDTkVCMQjt2h6eBVY28KCjikZqZfMcC15YBeNjkgUpdCfBu5HoiOTDu86v6smE8yOjyEktJ8hlbANHQA==", - "engines": { - "node": ">=0.6.x" - } - }, - "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/tunnel-agent": { - "version": "0.6.0", - "resolved": "https://registry.npmjs.org/tunnel-agent/-/tunnel-agent-0.6.0.tgz", - "integrity": "sha1-J6XeoGs2sEoKmWZ3SykIaPD8QP0=", - "dev": true, - "dependencies": { - "safe-buffer": "^5.0.1" - }, - "engines": { - "node": "*" - } - }, - "node_modules/tweetnacl": { - "version": "0.14.5", - "resolved": "https://registry.npmjs.org/tweetnacl/-/tweetnacl-0.14.5.tgz", - "integrity": "sha1-WuaBd/GS1EViadEIr6k/+HQ/T2Q=", - "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": "1.0.0", - "resolved": "https://registry.npmjs.org/type-detect/-/type-detect-1.0.0.tgz", - "integrity": "sha1-diIXzAbbJY7EiQihKY6LlRIejqI=", - "engines": { - "node": "*" - } - }, - "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/typedarray": { - "version": "0.0.6", - "resolved": "https://registry.npmjs.org/typedarray/-/typedarray-0.0.6.tgz", - "integrity": "sha1-hnrHTjhkGHsdPUfZlqeOxciDB3c=" - }, - "node_modules/typedarray-to-buffer": { - "version": "3.1.5", - "resolved": "https://registry.npmjs.org/typedarray-to-buffer/-/typedarray-to-buffer-3.1.5.tgz", - "integrity": "sha512-zdu8XMNEDepKKR+XYOXAVPtWui0ly0NtohUscw+UmaHiAWT8hrV1rr//H6V+0DvJ3OQ19S979M0laLfX8rm82Q==", - "dev": true, - "dependencies": { - "is-typedarray": "^1.0.0" - } - }, - "node_modules/typescript": { - "version": "4.5.4", - "resolved": "https://registry.npmjs.org/typescript/-/typescript-4.5.4.tgz", - "integrity": "sha512-VgYs2A2QIRuGphtzFV7aQJduJ2gyfTljngLzjpfW9FoYZF6xuw1W0vW9ghCKLfcWrCFxK81CSGRAvS1pn4fIUg==", - "bin": { - "tsc": "bin/tsc", - "tsserver": "bin/tsserver" - }, - "engines": { - "node": ">=4.2.0" - } - }, - "node_modules/uglify-js": { - "version": "3.14.5", - "resolved": "https://registry.npmjs.org/uglify-js/-/uglify-js-3.14.5.tgz", - "integrity": "sha512-qZukoSxOG0urUTvjc2ERMTcAy+BiFh3weWAkeurLwjrCba73poHmG3E36XEjd/JGukMzwTL7uCxZiAexj8ppvQ==", - "dev": true, - "optional": true, - "bin": { - "uglifyjs": "bin/uglifyjs" - }, - "engines": { - "node": ">=0.8.0" - } - }, - "node_modules/uglify-to-browserify": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/uglify-to-browserify/-/uglify-to-browserify-1.0.2.tgz", - "integrity": "sha1-bgkk1r2mta/jSeOabWMoUKD4grc=", - "optional": true - }, - "node_modules/uid-number": { - "version": "0.0.6", - "resolved": "https://registry.npmjs.org/uid-number/-/uid-number-0.0.6.tgz", - "integrity": "sha1-DqEOgDXo61uOREnwbaHHMGY7qoE=", - "dev": true, - "engines": { - "node": "*" - } - }, - "node_modules/uid-safe": { - "version": "2.1.5", - "resolved": "https://registry.npmjs.org/uid-safe/-/uid-safe-2.1.5.tgz", - "integrity": "sha512-KPHm4VL5dDXKz01UuEd88Df+KzynaohSL9fBh096KWAxSKZQDI2uBrVqtvRM4rwrIrRRKsdLNML/lnaaVSRioA==", - "dependencies": { - "random-bytes": "~1.0.0" - }, - "engines": { - "node": ">= 0.8" - } - }, - "node_modules/ultron": { - "version": "1.1.1", - "resolved": "https://registry.npmjs.org/ultron/-/ultron-1.1.1.tgz", - "integrity": "sha512-UIEXBNeYmKptWH6z8ZnqTeS8fV74zG0/eRU9VGkpzz+LIJNs8W/zM/L+7ctCkRrgbNnnR0xxw4bKOr0cW0N0Og==" - }, - "node_modules/umask": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/umask/-/umask-1.1.0.tgz", - "integrity": "sha1-8pzr8B31F5ErtY/5xOUP3o4zMg0=", - "dev": true - }, - "node_modules/unbox-primitive": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/unbox-primitive/-/unbox-primitive-1.0.1.tgz", - "integrity": "sha512-tZU/3NqK3dA5gpE1KtyiJUrEB0lxnGkMFHptJ7q6ewdZ8s12QrODwNbhIJStmJkd1QDXa1NRA8aF2A1zk/Ypyw==", - "dev": true, - "dependencies": { - "function-bind": "^1.1.1", - "has-bigints": "^1.0.1", - "has-symbols": "^1.0.2", - "which-boxed-primitive": "^1.0.2" - }, - "funding": { - "url": "https://github.com/sponsors/ljharb" - } - }, - "node_modules/unc-path-regex": { - "version": "0.1.2", - "resolved": "https://registry.npmjs.org/unc-path-regex/-/unc-path-regex-0.1.2.tgz", - "integrity": "sha1-5z3T17DXxe2G+6xrCufYxqadUPo=", - "engines": { - "node": ">=0.10.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==", - "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==", - "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.0.0", - "resolved": "https://registry.npmjs.org/unicode-match-property-value-ecmascript/-/unicode-match-property-value-ecmascript-2.0.0.tgz", - "integrity": "sha512-7Yhkc0Ye+t4PNYzOGKedDhXbYIBe1XEQYQxOPyhcXNMJ0WCABqqj6ckydd6pWRZTHV4GuCPKdBAUiMc60tsKVw==", - "engines": { - "node": ">=4" - } - }, - "node_modules/unicode-property-aliases-ecmascript": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/unicode-property-aliases-ecmascript/-/unicode-property-aliases-ecmascript-2.0.0.tgz", - "integrity": "sha512-5Zfuy9q/DFr4tfO7ZPeVXb1aPoeQSdeFMLpYuFebehDAhbuevLs5yxSZmIFN1tP5F9Wl4IpJrYojg85/zgyZHQ==", - "engines": { - "node": ">=4" - } - }, - "node_modules/unique-filename": { - "version": "1.1.1", - "resolved": "https://registry.npmjs.org/unique-filename/-/unique-filename-1.1.1.tgz", - "integrity": "sha512-Vmp0jIp2ln35UTXuryvjzkjGdRyf9b2lTXuSYUiPmzRcl3FDtYqAwOnTJkAngD9SWhnoJzDbTKwaOrZ+STtxNQ==", - "dev": true, - "dependencies": { - "unique-slug": "^2.0.0" - } - }, - "node_modules/unique-slug": { - "version": "2.0.2", - "resolved": "https://registry.npmjs.org/unique-slug/-/unique-slug-2.0.2.tgz", - "integrity": "sha512-zoWr9ObaxALD3DOPfjPSqxt4fnZiWblxHIgeWqW8x7UqDzEtHEQLzji2cuJYQFCU6KmoJikOYAZlrTHHebjx2w==", - "dev": true, - "dependencies": { - "imurmurhash": "^0.1.4" - } - }, - "node_modules/unique-string": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/unique-string/-/unique-string-2.0.0.tgz", - "integrity": "sha512-uNaeirEPvpZWSgzwsPGtU2zVSTrn/8L5q/IexZmH0eH6SA73CmAA5U4GwORTxQAZs95TAXLNqeLoPPNO5gZfWg==", - "dev": true, - "dependencies": { - "crypto-random-string": "^2.0.0" - }, - "engines": { - "node": ">=8" - } - }, - "node_modules/universal-user-agent": { - "version": "6.0.0", - "resolved": "https://registry.npmjs.org/universal-user-agent/-/universal-user-agent-6.0.0.tgz", - "integrity": "sha512-isyNax3wXoKaulPDZWHQqbmIx1k2tb9fb3GGDBRxCscfYV2Ch7WxPArBsFEG8s/safwXTT7H4QGhaIkTp9447w==", - "dev": true - }, - "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": "sha1-sr9O6FFKrmFltIF4KdIbLvSZBOw=", - "engines": { - "node": ">= 0.8" - } - }, - "node_modules/upath": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/upath/-/upath-2.0.1.tgz", - "integrity": "sha512-1uEe95xksV1O0CYKXo8vQvN1JEbtJp7lb7C5U9HMsIp6IVwntkH/oNUzyVNQSd4S1sYk2FpSSW44FqMc8qee5w==", - "dev": true, - "engines": { - "node": ">=4", - "yarn": "*" - } - }, - "node_modules/update-notifier": { - "version": "5.1.0", - "resolved": "https://registry.npmjs.org/update-notifier/-/update-notifier-5.1.0.tgz", - "integrity": "sha512-ItnICHbeMh9GqUy31hFPrD1kcuZ3rpxDZbf4KUDavXwS0bW5m7SLbDQpGX3UYr072cbrF5hFUs3r5tUsPwjfHw==", - "dev": true, - "dependencies": { - "boxen": "^5.0.0", - "chalk": "^4.1.0", - "configstore": "^5.0.1", - "has-yarn": "^2.1.0", - "import-lazy": "^2.1.0", - "is-ci": "^2.0.0", - "is-installed-globally": "^0.4.0", - "is-npm": "^5.0.0", - "is-yarn-global": "^0.3.0", - "latest-version": "^5.1.0", - "pupa": "^2.1.1", - "semver": "^7.3.4", - "semver-diff": "^3.1.1", - "xdg-basedir": "^4.0.0" - }, - "engines": { - "node": ">=10" - }, - "funding": { - "url": "https://github.com/yeoman/update-notifier?sponsor=1" - } - }, - "node_modules/uri-js": { - "version": "4.4.1", - "resolved": "https://registry.npmjs.org/uri-js/-/uri-js-4.4.1.tgz", - "integrity": "sha512-7rKUyy33Q1yc98pQ1DAmLtwX109F7TIfWlW1Ydo8Wl1ii1SeHieeh0HHfPeL2fMXK6z0s8ecKs9frCuLJvndBg==", - "dependencies": { - "punycode": "^2.1.0" - } - }, - "node_modules/url": { - "version": "0.11.0", - "resolved": "https://registry.npmjs.org/url/-/url-0.11.0.tgz", - "integrity": "sha1-ODjpfPxgUh63PFJajlW/3Z4uKPE=", - "dependencies": { - "punycode": "1.3.2", - "querystring": "0.2.0" - } - }, - "node_modules/url-parse-lax": { - "version": "3.0.0", - "resolved": "https://registry.npmjs.org/url-parse-lax/-/url-parse-lax-3.0.0.tgz", - "integrity": "sha1-FrXK/Afb42dsGxmZF3gj1lA6yww=", - "dev": true, - "dependencies": { - "prepend-http": "^2.0.0" - }, - "engines": { - "node": ">=4" - } - }, - "node_modules/url/node_modules/punycode": { - "version": "1.3.2", - "resolved": "https://registry.npmjs.org/punycode/-/punycode-1.3.2.tgz", - "integrity": "sha1-llOgNvt8HuQjQvIyXM7v6jkmxI0=" - }, - "node_modules/util": { - "version": "0.11.1", - "resolved": "https://registry.npmjs.org/util/-/util-0.11.1.tgz", - "integrity": "sha512-HShAsny+zS2TZfaXxD9tYj4HQGlBezXZMZuM/S5PKLLoZkShZiGk9o5CzukI1LVHZvjdvZ2Sj1aW/Ndn2NB/HQ==", - "dependencies": { - "inherits": "2.0.3" - } - }, - "node_modules/util-deprecate": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/util-deprecate/-/util-deprecate-1.0.2.tgz", - "integrity": "sha1-RQ1Nyfpw3nMnYvvS1KKJgUGaDM8=" - }, - "node_modules/util-promisify": { - "version": "2.1.0", - "resolved": "https://registry.npmjs.org/util-promisify/-/util-promisify-2.1.0.tgz", - "integrity": "sha1-PCI2R2xNMsX/PEcAKt18E7moKlM=", - "dev": true, - "dependencies": { - "object.getownpropertydescriptors": "^2.0.3" - } - }, - "node_modules/util/node_modules/inherits": { - "version": "2.0.3", - "resolved": "https://registry.npmjs.org/inherits/-/inherits-2.0.3.tgz", - "integrity": "sha1-Yzwsg+PaQqUC9SRmAiSA9CCCYd4=" - }, - "node_modules/utils-merge": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/utils-merge/-/utils-merge-1.0.1.tgz", - "integrity": "sha1-n5VxD1CiZ5R7LMwSR0HBAoQn5xM=", - "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==", - "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/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==", - "dependencies": { - "spdx-correct": "^3.0.0", - "spdx-expression-parse": "^3.0.0" - } - }, - "node_modules/validate-npm-package-name": { - "version": "3.0.0", - "resolved": "https://registry.npmjs.org/validate-npm-package-name/-/validate-npm-package-name-3.0.0.tgz", - "integrity": "sha1-X6kS2B630MdK/BQN5zF/DKffQ34=", - "dev": true, - "dependencies": { - "builtins": "^1.0.3" - } - }, - "node_modules/vary": { - "version": "1.1.2", - "resolved": "https://registry.npmjs.org/vary/-/vary-1.1.2.tgz", - "integrity": "sha1-IpnwLG3tMNSllhsLn3RSShj2NPw=", - "engines": { - "node": ">= 0.8" - } - }, - "node_modules/verror": { - "version": "1.10.0", - "resolved": "https://registry.npmjs.org/verror/-/verror-1.10.0.tgz", - "integrity": "sha1-OhBcoXBTr1XW4nDB+CiGguGNpAA=", - "dev": true, - "engines": [ - "node >=0.6.0" - ], - "dependencies": { - "assert-plus": "^1.0.0", - "core-util-is": "1.0.2", - "extsprintf": "^1.2.0" - } - }, - "node_modules/warp10": { - "version": "2.0.2", - "resolved": "https://registry.npmjs.org/warp10/-/warp10-2.0.2.tgz", - "integrity": "sha512-CC8MD3mBxPvKgBz58QJo8G+jPGo/oaBL2vcT6EWVpWsgzvDNwhiBBLGUDmRqaaVXv1INh8bpJPpVMUP5q1myBw==" - }, - "node_modules/watchpack": { - "version": "2.3.1", - "resolved": "https://registry.npmjs.org/watchpack/-/watchpack-2.3.1.tgz", - "integrity": "sha512-x0t0JuydIo8qCNctdDrn1OzH/qDzk2+rdCOC3YzumZ42fiMqmQ7T3xQurykYMhYfHaPHTp4ZxAx2NfUo1K6QaA==", - "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": "sha1-8LDc+RW8X/FSivrbLA4XtTLaL+g=", - "dev": true, - "dependencies": { - "defaults": "^1.0.3" - } - }, - "node_modules/webidl-conversions": { - "version": "6.1.0", - "resolved": "https://registry.npmjs.org/webidl-conversions/-/webidl-conversions-6.1.0.tgz", - "integrity": "sha512-qBIvFLGiBpLjfwmYAaHPXsn+ho5xZnGvyGvsarywGNc8VyQJUMHJ8OBKGGrPER0okBeMDaan4mNBlgBROxuI8w==", - "dev": true, - "engines": { - "node": ">=10.4" - } - }, - "node_modules/webpack": { - "version": "5.65.0", - "resolved": "https://registry.npmjs.org/webpack/-/webpack-5.65.0.tgz", - "integrity": "sha512-Q5or2o6EKs7+oKmJo7LaqZaMOlDWQse9Tm5l1WAfU/ujLGN5Pb0SqGeVkN/4bpPmEqEP5RnVhiqsOtWtUVwGRw==", - "dependencies": { - "@types/eslint-scope": "^3.7.0", - "@types/estree": "^0.0.50", - "@webassemblyjs/ast": "1.11.1", - "@webassemblyjs/wasm-edit": "1.11.1", - "@webassemblyjs/wasm-parser": "1.11.1", - "acorn": "^8.4.1", - "acorn-import-assertions": "^1.7.6", - "browserslist": "^4.14.5", - "chrome-trace-event": "^1.0.2", - "enhanced-resolve": "^5.8.3", - "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.4", - "json-parse-better-errors": "^1.0.2", - "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.3.1", - "webpack-sources": "^3.2.2" - }, - "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": "4.9.1", - "resolved": "https://registry.npmjs.org/webpack-cli/-/webpack-cli-4.9.1.tgz", - "integrity": "sha512-JYRFVuyFpzDxMDB+v/nanUdQYcZtqFPGzmlW4s+UkPMFhSpfRNmf1z4AwYcHJVdvEFAM7FFCQdNTpsBYhDLusQ==", - "dependencies": { - "@discoveryjs/json-ext": "^0.5.0", - "@webpack-cli/configtest": "^1.1.0", - "@webpack-cli/info": "^1.4.0", - "@webpack-cli/serve": "^1.6.0", - "colorette": "^2.0.14", - "commander": "^7.0.0", - "execa": "^5.0.0", - "fastest-levenshtein": "^1.0.12", - "import-local": "^3.0.2", - "interpret": "^2.2.0", - "rechoir": "^0.7.0", - "webpack-merge": "^5.7.3" - }, - "bin": { - "webpack-cli": "bin/cli.js" - }, - "engines": { - "node": ">=10.13.0" - }, - "peerDependencies": { - "webpack": "4.x.x || 5.x.x" - }, - "peerDependenciesMeta": { - "@webpack-cli/generators": { - "optional": true - }, - "@webpack-cli/migrate": { - "optional": true - }, - "webpack-bundle-analyzer": { - "optional": true - }, - "webpack-dev-server": { - "optional": true - } - } - }, - "node_modules/webpack-cli/node_modules/commander": { - "version": "7.2.0", - "resolved": "https://registry.npmjs.org/commander/-/commander-7.2.0.tgz", - "integrity": "sha512-QrWXB+ZQSVPmIWIhtEO9H+gwHaMGYiF5ChvoJ+K9ZGHG/sVsa6yiesAD1GC/x46sET00Xlwo1u49RVVVzvcSkw==", - "engines": { - "node": ">= 10" - } - }, - "node_modules/webpack-cli/node_modules/interpret": { - "version": "2.2.0", - "resolved": "https://registry.npmjs.org/interpret/-/interpret-2.2.0.tgz", - "integrity": "sha512-Ju0Bz/cEia55xDwUWEa8+olFpCiQoypjnQySseKtmjNrnps3P+xfpUmGr90T7yjlVJmOtybRvPXhKMbHr+fWnw==", - "engines": { - "node": ">= 0.10" - } - }, - "node_modules/webpack-cli/node_modules/rechoir": { - "version": "0.7.1", - "resolved": "https://registry.npmjs.org/rechoir/-/rechoir-0.7.1.tgz", - "integrity": "sha512-/njmZ8s1wVeR6pjTZ+0nCnv8SpZNRMT2D1RLOJQESlYFDBvwpTA4KWJpZ+sBJ4+vhjILRcK7JIFdGCdxEAAitg==", - "dependencies": { - "resolve": "^1.9.0" - }, - "engines": { - "node": ">= 0.10" - } - }, - "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==", - "dependencies": { - "clone-deep": "^4.0.1", - "wildcard": "^2.0.0" - }, - "engines": { - "node": ">=10.0.0" - } - }, - "node_modules/webpack-sources": { - "version": "3.2.2", - "resolved": "https://registry.npmjs.org/webpack-sources/-/webpack-sources-3.2.2.tgz", - "integrity": "sha512-cp5qdmHnu5T8wRg2G3vZZHoJPN14aqQ89SyQ11NpGH5zEMDCclt49rzo+MaRazk7/UeILhAI+/sEtcM+7Fr0nw==", - "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==", - "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==", - "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==" - }, - "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==", - "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/whatwg-url": { - "version": "8.7.0", - "resolved": "https://registry.npmjs.org/whatwg-url/-/whatwg-url-8.7.0.tgz", - "integrity": "sha512-gAojqb/m9Q8a5IV96E3fHJM70AzCkgt4uXYX2O7EmuyOnLrViCQlsEBmF9UQIu3/aeAIp2U17rtbpZWNntQqdg==", - "dev": true, - "dependencies": { - "lodash": "^4.7.0", - "tr46": "^2.1.0", - "webidl-conversions": "^6.1.0" - }, - "engines": { - "node": ">=10" - } - }, - "node_modules/which": { - "version": "2.0.2", - "resolved": "https://registry.npmjs.org/which/-/which-2.0.2.tgz", - "integrity": "sha512-BLI3Tl1TW3Pvl70l3yq3Y64i+awpwXqsGBYWkkqMtnbXgrMD+yj7rhW0kuEDxzJaYXGjEW5ogapKNMEKNMjibA==", - "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-module": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/which-module/-/which-module-2.0.0.tgz", - "integrity": "sha1-2e8H3Od7mQK4o6j6SzHD4/fm6Ho=", - "dev": true - }, - "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==", - "dev": true, - "dependencies": { - "string-width": "^1.0.2 || 2 || 3 || 4" - } - }, - "node_modules/widest-line": { - "version": "3.1.0", - "resolved": "https://registry.npmjs.org/widest-line/-/widest-line-3.1.0.tgz", - "integrity": "sha512-NsmoXalsWVDMGupxZ5R08ka9flZjjiLvHVAWYOKtiKM8ujtZWr9cRffak+uSE48+Ob8ObalXpwyeUiyDD6QFgg==", - "dev": true, - "dependencies": { - "string-width": "^4.0.0" - }, - "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==" - }, - "node_modules/window-size": { - "version": "0.1.0", - "resolved": "https://registry.npmjs.org/window-size/-/window-size-0.1.0.tgz", - "integrity": "sha1-VDjNLqk7IC76Ohn+iIeu58lPnJ0=", - "engines": { - "node": ">= 0.8.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==", - "engines": { - "node": ">=0.10.0" - } - }, - "node_modules/wordwrap": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/wordwrap/-/wordwrap-1.0.0.tgz", - "integrity": "sha1-J1hIEIkUVqQXHI0CJkQa3pDLyus=", - "dev": true - }, - "node_modules/workerpool": { - "version": "6.1.5", - "resolved": "https://registry.npmjs.org/workerpool/-/workerpool-6.1.5.tgz", - "integrity": "sha512-XdKkCK0Zqc6w3iTxLckiuJ81tiD/o5rBE/m+nXpRCB+/Sq4DqkfXZ/x0jW02DG1tGsfUGXbTJyZDP+eu67haSw==" - }, - "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==", - "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": "sha1-tSQ9jz7BqjXxNkYFvA0QNuMKtp8=" - }, - "node_modules/write-file-atomic": { - "version": "3.0.3", - "resolved": "https://registry.npmjs.org/write-file-atomic/-/write-file-atomic-3.0.3.tgz", - "integrity": "sha512-AvHcyZ5JnSfq3ioSyjrBkH9yW4m7Ayk8/9My/DD9onKeu/94fwrMocemO2QAJFAlnnDN+ZDS+ZjAR5ua1/PV/Q==", - "dev": true, - "dependencies": { - "imurmurhash": "^0.1.4", - "is-typedarray": "^1.0.0", - "signal-exit": "^3.0.2", - "typedarray-to-buffer": "^3.1.5" - } - }, - "node_modules/write-json-file": { - "version": "4.3.0", - "resolved": "https://registry.npmjs.org/write-json-file/-/write-json-file-4.3.0.tgz", - "integrity": "sha512-PxiShnxf0IlnQuMYOPPhPkhExoCQuTUNPOa/2JWCYTmBquU9njyyDuwRKN26IZBlp4yn1nt+Agh2HOOBl+55HQ==", - "dev": true, - "dependencies": { - "detect-indent": "^6.0.0", - "graceful-fs": "^4.1.15", - "is-plain-obj": "^2.0.0", - "make-dir": "^3.0.0", - "sort-keys": "^4.0.0", - "write-file-atomic": "^3.0.0" - }, - "engines": { - "node": ">=8.3" - }, - "funding": { - "url": "https://github.com/sponsors/sindresorhus" - } - }, - "node_modules/write-json-file/node_modules/is-plain-obj": { - "version": "2.1.0", - "resolved": "https://registry.npmjs.org/is-plain-obj/-/is-plain-obj-2.1.0.tgz", - "integrity": "sha512-YWnfyRwxL/+SsrWYfOpUtz5b3YD+nyfkHvjbcanzk8zgyO4ASD67uVMRt8k5bM4lLMDnXfriRhOpemw+NfT1eA==", - "dev": true, - "engines": { - "node": ">=8" - } - }, - "node_modules/write-pkg": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/write-pkg/-/write-pkg-4.0.0.tgz", - "integrity": "sha512-v2UQ+50TNf2rNHJ8NyWttfm/EJUBWMJcx6ZTYZr6Qp52uuegWw/lBkCtCbnYZEmPRNL61m+u67dAmGxo+HTULA==", - "dev": true, - "dependencies": { - "sort-keys": "^2.0.0", - "type-fest": "^0.4.1", - "write-json-file": "^3.2.0" - }, - "engines": { - "node": ">=8" - } - }, - "node_modules/write-pkg/node_modules/detect-indent": { - "version": "5.0.0", - "resolved": "https://registry.npmjs.org/detect-indent/-/detect-indent-5.0.0.tgz", - "integrity": "sha1-OHHMCmoALow+Wzz38zYmRnXwa50=", - "dev": true, - "engines": { - "node": ">=4" - } - }, - "node_modules/write-pkg/node_modules/make-dir": { - "version": "2.1.0", - "resolved": "https://registry.npmjs.org/make-dir/-/make-dir-2.1.0.tgz", - "integrity": "sha512-LS9X+dc8KLxXCb8dni79fLIIUA5VyZoyjSMCwTluaXA0o27cCK0bhXkpgw+sTXVpPy/lSO57ilRixqk0vDmtRA==", - "dev": true, - "dependencies": { - "pify": "^4.0.1", - "semver": "^5.6.0" - }, - "engines": { - "node": ">=6" - } - }, - "node_modules/write-pkg/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/write-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/write-pkg/node_modules/sort-keys": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/sort-keys/-/sort-keys-2.0.0.tgz", - "integrity": "sha1-ZYU1WEhh7JfXMNbPQYIuH1ZoQSg=", - "dev": true, - "dependencies": { - "is-plain-obj": "^1.0.0" - }, - "engines": { - "node": ">=4" - } - }, - "node_modules/write-pkg/node_modules/type-fest": { - "version": "0.4.1", - "resolved": "https://registry.npmjs.org/type-fest/-/type-fest-0.4.1.tgz", - "integrity": "sha512-IwzA/LSfD2vC1/YDYMv/zHP4rDF1usCwllsDpbolT3D4fUepIO7f9K70jjmUewU/LmGUKJcwcVtDCpnKk4BPMw==", - "dev": true, - "engines": { - "node": ">=6" - } - }, - "node_modules/write-pkg/node_modules/write-file-atomic": { - "version": "2.4.3", - "resolved": "https://registry.npmjs.org/write-file-atomic/-/write-file-atomic-2.4.3.tgz", - "integrity": "sha512-GaETH5wwsX+GcnzhPgKcKjJ6M2Cq3/iZp1WyY/X1CSqrW+jVNM9Y7D8EC2sM4ZG/V8wZlSniJnCKWPmBYAucRQ==", - "dev": true, - "dependencies": { - "graceful-fs": "^4.1.11", - "imurmurhash": "^0.1.4", - "signal-exit": "^3.0.2" - } - }, - "node_modules/write-pkg/node_modules/write-json-file": { - "version": "3.2.0", - "resolved": "https://registry.npmjs.org/write-json-file/-/write-json-file-3.2.0.tgz", - "integrity": "sha512-3xZqT7Byc2uORAatYiP3DHUUAVEkNOswEWNs9H5KXiicRTvzYzYqKjYc4G7p+8pltvAw641lVByKVtMpf+4sYQ==", - "dev": true, - "dependencies": { - "detect-indent": "^5.0.0", - "graceful-fs": "^4.1.15", - "make-dir": "^2.1.0", - "pify": "^4.0.1", - "sort-keys": "^2.0.0", - "write-file-atomic": "^2.4.2" - }, - "engines": { - "node": ">=6" - } - }, - "node_modules/ws": { - "version": "3.3.3", - "resolved": "https://registry.npmjs.org/ws/-/ws-3.3.3.tgz", - "integrity": "sha512-nnWLa/NwZSt4KQJu51MYlCcSQ5g7INpOrOMt4XV8j4dqTXdmlUmSHQ8/oLC069ckre0fRsgfvsKwbTdtKLCDkA==", - "dependencies": { - "async-limiter": "~1.0.0", - "safe-buffer": "~5.1.0", - "ultron": "~1.1.0" - } - }, - "node_modules/xdg-basedir": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/xdg-basedir/-/xdg-basedir-4.0.0.tgz", - "integrity": "sha512-PSNhEJDejZYV7h50BohL09Er9VaIefr2LMAf3OEmpCkjOi34eYyQYAXUTjEQtZJTKcF0E2UKTh+osDLsgNim9Q==", - "dev": true, - "engines": { - "node": ">=8" - } - }, - "node_modules/xmlhttprequest-ssl": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/xmlhttprequest-ssl/-/xmlhttprequest-ssl-2.0.0.tgz", - "integrity": "sha512-QKxVRxiRACQcVuQEYFsI1hhkrMlrXHPegbbd1yn9UHOmRxY+si12nQYzri3vbzt8VdTTRviqcKxcyllFas5z2A==", - "engines": { - "node": ">=0.4.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==", - "dev": true, - "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==", - "engines": { - "node": ">=10" - } - }, - "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/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": "16.2.0", - "resolved": "https://registry.npmjs.org/yargs/-/yargs-16.2.0.tgz", - "integrity": "sha512-D1mvvtDG0L5ft/jGWkLpG1+m0eQxOfaBvTNELraWj22wSVUMWxZUvYgJYcKh6jGGIkJFhH4IZPQhR4TKpc8mBw==", - "dependencies": { - "cliui": "^7.0.2", - "escalade": "^3.1.1", - "get-caller-file": "^2.0.5", - "require-directory": "^2.1.1", - "string-width": "^4.2.0", - "y18n": "^5.0.5", - "yargs-parser": "^20.2.2" - }, - "engines": { - "node": ">=10" - } - }, - "node_modules/yargs-parser": { - "version": "20.2.4", - "resolved": "https://registry.npmjs.org/yargs-parser/-/yargs-parser-20.2.4.tgz", - "integrity": "sha512-WOkpgNhPTlE73h4VFAFsOnomJVaovO8VqLDzy5saChRBFQFBoMYirowyW+Q9HB4HFF4Z7VZTiG3iSzJJA29yRA==", - "engines": { - "node": ">=10" - } - }, - "node_modules/yargs-unparser": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/yargs-unparser/-/yargs-unparser-2.0.0.tgz", - "integrity": "sha512-7pRTIA9Qc1caZ0bZ6RYRGbHJthJWuakf+WmHK0rVeLkNrrGhfoabBNdue6kdINI6r4if7ocq9aD/n7xwKOdzOA==", - "dependencies": { - "camelcase": "^6.0.0", - "decamelize": "^4.0.0", - "flat": "^5.0.2", - "is-plain-obj": "^2.1.0" - }, - "engines": { - "node": ">=10" - } - }, - "node_modules/yargs-unparser/node_modules/camelcase": { - "version": "6.3.0", - "resolved": "https://registry.npmjs.org/camelcase/-/camelcase-6.3.0.tgz", - "integrity": "sha512-Gmy6FhYlCY7uOElZUSbxo2UCDH8owEk996gkbrpsgGtrJLM3J7jGxl9Ic7Qwwj4ivOE5AWZWRMecDdF7hqGjFA==", - "engines": { - "node": ">=10" - }, - "funding": { - "url": "https://github.com/sponsors/sindresorhus" - } - }, - "node_modules/yargs-unparser/node_modules/decamelize": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/decamelize/-/decamelize-4.0.0.tgz", - "integrity": "sha512-9iE1PgSik9HeIIw2JO94IidnE3eBoQrFJ3w7sFuzSX4DpmZ3v5sZpUiV5Swcf6mQEF+Y0ru8Neo+p+nyh2J+hQ==", - "engines": { - "node": ">=10" - }, - "funding": { - "url": "https://github.com/sponsors/sindresorhus" - } - }, - "node_modules/yargs-unparser/node_modules/is-plain-obj": { - "version": "2.1.0", - "resolved": "https://registry.npmjs.org/is-plain-obj/-/is-plain-obj-2.1.0.tgz", - "integrity": "sha512-YWnfyRwxL/+SsrWYfOpUtz5b3YD+nyfkHvjbcanzk8zgyO4ASD67uVMRt8k5bM4lLMDnXfriRhOpemw+NfT1eA==", - "engines": { - "node": ">=8" - } - }, - "node_modules/yauzl": { - "version": "2.10.0", - "resolved": "https://registry.npmjs.org/yauzl/-/yauzl-2.10.0.tgz", - "integrity": "sha1-x+sXyT4RLLEIb6bY5R+wZnt5pfk=", - "dependencies": { - "buffer-crc32": "~0.2.3", - "fd-slicer": "~1.1.0" - } - }, - "node_modules/yeast": { - "version": "0.1.2", - "resolved": "https://registry.npmjs.org/yeast/-/yeast-0.1.2.tgz", - "integrity": "sha1-AI4G2AlDIMNy28L47XagymyKxBk=" - }, - "node_modules/ylru": { - "version": "1.2.1", - "resolved": "https://registry.npmjs.org/ylru/-/ylru-1.2.1.tgz", - "integrity": "sha512-faQrqNMzcPCHGVC2aaOINk13K+aaBDUPjGWl0teOXywElLjyVAB6Oe2jj62jHYtwsU49jXhScYbvPENK+6zAvQ==", - "engines": { - "node": ">= 4.0.0" - } - }, - "node_modules/yn": { - "version": "3.1.1", - "resolved": "https://registry.npmjs.org/yn/-/yn-3.1.1.tgz", - "integrity": "sha512-Ux4ygGWsu2c7isFWe8Yu1YluJmqVhxqK2cLXNQA5AcC3QfbGNpM7fu0Y8b/z16pXLnFxZYvWhd3fhBY9DLmC6Q==", - "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==", - "engines": { - "node": ">=10" - }, - "funding": { - "url": "https://github.com/sponsors/sindresorhus" - } - } - }, - "dependencies": { - "@babel/code-frame": { - "version": "7.16.7", - "resolved": "https://registry.npmjs.org/@babel/code-frame/-/code-frame-7.16.7.tgz", - "integrity": "sha512-iAXqUn8IIeBTNd72xsFlgaXHkMBMt6y4HJp1tIaK465CWLT/fG1aqB7ykr95gHHmlBdGbFeWWfyB4NJJ0nmeIg==", - "requires": { - "@babel/highlight": "^7.16.7" - } - }, - "@babel/compat-data": { - "version": "7.16.4", - "resolved": "https://registry.npmjs.org/@babel/compat-data/-/compat-data-7.16.4.tgz", - "integrity": "sha512-1o/jo7D+kC9ZjHX5v+EHrdjl3PhxMrLSOTGsOdHJ+KL8HCaEK6ehrVL2RS6oHDZp+L7xLirLrPmQtEng769J/Q==" - }, - "@babel/core": { - "version": "7.16.7", - "resolved": "https://registry.npmjs.org/@babel/core/-/core-7.16.7.tgz", - "integrity": "sha512-aeLaqcqThRNZYmbMqtulsetOQZ/5gbR/dWruUCJcpas4Qoyy+QeagfDsPdMrqwsPRDNxJvBlRiZxxX7THO7qtA==", - "requires": { - "@babel/code-frame": "^7.16.7", - "@babel/generator": "^7.16.7", - "@babel/helper-compilation-targets": "^7.16.7", - "@babel/helper-module-transforms": "^7.16.7", - "@babel/helpers": "^7.16.7", - "@babel/parser": "^7.16.7", - "@babel/template": "^7.16.7", - "@babel/traverse": "^7.16.7", - "@babel/types": "^7.16.7", - "convert-source-map": "^1.7.0", - "debug": "^4.1.0", - "gensync": "^1.0.0-beta.2", - "json5": "^2.1.2", - "semver": "^6.3.0", - "source-map": "^0.5.0" - }, - "dependencies": { - "semver": { - "version": "6.3.0", - "resolved": "https://registry.npmjs.org/semver/-/semver-6.3.0.tgz", - "integrity": "sha512-b39TBaTSfV6yBrapU89p5fKekE2m/NwnDocOVruQFS1/veMgdzuPcnOM34M6CwxW8jH/lxEa5rBoDeUwu5HHTw==" - }, - "source-map": { - "version": "0.5.7", - "resolved": "https://registry.npmjs.org/source-map/-/source-map-0.5.7.tgz", - "integrity": "sha1-igOdLRAh0i0eoUyA2OpGi6LvP8w=" - } - } - }, - "@babel/generator": { - "version": "7.16.7", - "resolved": "https://registry.npmjs.org/@babel/generator/-/generator-7.16.7.tgz", - "integrity": "sha512-/ST3Sg8MLGY5HVYmrjOgL60ENux/HfO/CsUh7y4MalThufhE/Ff/6EibFDHi4jiDCaWfJKoqbE6oTh21c5hrRg==", - "requires": { - "@babel/types": "^7.16.7", - "jsesc": "^2.5.1", - "source-map": "^0.5.0" - }, - "dependencies": { - "source-map": { - "version": "0.5.7", - "resolved": "https://registry.npmjs.org/source-map/-/source-map-0.5.7.tgz", - "integrity": "sha1-igOdLRAh0i0eoUyA2OpGi6LvP8w=" - } - } - }, - "@babel/helper-annotate-as-pure": { - "version": "7.16.7", - "resolved": "https://registry.npmjs.org/@babel/helper-annotate-as-pure/-/helper-annotate-as-pure-7.16.7.tgz", - "integrity": "sha512-s6t2w/IPQVTAET1HitoowRGXooX8mCgtuP5195wD/QJPV6wYjpujCGF7JuMODVX2ZAJOf1GT6DT9MHEZvLOFSw==", - "requires": { - "@babel/types": "^7.16.7" - } - }, - "@babel/helper-builder-binary-assignment-operator-visitor": { - "version": "7.16.7", - "resolved": "https://registry.npmjs.org/@babel/helper-builder-binary-assignment-operator-visitor/-/helper-builder-binary-assignment-operator-visitor-7.16.7.tgz", - "integrity": "sha512-C6FdbRaxYjwVu/geKW4ZeQ0Q31AftgRcdSnZ5/jsH6BzCJbtvXvhpfkbkThYSuutZA7nCXpPR6AD9zd1dprMkA==", - "requires": { - "@babel/helper-explode-assignable-expression": "^7.16.7", - "@babel/types": "^7.16.7" - } - }, - "@babel/helper-compilation-targets": { - "version": "7.16.7", - "resolved": "https://registry.npmjs.org/@babel/helper-compilation-targets/-/helper-compilation-targets-7.16.7.tgz", - "integrity": "sha512-mGojBwIWcwGD6rfqgRXVlVYmPAv7eOpIemUG3dGnDdCY4Pae70ROij3XmfrH6Fa1h1aiDylpglbZyktfzyo/hA==", - "requires": { - "@babel/compat-data": "^7.16.4", - "@babel/helper-validator-option": "^7.16.7", - "browserslist": "^4.17.5", - "semver": "^6.3.0" - }, - "dependencies": { - "semver": { - "version": "6.3.0", - "resolved": "https://registry.npmjs.org/semver/-/semver-6.3.0.tgz", - "integrity": "sha512-b39TBaTSfV6yBrapU89p5fKekE2m/NwnDocOVruQFS1/veMgdzuPcnOM34M6CwxW8jH/lxEa5rBoDeUwu5HHTw==" - } - } - }, - "@babel/helper-create-class-features-plugin": { - "version": "7.16.7", - "resolved": "https://registry.npmjs.org/@babel/helper-create-class-features-plugin/-/helper-create-class-features-plugin-7.16.7.tgz", - "integrity": "sha512-kIFozAvVfK05DM4EVQYKK+zteWvY85BFdGBRQBytRyY3y+6PX0DkDOn/CZ3lEuczCfrCxEzwt0YtP/87YPTWSw==", - "requires": { - "@babel/helper-annotate-as-pure": "^7.16.7", - "@babel/helper-environment-visitor": "^7.16.7", - "@babel/helper-function-name": "^7.16.7", - "@babel/helper-member-expression-to-functions": "^7.16.7", - "@babel/helper-optimise-call-expression": "^7.16.7", - "@babel/helper-replace-supers": "^7.16.7", - "@babel/helper-split-export-declaration": "^7.16.7" - } - }, - "@babel/helper-create-regexp-features-plugin": { - "version": "7.16.7", - "resolved": "https://registry.npmjs.org/@babel/helper-create-regexp-features-plugin/-/helper-create-regexp-features-plugin-7.16.7.tgz", - "integrity": "sha512-fk5A6ymfp+O5+p2yCkXAu5Kyj6v0xh0RBeNcAkYUMDvvAAoxvSKXn+Jb37t/yWFiQVDFK1ELpUTD8/aLhCPu+g==", - "requires": { - "@babel/helper-annotate-as-pure": "^7.16.7", - "regexpu-core": "^4.7.1" - } - }, - "@babel/helper-define-polyfill-provider": { - "version": "0.3.0", - "resolved": "https://registry.npmjs.org/@babel/helper-define-polyfill-provider/-/helper-define-polyfill-provider-0.3.0.tgz", - "integrity": "sha512-7hfT8lUljl/tM3h+izTX/pO3W3frz2ok6Pk+gzys8iJqDfZrZy2pXjRTZAvG2YmfHun1X4q8/UZRLatMfqc5Tg==", - "requires": { - "@babel/helper-compilation-targets": "^7.13.0", - "@babel/helper-module-imports": "^7.12.13", - "@babel/helper-plugin-utils": "^7.13.0", - "@babel/traverse": "^7.13.0", - "debug": "^4.1.1", - "lodash.debounce": "^4.0.8", - "resolve": "^1.14.2", - "semver": "^6.1.2" - }, - "dependencies": { - "semver": { - "version": "6.3.0", - "resolved": "https://registry.npmjs.org/semver/-/semver-6.3.0.tgz", - "integrity": "sha512-b39TBaTSfV6yBrapU89p5fKekE2m/NwnDocOVruQFS1/veMgdzuPcnOM34M6CwxW8jH/lxEa5rBoDeUwu5HHTw==" - } - } - }, - "@babel/helper-environment-visitor": { - "version": "7.16.7", - "resolved": "https://registry.npmjs.org/@babel/helper-environment-visitor/-/helper-environment-visitor-7.16.7.tgz", - "integrity": "sha512-SLLb0AAn6PkUeAfKJCCOl9e1R53pQlGAfc4y4XuMRZfqeMYLE0dM1LMhqbGAlGQY0lfw5/ohoYWAe9V1yibRag==", - "requires": { - "@babel/types": "^7.16.7" - } - }, - "@babel/helper-explode-assignable-expression": { - "version": "7.16.7", - "resolved": "https://registry.npmjs.org/@babel/helper-explode-assignable-expression/-/helper-explode-assignable-expression-7.16.7.tgz", - "integrity": "sha512-KyUenhWMC8VrxzkGP0Jizjo4/Zx+1nNZhgocs+gLzyZyB8SHidhoq9KK/8Ato4anhwsivfkBLftky7gvzbZMtQ==", - "requires": { - "@babel/types": "^7.16.7" - } - }, - "@babel/helper-function-name": { - "version": "7.16.7", - "resolved": "https://registry.npmjs.org/@babel/helper-function-name/-/helper-function-name-7.16.7.tgz", - "integrity": "sha512-QfDfEnIUyyBSR3HtrtGECuZ6DAyCkYFp7GHl75vFtTnn6pjKeK0T1DB5lLkFvBea8MdaiUABx3osbgLyInoejA==", - "requires": { - "@babel/helper-get-function-arity": "^7.16.7", - "@babel/template": "^7.16.7", - "@babel/types": "^7.16.7" - } - }, - "@babel/helper-get-function-arity": { - "version": "7.16.7", - "resolved": "https://registry.npmjs.org/@babel/helper-get-function-arity/-/helper-get-function-arity-7.16.7.tgz", - "integrity": "sha512-flc+RLSOBXzNzVhcLu6ujeHUrD6tANAOU5ojrRx/as+tbzf8+stUCj7+IfRRoAbEZqj/ahXEMsjhOhgeZsrnTw==", - "requires": { - "@babel/types": "^7.16.7" - } - }, - "@babel/helper-hoist-variables": { - "version": "7.16.7", - "resolved": "https://registry.npmjs.org/@babel/helper-hoist-variables/-/helper-hoist-variables-7.16.7.tgz", - "integrity": "sha512-m04d/0Op34H5v7pbZw6pSKP7weA6lsMvfiIAMeIvkY/R4xQtBSMFEigu9QTZ2qB/9l22vsxtM8a+Q8CzD255fg==", - "requires": { - "@babel/types": "^7.16.7" - } - }, - "@babel/helper-member-expression-to-functions": { - "version": "7.16.7", - "resolved": "https://registry.npmjs.org/@babel/helper-member-expression-to-functions/-/helper-member-expression-to-functions-7.16.7.tgz", - "integrity": "sha512-VtJ/65tYiU/6AbMTDwyoXGPKHgTsfRarivm+YbB5uAzKUyuPjgZSgAFeG87FCigc7KNHu2Pegh1XIT3lXjvz3Q==", - "requires": { - "@babel/types": "^7.16.7" - } - }, - "@babel/helper-module-imports": { - "version": "7.16.7", - "resolved": "https://registry.npmjs.org/@babel/helper-module-imports/-/helper-module-imports-7.16.7.tgz", - "integrity": "sha512-LVtS6TqjJHFc+nYeITRo6VLXve70xmq7wPhWTqDJusJEgGmkAACWwMiTNrvfoQo6hEhFwAIixNkvB0jPXDL8Wg==", - "requires": { - "@babel/types": "^7.16.7" - } - }, - "@babel/helper-module-transforms": { - "version": "7.16.7", - "resolved": "https://registry.npmjs.org/@babel/helper-module-transforms/-/helper-module-transforms-7.16.7.tgz", - "integrity": "sha512-gaqtLDxJEFCeQbYp9aLAefjhkKdjKcdh6DB7jniIGU3Pz52WAmP268zK0VgPz9hUNkMSYeH976K2/Y6yPadpng==", - "requires": { - "@babel/helper-environment-visitor": "^7.16.7", - "@babel/helper-module-imports": "^7.16.7", - "@babel/helper-simple-access": "^7.16.7", - "@babel/helper-split-export-declaration": "^7.16.7", - "@babel/helper-validator-identifier": "^7.16.7", - "@babel/template": "^7.16.7", - "@babel/traverse": "^7.16.7", - "@babel/types": "^7.16.7" - } - }, - "@babel/helper-optimise-call-expression": { - "version": "7.16.7", - "resolved": "https://registry.npmjs.org/@babel/helper-optimise-call-expression/-/helper-optimise-call-expression-7.16.7.tgz", - "integrity": "sha512-EtgBhg7rd/JcnpZFXpBy0ze1YRfdm7BnBX4uKMBd3ixa3RGAE002JZB66FJyNH7g0F38U05pXmA5P8cBh7z+1w==", - "requires": { - "@babel/types": "^7.16.7" - } - }, - "@babel/helper-plugin-utils": { - "version": "7.16.7", - "resolved": "https://registry.npmjs.org/@babel/helper-plugin-utils/-/helper-plugin-utils-7.16.7.tgz", - "integrity": "sha512-Qg3Nk7ZxpgMrsox6HreY1ZNKdBq7K72tDSliA6dCl5f007jR4ne8iD5UzuNnCJH2xBf2BEEVGr+/OL6Gdp7RxA==" - }, - "@babel/helper-remap-async-to-generator": { - "version": "7.16.7", - "resolved": "https://registry.npmjs.org/@babel/helper-remap-async-to-generator/-/helper-remap-async-to-generator-7.16.7.tgz", - "integrity": "sha512-C3o117GnP/j/N2OWo+oepeWbFEKRfNaay+F1Eo5Mj3A1SRjyx+qaFhm23nlipub7Cjv2azdUUiDH+VlpdwUFRg==", - "requires": { - "@babel/helper-annotate-as-pure": "^7.16.7", - "@babel/helper-wrap-function": "^7.16.7", - "@babel/types": "^7.16.7" - } - }, - "@babel/helper-replace-supers": { - "version": "7.16.7", - "resolved": "https://registry.npmjs.org/@babel/helper-replace-supers/-/helper-replace-supers-7.16.7.tgz", - "integrity": "sha512-y9vsWilTNaVnVh6xiJfABzsNpgDPKev9HnAgz6Gb1p6UUwf9NepdlsV7VXGCftJM+jqD5f7JIEubcpLjZj5dBw==", - "requires": { - "@babel/helper-environment-visitor": "^7.16.7", - "@babel/helper-member-expression-to-functions": "^7.16.7", - "@babel/helper-optimise-call-expression": "^7.16.7", - "@babel/traverse": "^7.16.7", - "@babel/types": "^7.16.7" - } - }, - "@babel/helper-simple-access": { - "version": "7.16.7", - "resolved": "https://registry.npmjs.org/@babel/helper-simple-access/-/helper-simple-access-7.16.7.tgz", - "integrity": "sha512-ZIzHVyoeLMvXMN/vok/a4LWRy8G2v205mNP0XOuf9XRLyX5/u9CnVulUtDgUTama3lT+bf/UqucuZjqiGuTS1g==", - "requires": { - "@babel/types": "^7.16.7" - } - }, - "@babel/helper-skip-transparent-expression-wrappers": { - "version": "7.16.0", - "resolved": "https://registry.npmjs.org/@babel/helper-skip-transparent-expression-wrappers/-/helper-skip-transparent-expression-wrappers-7.16.0.tgz", - "integrity": "sha512-+il1gTy0oHwUsBQZyJvukbB4vPMdcYBrFHa0Uc4AizLxbq6BOYC51Rv4tWocX9BLBDLZ4kc6qUFpQ6HRgL+3zw==", - "requires": { - "@babel/types": "^7.16.0" - } - }, - "@babel/helper-split-export-declaration": { - "version": "7.16.7", - "resolved": "https://registry.npmjs.org/@babel/helper-split-export-declaration/-/helper-split-export-declaration-7.16.7.tgz", - "integrity": "sha512-xbWoy/PFoxSWazIToT9Sif+jJTlrMcndIsaOKvTA6u7QEo7ilkRZpjew18/W3c7nm8fXdUDXh02VXTbZ0pGDNw==", - "requires": { - "@babel/types": "^7.16.7" - } - }, - "@babel/helper-validator-identifier": { - "version": "7.16.7", - "resolved": "https://registry.npmjs.org/@babel/helper-validator-identifier/-/helper-validator-identifier-7.16.7.tgz", - "integrity": "sha512-hsEnFemeiW4D08A5gUAZxLBTXpZ39P+a+DGDsHw1yxqyQ/jzFEnxf5uTEGp+3bzAbNOxU1paTgYS4ECU/IgfDw==" - }, - "@babel/helper-validator-option": { - "version": "7.16.7", - "resolved": "https://registry.npmjs.org/@babel/helper-validator-option/-/helper-validator-option-7.16.7.tgz", - "integrity": "sha512-TRtenOuRUVo9oIQGPC5G9DgK4743cdxvtOw0weQNpZXaS16SCBi5MNjZF8vba3ETURjZpTbVn7Vvcf2eAwFozQ==" - }, - "@babel/helper-wrap-function": { - "version": "7.16.7", - "resolved": "https://registry.npmjs.org/@babel/helper-wrap-function/-/helper-wrap-function-7.16.7.tgz", - "integrity": "sha512-7a9sABeVwcunnztZZ7WTgSw6jVYLzM1wua0Z4HIXm9S3/HC96WKQTkFgGEaj5W06SHHihPJ6Le6HzS5cGOQMNw==", - "requires": { - "@babel/helper-function-name": "^7.16.7", - "@babel/template": "^7.16.7", - "@babel/traverse": "^7.16.7", - "@babel/types": "^7.16.7" - } - }, - "@babel/helpers": { - "version": "7.16.7", - "resolved": "https://registry.npmjs.org/@babel/helpers/-/helpers-7.16.7.tgz", - "integrity": "sha512-9ZDoqtfY7AuEOt3cxchfii6C7GDyyMBffktR5B2jvWv8u2+efwvpnVKXMWzNehqy68tKgAfSwfdw/lWpthS2bw==", - "requires": { - "@babel/template": "^7.16.7", - "@babel/traverse": "^7.16.7", - "@babel/types": "^7.16.7" - } - }, - "@babel/highlight": { - "version": "7.16.7", - "resolved": "https://registry.npmjs.org/@babel/highlight/-/highlight-7.16.7.tgz", - "integrity": "sha512-aKpPMfLvGO3Q97V0qhw/V2SWNWlwfJknuwAunU7wZLSfrM4xTBvg7E5opUVi1kJTBKihE38CPg4nBiqX83PWYw==", - "requires": { - "@babel/helper-validator-identifier": "^7.16.7", - "chalk": "^2.0.0", - "js-tokens": "^4.0.0" - }, - "dependencies": { - "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==", - "requires": { - "color-convert": "^1.9.0" - } - }, - "chalk": { - "version": "2.4.2", - "resolved": "https://registry.npmjs.org/chalk/-/chalk-2.4.2.tgz", - "integrity": "sha512-Mti+f9lpJNcwF4tWV8/OrTTtF1gZi+f8FqlyAdouralcFWFQWF2+NgCHShjkCb+IFBLq9buZwE1xckQU4peSuQ==", - "requires": { - "ansi-styles": "^3.2.1", - "escape-string-regexp": "^1.0.5", - "supports-color": "^5.3.0" - } - }, - "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==", - "requires": { - "color-name": "1.1.3" - } - }, - "color-name": { - "version": "1.1.3", - "resolved": "https://registry.npmjs.org/color-name/-/color-name-1.1.3.tgz", - "integrity": "sha1-p9BVi9icQveV3UIyj3QIMcpTvCU=" - }, - "escape-string-regexp": { - "version": "1.0.5", - "resolved": "https://registry.npmjs.org/escape-string-regexp/-/escape-string-regexp-1.0.5.tgz", - "integrity": "sha1-G2HAViGQqN/2rjuyzwIAyhMLhtQ=" - }, - "has-flag": { - "version": "3.0.0", - "resolved": "https://registry.npmjs.org/has-flag/-/has-flag-3.0.0.tgz", - "integrity": "sha1-tdRU3CGZriJWmfNGfloH87lVuv0=" - }, - "supports-color": { - "version": "5.5.0", - "resolved": "https://registry.npmjs.org/supports-color/-/supports-color-5.5.0.tgz", - "integrity": "sha512-QjVjwdXIt408MIiAqCX4oUKsgU2EqAGzs2Ppkm4aQYbjm+ZEWEcW4SfFNTr4uMNZma0ey4f5lgLrkB0aX0QMow==", - "requires": { - "has-flag": "^3.0.0" - } - } - } - }, - "@babel/parser": { - "version": "7.16.7", - "resolved": "https://registry.npmjs.org/@babel/parser/-/parser-7.16.7.tgz", - "integrity": "sha512-sR4eaSrnM7BV7QPzGfEX5paG/6wrZM3I0HDzfIAK06ESvo9oy3xBuVBxE3MbQaKNhvg8g/ixjMWo2CGpzpHsDA==" - }, - "@babel/plugin-bugfix-safari-id-destructuring-collision-in-function-expression": { - "version": "7.16.7", - "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.16.7.tgz", - "integrity": "sha512-anv/DObl7waiGEnC24O9zqL0pSuI9hljihqiDuFHC8d7/bjr/4RLGPWuc8rYOff/QPzbEPSkzG8wGG9aDuhHRg==", - "requires": { - "@babel/helper-plugin-utils": "^7.16.7" - } - }, - "@babel/plugin-bugfix-v8-spread-parameters-in-optional-chaining": { - "version": "7.16.7", - "resolved": "https://registry.npmjs.org/@babel/plugin-bugfix-v8-spread-parameters-in-optional-chaining/-/plugin-bugfix-v8-spread-parameters-in-optional-chaining-7.16.7.tgz", - "integrity": "sha512-di8vUHRdf+4aJ7ltXhaDbPoszdkh59AQtJM5soLsuHpQJdFQZOA4uGj0V2u/CZ8bJ/u8ULDL5yq6FO/bCXnKHw==", - "requires": { - "@babel/helper-plugin-utils": "^7.16.7", - "@babel/helper-skip-transparent-expression-wrappers": "^7.16.0", - "@babel/plugin-proposal-optional-chaining": "^7.16.7" - } - }, - "@babel/plugin-proposal-async-generator-functions": { - "version": "7.16.7", - "resolved": "https://registry.npmjs.org/@babel/plugin-proposal-async-generator-functions/-/plugin-proposal-async-generator-functions-7.16.7.tgz", - "integrity": "sha512-TTXBT3A5c11eqRzaC6beO6rlFT3Mo9C2e8eB44tTr52ESXSK2CIc2fOp1ynpAwQA8HhBMho+WXhMHWlAe3xkpw==", - "requires": { - "@babel/helper-plugin-utils": "^7.16.7", - "@babel/helper-remap-async-to-generator": "^7.16.7", - "@babel/plugin-syntax-async-generators": "^7.8.4" - } - }, - "@babel/plugin-proposal-class-properties": { - "version": "7.16.7", - "resolved": "https://registry.npmjs.org/@babel/plugin-proposal-class-properties/-/plugin-proposal-class-properties-7.16.7.tgz", - "integrity": "sha512-IobU0Xme31ewjYOShSIqd/ZGM/r/cuOz2z0MDbNrhF5FW+ZVgi0f2lyeoj9KFPDOAqsYxmLWZte1WOwlvY9aww==", - "requires": { - "@babel/helper-create-class-features-plugin": "^7.16.7", - "@babel/helper-plugin-utils": "^7.16.7" - } - }, - "@babel/plugin-proposal-class-static-block": { - "version": "7.16.7", - "resolved": "https://registry.npmjs.org/@babel/plugin-proposal-class-static-block/-/plugin-proposal-class-static-block-7.16.7.tgz", - "integrity": "sha512-dgqJJrcZoG/4CkMopzhPJjGxsIe9A8RlkQLnL/Vhhx8AA9ZuaRwGSlscSh42hazc7WSrya/IK7mTeoF0DP9tEw==", - "requires": { - "@babel/helper-create-class-features-plugin": "^7.16.7", - "@babel/helper-plugin-utils": "^7.16.7", - "@babel/plugin-syntax-class-static-block": "^7.14.5" - } - }, - "@babel/plugin-proposal-dynamic-import": { - "version": "7.16.7", - "resolved": "https://registry.npmjs.org/@babel/plugin-proposal-dynamic-import/-/plugin-proposal-dynamic-import-7.16.7.tgz", - "integrity": "sha512-I8SW9Ho3/8DRSdmDdH3gORdyUuYnk1m4cMxUAdu5oy4n3OfN8flDEH+d60iG7dUfi0KkYwSvoalHzzdRzpWHTg==", - "requires": { - "@babel/helper-plugin-utils": "^7.16.7", - "@babel/plugin-syntax-dynamic-import": "^7.8.3" - } - }, - "@babel/plugin-proposal-export-namespace-from": { - "version": "7.16.7", - "resolved": "https://registry.npmjs.org/@babel/plugin-proposal-export-namespace-from/-/plugin-proposal-export-namespace-from-7.16.7.tgz", - "integrity": "sha512-ZxdtqDXLRGBL64ocZcs7ovt71L3jhC1RGSyR996svrCi3PYqHNkb3SwPJCs8RIzD86s+WPpt2S73+EHCGO+NUA==", - "requires": { - "@babel/helper-plugin-utils": "^7.16.7", - "@babel/plugin-syntax-export-namespace-from": "^7.8.3" - } - }, - "@babel/plugin-proposal-json-strings": { - "version": "7.16.7", - "resolved": "https://registry.npmjs.org/@babel/plugin-proposal-json-strings/-/plugin-proposal-json-strings-7.16.7.tgz", - "integrity": "sha512-lNZ3EEggsGY78JavgbHsK9u5P3pQaW7k4axlgFLYkMd7UBsiNahCITShLjNQschPyjtO6dADrL24757IdhBrsQ==", - "requires": { - "@babel/helper-plugin-utils": "^7.16.7", - "@babel/plugin-syntax-json-strings": "^7.8.3" - } - }, - "@babel/plugin-proposal-logical-assignment-operators": { - "version": "7.16.7", - "resolved": "https://registry.npmjs.org/@babel/plugin-proposal-logical-assignment-operators/-/plugin-proposal-logical-assignment-operators-7.16.7.tgz", - "integrity": "sha512-K3XzyZJGQCr00+EtYtrDjmwX7o7PLK6U9bi1nCwkQioRFVUv6dJoxbQjtWVtP+bCPy82bONBKG8NPyQ4+i6yjg==", - "requires": { - "@babel/helper-plugin-utils": "^7.16.7", - "@babel/plugin-syntax-logical-assignment-operators": "^7.10.4" - } - }, - "@babel/plugin-proposal-nullish-coalescing-operator": { - "version": "7.16.7", - "resolved": "https://registry.npmjs.org/@babel/plugin-proposal-nullish-coalescing-operator/-/plugin-proposal-nullish-coalescing-operator-7.16.7.tgz", - "integrity": "sha512-aUOrYU3EVtjf62jQrCj63pYZ7k6vns2h/DQvHPWGmsJRYzWXZ6/AsfgpiRy6XiuIDADhJzP2Q9MwSMKauBQ+UQ==", - "requires": { - "@babel/helper-plugin-utils": "^7.16.7", - "@babel/plugin-syntax-nullish-coalescing-operator": "^7.8.3" - } - }, - "@babel/plugin-proposal-numeric-separator": { - "version": "7.16.7", - "resolved": "https://registry.npmjs.org/@babel/plugin-proposal-numeric-separator/-/plugin-proposal-numeric-separator-7.16.7.tgz", - "integrity": "sha512-vQgPMknOIgiuVqbokToyXbkY/OmmjAzr/0lhSIbG/KmnzXPGwW/AdhdKpi+O4X/VkWiWjnkKOBiqJrTaC98VKw==", - "requires": { - "@babel/helper-plugin-utils": "^7.16.7", - "@babel/plugin-syntax-numeric-separator": "^7.10.4" - } - }, - "@babel/plugin-proposal-object-rest-spread": { - "version": "7.16.7", - "resolved": "https://registry.npmjs.org/@babel/plugin-proposal-object-rest-spread/-/plugin-proposal-object-rest-spread-7.16.7.tgz", - "integrity": "sha512-3O0Y4+dw94HA86qSg9IHfyPktgR7q3gpNVAeiKQd+8jBKFaU5NQS1Yatgo4wY+UFNuLjvxcSmzcsHqrhgTyBUA==", - "requires": { - "@babel/compat-data": "^7.16.4", - "@babel/helper-compilation-targets": "^7.16.7", - "@babel/helper-plugin-utils": "^7.16.7", - "@babel/plugin-syntax-object-rest-spread": "^7.8.3", - "@babel/plugin-transform-parameters": "^7.16.7" - } - }, - "@babel/plugin-proposal-optional-catch-binding": { - "version": "7.16.7", - "resolved": "https://registry.npmjs.org/@babel/plugin-proposal-optional-catch-binding/-/plugin-proposal-optional-catch-binding-7.16.7.tgz", - "integrity": "sha512-eMOH/L4OvWSZAE1VkHbr1vckLG1WUcHGJSLqqQwl2GaUqG6QjddvrOaTUMNYiv77H5IKPMZ9U9P7EaHwvAShfA==", - "requires": { - "@babel/helper-plugin-utils": "^7.16.7", - "@babel/plugin-syntax-optional-catch-binding": "^7.8.3" - } - }, - "@babel/plugin-proposal-optional-chaining": { - "version": "7.16.7", - "resolved": "https://registry.npmjs.org/@babel/plugin-proposal-optional-chaining/-/plugin-proposal-optional-chaining-7.16.7.tgz", - "integrity": "sha512-eC3xy+ZrUcBtP7x+sq62Q/HYd674pPTb/77XZMb5wbDPGWIdUbSr4Agr052+zaUPSb+gGRnjxXfKFvx5iMJ+DA==", - "requires": { - "@babel/helper-plugin-utils": "^7.16.7", - "@babel/helper-skip-transparent-expression-wrappers": "^7.16.0", - "@babel/plugin-syntax-optional-chaining": "^7.8.3" - } - }, - "@babel/plugin-proposal-private-methods": { - "version": "7.16.7", - "resolved": "https://registry.npmjs.org/@babel/plugin-proposal-private-methods/-/plugin-proposal-private-methods-7.16.7.tgz", - "integrity": "sha512-7twV3pzhrRxSwHeIvFE6coPgvo+exNDOiGUMg39o2LiLo1Y+4aKpfkcLGcg1UHonzorCt7SNXnoMyCnnIOA8Sw==", - "requires": { - "@babel/helper-create-class-features-plugin": "^7.16.7", - "@babel/helper-plugin-utils": "^7.16.7" - } - }, - "@babel/plugin-proposal-private-property-in-object": { - "version": "7.16.7", - "resolved": "https://registry.npmjs.org/@babel/plugin-proposal-private-property-in-object/-/plugin-proposal-private-property-in-object-7.16.7.tgz", - "integrity": "sha512-rMQkjcOFbm+ufe3bTZLyOfsOUOxyvLXZJCTARhJr+8UMSoZmqTe1K1BgkFcrW37rAchWg57yI69ORxiWvUINuQ==", - "requires": { - "@babel/helper-annotate-as-pure": "^7.16.7", - "@babel/helper-create-class-features-plugin": "^7.16.7", - "@babel/helper-plugin-utils": "^7.16.7", - "@babel/plugin-syntax-private-property-in-object": "^7.14.5" - } - }, - "@babel/plugin-proposal-unicode-property-regex": { - "version": "7.16.7", - "resolved": "https://registry.npmjs.org/@babel/plugin-proposal-unicode-property-regex/-/plugin-proposal-unicode-property-regex-7.16.7.tgz", - "integrity": "sha512-QRK0YI/40VLhNVGIjRNAAQkEHws0cswSdFFjpFyt943YmJIU1da9uW63Iu6NFV6CxTZW5eTDCrwZUstBWgp/Rg==", - "requires": { - "@babel/helper-create-regexp-features-plugin": "^7.16.7", - "@babel/helper-plugin-utils": "^7.16.7" - } - }, - "@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==", - "requires": { - "@babel/helper-plugin-utils": "^7.8.0" - } - }, - "@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==", - "requires": { - "@babel/helper-plugin-utils": "^7.12.13" - } - }, - "@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==", - "requires": { - "@babel/helper-plugin-utils": "^7.14.5" - } - }, - "@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==", - "requires": { - "@babel/helper-plugin-utils": "^7.8.0" - } - }, - "@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==", - "requires": { - "@babel/helper-plugin-utils": "^7.8.3" - } - }, - "@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==", - "requires": { - "@babel/helper-plugin-utils": "^7.8.0" - } - }, - "@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==", - "requires": { - "@babel/helper-plugin-utils": "^7.10.4" - } - }, - "@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==", - "requires": { - "@babel/helper-plugin-utils": "^7.8.0" - } - }, - "@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==", - "requires": { - "@babel/helper-plugin-utils": "^7.10.4" - } - }, - "@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==", - "requires": { - "@babel/helper-plugin-utils": "^7.8.0" - } - }, - "@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==", - "requires": { - "@babel/helper-plugin-utils": "^7.8.0" - } - }, - "@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==", - "requires": { - "@babel/helper-plugin-utils": "^7.8.0" - } - }, - "@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==", - "requires": { - "@babel/helper-plugin-utils": "^7.14.5" - } - }, - "@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==", - "requires": { - "@babel/helper-plugin-utils": "^7.14.5" - } - }, - "@babel/plugin-transform-arrow-functions": { - "version": "7.16.7", - "resolved": "https://registry.npmjs.org/@babel/plugin-transform-arrow-functions/-/plugin-transform-arrow-functions-7.16.7.tgz", - "integrity": "sha512-9ffkFFMbvzTvv+7dTp/66xvZAWASuPD5Tl9LK3Z9vhOmANo6j94rik+5YMBt4CwHVMWLWpMsriIc2zsa3WW3xQ==", - "requires": { - "@babel/helper-plugin-utils": "^7.16.7" - } - }, - "@babel/plugin-transform-async-to-generator": { - "version": "7.16.7", - "resolved": "https://registry.npmjs.org/@babel/plugin-transform-async-to-generator/-/plugin-transform-async-to-generator-7.16.7.tgz", - "integrity": "sha512-pFEfjnK4DfXCfAlA5I98BYdDJD8NltMzx19gt6DAmfE+2lXRfPUoa0/5SUjT4+TDE1W/rcxU/1lgN55vpAjjdg==", - "requires": { - "@babel/helper-module-imports": "^7.16.7", - "@babel/helper-plugin-utils": "^7.16.7", - "@babel/helper-remap-async-to-generator": "^7.16.7" - } - }, - "@babel/plugin-transform-block-scoped-functions": { - "version": "7.16.7", - "resolved": "https://registry.npmjs.org/@babel/plugin-transform-block-scoped-functions/-/plugin-transform-block-scoped-functions-7.16.7.tgz", - "integrity": "sha512-JUuzlzmF40Z9cXyytcbZEZKckgrQzChbQJw/5PuEHYeqzCsvebDx0K0jWnIIVcmmDOAVctCgnYs0pMcrYj2zJg==", - "requires": { - "@babel/helper-plugin-utils": "^7.16.7" - } - }, - "@babel/plugin-transform-block-scoping": { - "version": "7.16.7", - "resolved": "https://registry.npmjs.org/@babel/plugin-transform-block-scoping/-/plugin-transform-block-scoping-7.16.7.tgz", - "integrity": "sha512-ObZev2nxVAYA4bhyusELdo9hb3H+A56bxH3FZMbEImZFiEDYVHXQSJ1hQKFlDnlt8G9bBrCZ5ZpURZUrV4G5qQ==", - "requires": { - "@babel/helper-plugin-utils": "^7.16.7" - } - }, - "@babel/plugin-transform-classes": { - "version": "7.16.7", - "resolved": "https://registry.npmjs.org/@babel/plugin-transform-classes/-/plugin-transform-classes-7.16.7.tgz", - "integrity": "sha512-WY7og38SFAGYRe64BrjKf8OrE6ulEHtr5jEYaZMwox9KebgqPi67Zqz8K53EKk1fFEJgm96r32rkKZ3qA2nCWQ==", - "requires": { - "@babel/helper-annotate-as-pure": "^7.16.7", - "@babel/helper-environment-visitor": "^7.16.7", - "@babel/helper-function-name": "^7.16.7", - "@babel/helper-optimise-call-expression": "^7.16.7", - "@babel/helper-plugin-utils": "^7.16.7", - "@babel/helper-replace-supers": "^7.16.7", - "@babel/helper-split-export-declaration": "^7.16.7", - "globals": "^11.1.0" - }, - "dependencies": { - "globals": { - "version": "11.12.0", - "resolved": "https://registry.npmjs.org/globals/-/globals-11.12.0.tgz", - "integrity": "sha512-WOBp/EEGUiIsJSp7wcv/y6MO+lV9UoncWqxuFfm8eBwzWNgyfBd6Gz+IeKQ9jCmyhoH99g15M3T+QaVHFjizVA==" - } - } - }, - "@babel/plugin-transform-computed-properties": { - "version": "7.16.7", - "resolved": "https://registry.npmjs.org/@babel/plugin-transform-computed-properties/-/plugin-transform-computed-properties-7.16.7.tgz", - "integrity": "sha512-gN72G9bcmenVILj//sv1zLNaPyYcOzUho2lIJBMh/iakJ9ygCo/hEF9cpGb61SCMEDxbbyBoVQxrt+bWKu5KGw==", - "requires": { - "@babel/helper-plugin-utils": "^7.16.7" - } - }, - "@babel/plugin-transform-destructuring": { - "version": "7.16.7", - "resolved": "https://registry.npmjs.org/@babel/plugin-transform-destructuring/-/plugin-transform-destructuring-7.16.7.tgz", - "integrity": "sha512-VqAwhTHBnu5xBVDCvrvqJbtLUa++qZaWC0Fgr2mqokBlulZARGyIvZDoqbPlPaKImQ9dKAcCzbv+ul//uqu70A==", - "requires": { - "@babel/helper-plugin-utils": "^7.16.7" - } - }, - "@babel/plugin-transform-dotall-regex": { - "version": "7.16.7", - "resolved": "https://registry.npmjs.org/@babel/plugin-transform-dotall-regex/-/plugin-transform-dotall-regex-7.16.7.tgz", - "integrity": "sha512-Lyttaao2SjZF6Pf4vk1dVKv8YypMpomAbygW+mU5cYP3S5cWTfCJjG8xV6CFdzGFlfWK81IjL9viiTvpb6G7gQ==", - "requires": { - "@babel/helper-create-regexp-features-plugin": "^7.16.7", - "@babel/helper-plugin-utils": "^7.16.7" - } - }, - "@babel/plugin-transform-duplicate-keys": { - "version": "7.16.7", - "resolved": "https://registry.npmjs.org/@babel/plugin-transform-duplicate-keys/-/plugin-transform-duplicate-keys-7.16.7.tgz", - "integrity": "sha512-03DvpbRfvWIXyK0/6QiR1KMTWeT6OcQ7tbhjrXyFS02kjuX/mu5Bvnh5SDSWHxyawit2g5aWhKwI86EE7GUnTw==", - "requires": { - "@babel/helper-plugin-utils": "^7.16.7" - } - }, - "@babel/plugin-transform-exponentiation-operator": { - "version": "7.16.7", - "resolved": "https://registry.npmjs.org/@babel/plugin-transform-exponentiation-operator/-/plugin-transform-exponentiation-operator-7.16.7.tgz", - "integrity": "sha512-8UYLSlyLgRixQvlYH3J2ekXFHDFLQutdy7FfFAMm3CPZ6q9wHCwnUyiXpQCe3gVVnQlHc5nsuiEVziteRNTXEA==", - "requires": { - "@babel/helper-builder-binary-assignment-operator-visitor": "^7.16.7", - "@babel/helper-plugin-utils": "^7.16.7" - } - }, - "@babel/plugin-transform-for-of": { - "version": "7.16.7", - "resolved": "https://registry.npmjs.org/@babel/plugin-transform-for-of/-/plugin-transform-for-of-7.16.7.tgz", - "integrity": "sha512-/QZm9W92Ptpw7sjI9Nx1mbcsWz33+l8kuMIQnDwgQBG5s3fAfQvkRjQ7NqXhtNcKOnPkdICmUHyCaWW06HCsqg==", - "requires": { - "@babel/helper-plugin-utils": "^7.16.7" - } - }, - "@babel/plugin-transform-function-name": { - "version": "7.16.7", - "resolved": "https://registry.npmjs.org/@babel/plugin-transform-function-name/-/plugin-transform-function-name-7.16.7.tgz", - "integrity": "sha512-SU/C68YVwTRxqWj5kgsbKINakGag0KTgq9f2iZEXdStoAbOzLHEBRYzImmA6yFo8YZhJVflvXmIHUO7GWHmxxA==", - "requires": { - "@babel/helper-compilation-targets": "^7.16.7", - "@babel/helper-function-name": "^7.16.7", - "@babel/helper-plugin-utils": "^7.16.7" - } - }, - "@babel/plugin-transform-literals": { - "version": "7.16.7", - "resolved": "https://registry.npmjs.org/@babel/plugin-transform-literals/-/plugin-transform-literals-7.16.7.tgz", - "integrity": "sha512-6tH8RTpTWI0s2sV6uq3e/C9wPo4PTqqZps4uF0kzQ9/xPLFQtipynvmT1g/dOfEJ+0EQsHhkQ/zyRId8J2b8zQ==", - "requires": { - "@babel/helper-plugin-utils": "^7.16.7" - } - }, - "@babel/plugin-transform-member-expression-literals": { - "version": "7.16.7", - "resolved": "https://registry.npmjs.org/@babel/plugin-transform-member-expression-literals/-/plugin-transform-member-expression-literals-7.16.7.tgz", - "integrity": "sha512-mBruRMbktKQwbxaJof32LT9KLy2f3gH+27a5XSuXo6h7R3vqltl0PgZ80C8ZMKw98Bf8bqt6BEVi3svOh2PzMw==", - "requires": { - "@babel/helper-plugin-utils": "^7.16.7" - } - }, - "@babel/plugin-transform-modules-amd": { - "version": "7.16.7", - "resolved": "https://registry.npmjs.org/@babel/plugin-transform-modules-amd/-/plugin-transform-modules-amd-7.16.7.tgz", - "integrity": "sha512-KaaEtgBL7FKYwjJ/teH63oAmE3lP34N3kshz8mm4VMAw7U3PxjVwwUmxEFksbgsNUaO3wId9R2AVQYSEGRa2+g==", - "requires": { - "@babel/helper-module-transforms": "^7.16.7", - "@babel/helper-plugin-utils": "^7.16.7", - "babel-plugin-dynamic-import-node": "^2.3.3" - } - }, - "@babel/plugin-transform-modules-commonjs": { - "version": "7.16.7", - "resolved": "https://registry.npmjs.org/@babel/plugin-transform-modules-commonjs/-/plugin-transform-modules-commonjs-7.16.7.tgz", - "integrity": "sha512-h2RP2kE7He1ZWKyAlanMZrAbdv+Acw1pA8dQZhE025WJZE2z0xzFADAinXA9fxd5bn7JnM+SdOGcndGx1ARs9w==", - "requires": { - "@babel/helper-module-transforms": "^7.16.7", - "@babel/helper-plugin-utils": "^7.16.7", - "@babel/helper-simple-access": "^7.16.7", - "babel-plugin-dynamic-import-node": "^2.3.3" - } - }, - "@babel/plugin-transform-modules-systemjs": { - "version": "7.16.7", - "resolved": "https://registry.npmjs.org/@babel/plugin-transform-modules-systemjs/-/plugin-transform-modules-systemjs-7.16.7.tgz", - "integrity": "sha512-DuK5E3k+QQmnOqBR9UkusByy5WZWGRxfzV529s9nPra1GE7olmxfqO2FHobEOYSPIjPBTr4p66YDcjQnt8cBmw==", - "requires": { - "@babel/helper-hoist-variables": "^7.16.7", - "@babel/helper-module-transforms": "^7.16.7", - "@babel/helper-plugin-utils": "^7.16.7", - "@babel/helper-validator-identifier": "^7.16.7", - "babel-plugin-dynamic-import-node": "^2.3.3" - } - }, - "@babel/plugin-transform-modules-umd": { - "version": "7.16.7", - "resolved": "https://registry.npmjs.org/@babel/plugin-transform-modules-umd/-/plugin-transform-modules-umd-7.16.7.tgz", - "integrity": "sha512-EMh7uolsC8O4xhudF2F6wedbSHm1HHZ0C6aJ7K67zcDNidMzVcxWdGr+htW9n21klm+bOn+Rx4CBsAntZd3rEQ==", - "requires": { - "@babel/helper-module-transforms": "^7.16.7", - "@babel/helper-plugin-utils": "^7.16.7" - } - }, - "@babel/plugin-transform-named-capturing-groups-regex": { - "version": "7.16.7", - "resolved": "https://registry.npmjs.org/@babel/plugin-transform-named-capturing-groups-regex/-/plugin-transform-named-capturing-groups-regex-7.16.7.tgz", - "integrity": "sha512-kFy35VwmwIQwCjwrAQhl3+c/kr292i4KdLPKp5lPH03Ltc51qnFlIADoyPxc/6Naz3ok3WdYKg+KK6AH+D4utg==", - "requires": { - "@babel/helper-create-regexp-features-plugin": "^7.16.7" - } - }, - "@babel/plugin-transform-new-target": { - "version": "7.16.7", - "resolved": "https://registry.npmjs.org/@babel/plugin-transform-new-target/-/plugin-transform-new-target-7.16.7.tgz", - "integrity": "sha512-xiLDzWNMfKoGOpc6t3U+etCE2yRnn3SM09BXqWPIZOBpL2gvVrBWUKnsJx0K/ADi5F5YC5f8APFfWrz25TdlGg==", - "requires": { - "@babel/helper-plugin-utils": "^7.16.7" - } - }, - "@babel/plugin-transform-object-super": { - "version": "7.16.7", - "resolved": "https://registry.npmjs.org/@babel/plugin-transform-object-super/-/plugin-transform-object-super-7.16.7.tgz", - "integrity": "sha512-14J1feiQVWaGvRxj2WjyMuXS2jsBkgB3MdSN5HuC2G5nRspa5RK9COcs82Pwy5BuGcjb+fYaUj94mYcOj7rCvw==", - "requires": { - "@babel/helper-plugin-utils": "^7.16.7", - "@babel/helper-replace-supers": "^7.16.7" - } - }, - "@babel/plugin-transform-parameters": { - "version": "7.16.7", - "resolved": "https://registry.npmjs.org/@babel/plugin-transform-parameters/-/plugin-transform-parameters-7.16.7.tgz", - "integrity": "sha512-AT3MufQ7zZEhU2hwOA11axBnExW0Lszu4RL/tAlUJBuNoRak+wehQW8h6KcXOcgjY42fHtDxswuMhMjFEuv/aw==", - "requires": { - "@babel/helper-plugin-utils": "^7.16.7" - } - }, - "@babel/plugin-transform-property-literals": { - "version": "7.16.7", - "resolved": "https://registry.npmjs.org/@babel/plugin-transform-property-literals/-/plugin-transform-property-literals-7.16.7.tgz", - "integrity": "sha512-z4FGr9NMGdoIl1RqavCqGG+ZuYjfZ/hkCIeuH6Do7tXmSm0ls11nYVSJqFEUOSJbDab5wC6lRE/w6YjVcr6Hqw==", - "requires": { - "@babel/helper-plugin-utils": "^7.16.7" - } - }, - "@babel/plugin-transform-regenerator": { - "version": "7.16.7", - "resolved": "https://registry.npmjs.org/@babel/plugin-transform-regenerator/-/plugin-transform-regenerator-7.16.7.tgz", - "integrity": "sha512-mF7jOgGYCkSJagJ6XCujSQg+6xC1M77/03K2oBmVJWoFGNUtnVJO4WHKJk3dnPC8HCcj4xBQP1Egm8DWh3Pb3Q==", - "requires": { - "regenerator-transform": "^0.14.2" - } - }, - "@babel/plugin-transform-reserved-words": { - "version": "7.16.7", - "resolved": "https://registry.npmjs.org/@babel/plugin-transform-reserved-words/-/plugin-transform-reserved-words-7.16.7.tgz", - "integrity": "sha512-KQzzDnZ9hWQBjwi5lpY5v9shmm6IVG0U9pB18zvMu2i4H90xpT4gmqwPYsn8rObiadYe2M0gmgsiOIF5A/2rtg==", - "requires": { - "@babel/helper-plugin-utils": "^7.16.7" - } - }, - "@babel/plugin-transform-shorthand-properties": { - "version": "7.16.7", - "resolved": "https://registry.npmjs.org/@babel/plugin-transform-shorthand-properties/-/plugin-transform-shorthand-properties-7.16.7.tgz", - "integrity": "sha512-hah2+FEnoRoATdIb05IOXf+4GzXYTq75TVhIn1PewihbpyrNWUt2JbudKQOETWw6QpLe+AIUpJ5MVLYTQbeeUg==", - "requires": { - "@babel/helper-plugin-utils": "^7.16.7" - } - }, - "@babel/plugin-transform-spread": { - "version": "7.16.7", - "resolved": "https://registry.npmjs.org/@babel/plugin-transform-spread/-/plugin-transform-spread-7.16.7.tgz", - "integrity": "sha512-+pjJpgAngb53L0iaA5gU/1MLXJIfXcYepLgXB3esVRf4fqmj8f2cxM3/FKaHsZms08hFQJkFccEWuIpm429TXg==", - "requires": { - "@babel/helper-plugin-utils": "^7.16.7", - "@babel/helper-skip-transparent-expression-wrappers": "^7.16.0" - } - }, - "@babel/plugin-transform-sticky-regex": { - "version": "7.16.7", - "resolved": "https://registry.npmjs.org/@babel/plugin-transform-sticky-regex/-/plugin-transform-sticky-regex-7.16.7.tgz", - "integrity": "sha512-NJa0Bd/87QV5NZZzTuZG5BPJjLYadeSZ9fO6oOUoL4iQx+9EEuw/eEM92SrsT19Yc2jgB1u1hsjqDtH02c3Drw==", - "requires": { - "@babel/helper-plugin-utils": "^7.16.7" - } - }, - "@babel/plugin-transform-template-literals": { - "version": "7.16.7", - "resolved": "https://registry.npmjs.org/@babel/plugin-transform-template-literals/-/plugin-transform-template-literals-7.16.7.tgz", - "integrity": "sha512-VwbkDDUeenlIjmfNeDX/V0aWrQH2QiVyJtwymVQSzItFDTpxfyJh3EVaQiS0rIN/CqbLGr0VcGmuwyTdZtdIsA==", - "requires": { - "@babel/helper-plugin-utils": "^7.16.7" - } - }, - "@babel/plugin-transform-typeof-symbol": { - "version": "7.16.7", - "resolved": "https://registry.npmjs.org/@babel/plugin-transform-typeof-symbol/-/plugin-transform-typeof-symbol-7.16.7.tgz", - "integrity": "sha512-p2rOixCKRJzpg9JB4gjnG4gjWkWa89ZoYUnl9snJ1cWIcTH/hvxZqfO+WjG6T8DRBpctEol5jw1O5rA8gkCokQ==", - "requires": { - "@babel/helper-plugin-utils": "^7.16.7" - } - }, - "@babel/plugin-transform-unicode-escapes": { - "version": "7.16.7", - "resolved": "https://registry.npmjs.org/@babel/plugin-transform-unicode-escapes/-/plugin-transform-unicode-escapes-7.16.7.tgz", - "integrity": "sha512-TAV5IGahIz3yZ9/Hfv35TV2xEm+kaBDaZQCn2S/hG9/CZ0DktxJv9eKfPc7yYCvOYR4JGx1h8C+jcSOvgaaI/Q==", - "requires": { - "@babel/helper-plugin-utils": "^7.16.7" - } - }, - "@babel/plugin-transform-unicode-regex": { - "version": "7.16.7", - "resolved": "https://registry.npmjs.org/@babel/plugin-transform-unicode-regex/-/plugin-transform-unicode-regex-7.16.7.tgz", - "integrity": "sha512-oC5tYYKw56HO75KZVLQ+R/Nl3Hro9kf8iG0hXoaHP7tjAyCpvqBiSNe6vGrZni1Z6MggmUOC6A7VP7AVmw225Q==", - "requires": { - "@babel/helper-create-regexp-features-plugin": "^7.16.7", - "@babel/helper-plugin-utils": "^7.16.7" - } - }, - "@babel/preset-env": { - "version": "7.16.7", - "resolved": "https://registry.npmjs.org/@babel/preset-env/-/preset-env-7.16.7.tgz", - "integrity": "sha512-urX3Cee4aOZbRWOSa3mKPk0aqDikfILuo+C7qq7HY0InylGNZ1fekq9jmlr3pLWwZHF4yD7heQooc2Pow2KMyQ==", - "requires": { - "@babel/compat-data": "^7.16.4", - "@babel/helper-compilation-targets": "^7.16.7", - "@babel/helper-plugin-utils": "^7.16.7", - "@babel/helper-validator-option": "^7.16.7", - "@babel/plugin-bugfix-safari-id-destructuring-collision-in-function-expression": "^7.16.7", - "@babel/plugin-bugfix-v8-spread-parameters-in-optional-chaining": "^7.16.7", - "@babel/plugin-proposal-async-generator-functions": "^7.16.7", - "@babel/plugin-proposal-class-properties": "^7.16.7", - "@babel/plugin-proposal-class-static-block": "^7.16.7", - "@babel/plugin-proposal-dynamic-import": "^7.16.7", - "@babel/plugin-proposal-export-namespace-from": "^7.16.7", - "@babel/plugin-proposal-json-strings": "^7.16.7", - "@babel/plugin-proposal-logical-assignment-operators": "^7.16.7", - "@babel/plugin-proposal-nullish-coalescing-operator": "^7.16.7", - "@babel/plugin-proposal-numeric-separator": "^7.16.7", - "@babel/plugin-proposal-object-rest-spread": "^7.16.7", - "@babel/plugin-proposal-optional-catch-binding": "^7.16.7", - "@babel/plugin-proposal-optional-chaining": "^7.16.7", - "@babel/plugin-proposal-private-methods": "^7.16.7", - "@babel/plugin-proposal-private-property-in-object": "^7.16.7", - "@babel/plugin-proposal-unicode-property-regex": "^7.16.7", - "@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-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.16.7", - "@babel/plugin-transform-async-to-generator": "^7.16.7", - "@babel/plugin-transform-block-scoped-functions": "^7.16.7", - "@babel/plugin-transform-block-scoping": "^7.16.7", - "@babel/plugin-transform-classes": "^7.16.7", - "@babel/plugin-transform-computed-properties": "^7.16.7", - "@babel/plugin-transform-destructuring": "^7.16.7", - "@babel/plugin-transform-dotall-regex": "^7.16.7", - "@babel/plugin-transform-duplicate-keys": "^7.16.7", - "@babel/plugin-transform-exponentiation-operator": "^7.16.7", - "@babel/plugin-transform-for-of": "^7.16.7", - "@babel/plugin-transform-function-name": "^7.16.7", - "@babel/plugin-transform-literals": "^7.16.7", - "@babel/plugin-transform-member-expression-literals": "^7.16.7", - "@babel/plugin-transform-modules-amd": "^7.16.7", - "@babel/plugin-transform-modules-commonjs": "^7.16.7", - "@babel/plugin-transform-modules-systemjs": "^7.16.7", - "@babel/plugin-transform-modules-umd": "^7.16.7", - "@babel/plugin-transform-named-capturing-groups-regex": "^7.16.7", - "@babel/plugin-transform-new-target": "^7.16.7", - "@babel/plugin-transform-object-super": "^7.16.7", - "@babel/plugin-transform-parameters": "^7.16.7", - "@babel/plugin-transform-property-literals": "^7.16.7", - "@babel/plugin-transform-regenerator": "^7.16.7", - "@babel/plugin-transform-reserved-words": "^7.16.7", - "@babel/plugin-transform-shorthand-properties": "^7.16.7", - "@babel/plugin-transform-spread": "^7.16.7", - "@babel/plugin-transform-sticky-regex": "^7.16.7", - "@babel/plugin-transform-template-literals": "^7.16.7", - "@babel/plugin-transform-typeof-symbol": "^7.16.7", - "@babel/plugin-transform-unicode-escapes": "^7.16.7", - "@babel/plugin-transform-unicode-regex": "^7.16.7", - "@babel/preset-modules": "^0.1.5", - "@babel/types": "^7.16.7", - "babel-plugin-polyfill-corejs2": "^0.3.0", - "babel-plugin-polyfill-corejs3": "^0.4.0", - "babel-plugin-polyfill-regenerator": "^0.3.0", - "core-js-compat": "^3.19.1", - "semver": "^6.3.0" - }, - "dependencies": { - "semver": { - "version": "6.3.0", - "resolved": "https://registry.npmjs.org/semver/-/semver-6.3.0.tgz", - "integrity": "sha512-b39TBaTSfV6yBrapU89p5fKekE2m/NwnDocOVruQFS1/veMgdzuPcnOM34M6CwxW8jH/lxEa5rBoDeUwu5HHTw==" - } - } - }, - "@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==", - "requires": { - "@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" - } - }, - "@babel/runtime": { - "version": "7.16.7", - "resolved": "https://registry.npmjs.org/@babel/runtime/-/runtime-7.16.7.tgz", - "integrity": "sha512-9E9FJowqAsytyOY6LG+1KuueckRL+aQW+mKvXRXnuFGyRAyepJPmEo9vgMfXUA6O9u3IeEdv9MAkppFcaQwogQ==", - "requires": { - "regenerator-runtime": "^0.13.4" - }, - "dependencies": { - "regenerator-runtime": { - "version": "0.13.9", - "resolved": "https://registry.npmjs.org/regenerator-runtime/-/regenerator-runtime-0.13.9.tgz", - "integrity": "sha512-p3VT+cOEgxFsRRA9X4lkI1E+k2/CtnKtU4gcxyaCUreilL/vqI6CdZ3wxVUx3UOUg+gnUOQQcRI7BmSI656MYA==" - } - } - }, - "@babel/template": { - "version": "7.16.7", - "resolved": "https://registry.npmjs.org/@babel/template/-/template-7.16.7.tgz", - "integrity": "sha512-I8j/x8kHUrbYRTUxXrrMbfCa7jxkE7tZre39x3kjr9hvI82cK1FfqLygotcWN5kdPGWcLdWMHpSBavse5tWw3w==", - "requires": { - "@babel/code-frame": "^7.16.7", - "@babel/parser": "^7.16.7", - "@babel/types": "^7.16.7" - } - }, - "@babel/traverse": { - "version": "7.16.7", - "resolved": "https://registry.npmjs.org/@babel/traverse/-/traverse-7.16.7.tgz", - "integrity": "sha512-8KWJPIb8c2VvY8AJrydh6+fVRo2ODx1wYBU2398xJVq0JomuLBZmVQzLPBblJgHIGYG4znCpUZUZ0Pt2vdmVYQ==", - "requires": { - "@babel/code-frame": "^7.16.7", - "@babel/generator": "^7.16.7", - "@babel/helper-environment-visitor": "^7.16.7", - "@babel/helper-function-name": "^7.16.7", - "@babel/helper-hoist-variables": "^7.16.7", - "@babel/helper-split-export-declaration": "^7.16.7", - "@babel/parser": "^7.16.7", - "@babel/types": "^7.16.7", - "debug": "^4.1.0", - "globals": "^11.1.0" - }, - "dependencies": { - "globals": { - "version": "11.12.0", - "resolved": "https://registry.npmjs.org/globals/-/globals-11.12.0.tgz", - "integrity": "sha512-WOBp/EEGUiIsJSp7wcv/y6MO+lV9UoncWqxuFfm8eBwzWNgyfBd6Gz+IeKQ9jCmyhoH99g15M3T+QaVHFjizVA==" - } - } - }, - "@babel/types": { - "version": "7.16.7", - "resolved": "https://registry.npmjs.org/@babel/types/-/types-7.16.7.tgz", - "integrity": "sha512-E8HuV7FO9qLpx6OtoGfUQ2cjIYnbFwvZWYBS+87EwtdMvmUPJSwykpovFB+8insbpF0uJcpr8KMUi64XZntZcg==", - "requires": { - "@babel/helper-validator-identifier": "^7.16.7", - "to-fast-properties": "^2.0.0" - } - }, - "@cspotcode/source-map-consumer": { - "version": "0.8.0", - "resolved": "https://registry.npmjs.org/@cspotcode/source-map-consumer/-/source-map-consumer-0.8.0.tgz", - "integrity": "sha512-41qniHzTU8yAGbCp04ohlmSrZf8bkf/iJsl3V0dRGsQN/5GFfx+LbCSsCpp2gqrqjTVg/K6O8ycoV35JIwAzAg==" - }, - "@cspotcode/source-map-support": { - "version": "0.7.0", - "resolved": "https://registry.npmjs.org/@cspotcode/source-map-support/-/source-map-support-0.7.0.tgz", - "integrity": "sha512-X4xqRHqN8ACt2aHVe51OxeA2HjbcL4MqFqXkrmQszJ1NOUuUu5u6Vqx/0lZSVNku7velL5FC/s5uEAj1lsBMhA==", - "requires": { - "@cspotcode/source-map-consumer": "0.8.0" - } - }, - "@discoveryjs/json-ext": { - "version": "0.5.6", - "resolved": "https://registry.npmjs.org/@discoveryjs/json-ext/-/json-ext-0.5.6.tgz", - "integrity": "sha512-ws57AidsDvREKrZKYffXddNkyaF14iHNHm8VQnZH6t99E8gczjNN0GpvcGny0imC80yQ0tHz1xVUKk/KFQSUyA==" - }, - "@eslint/eslintrc": { - "version": "1.0.5", - "resolved": "https://registry.npmjs.org/@eslint/eslintrc/-/eslintrc-1.0.5.tgz", - "integrity": "sha512-BLxsnmK3KyPunz5wmCCpqy0YelEoxxGmH73Is+Z74oOTMtExcjkr3dDR6quwrjh1YspA8DH9gnX1o069KiS9AQ==", - "dev": true, - "requires": { - "ajv": "^6.12.4", - "debug": "^4.3.2", - "espree": "^9.2.0", - "globals": "^13.9.0", - "ignore": "^4.0.6", - "import-fresh": "^3.2.1", - "js-yaml": "^4.1.0", - "minimatch": "^3.0.4", - "strip-json-comments": "^3.1.1" - }, - "dependencies": { - "ajv": { - "version": "6.12.6", - "resolved": "https://registry.npmjs.org/ajv/-/ajv-6.12.6.tgz", - "integrity": "sha512-j3fVLgvTo527anyYyJOGTYJbG+vnnQYvE0m5mmkc1TK+nxAppkCLMIL0aZ4dblVCNoGShhm+kzE4ZUykBoMg4g==", - "dev": true, - "requires": { - "fast-deep-equal": "^3.1.1", - "fast-json-stable-stringify": "^2.0.0", - "json-schema-traverse": "^0.4.1", - "uri-js": "^4.2.2" - } - }, - "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 - }, - "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 - } - } - }, - "@feathersjs/hooks": { - "version": "0.6.5", - "resolved": "https://registry.npmjs.org/@feathersjs/hooks/-/hooks-0.6.5.tgz", - "integrity": "sha512-WtcEoG/imdHRvC3vofGi/OcgH+cjHHhO0AfEeTlsnrKLjVKKBXV6aoIrB2nHZPpE7iW5sA7AZMR6bPD8ytxN+w==" - }, - "@gar/promisify": { - "version": "1.1.2", - "resolved": "https://registry.npmjs.org/@gar/promisify/-/promisify-1.1.2.tgz", - "integrity": "sha512-82cpyJyKRoQoRi+14ibCeGPu0CwypgtBAdBhq1WfvagpCZNKqwXbKwXllYSMG91DhmG4jt9gN8eP6lGOtozuaw==", - "dev": true - }, - "@humanwhocodes/config-array": { - "version": "0.9.2", - "resolved": "https://registry.npmjs.org/@humanwhocodes/config-array/-/config-array-0.9.2.tgz", - "integrity": "sha512-UXOuFCGcwciWckOpmfKDq/GyhlTf9pN/BzG//x8p8zTOFEcGuA68ANXheFS0AGvy3qgZqLBUkMs7hqzqCKOVwA==", - "dev": true, - "requires": { - "@humanwhocodes/object-schema": "^1.2.1", - "debug": "^4.1.1", - "minimatch": "^3.0.4" - } - }, - "@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 - }, - "@hutson/parse-repository-url": { - "version": "3.0.2", - "resolved": "https://registry.npmjs.org/@hutson/parse-repository-url/-/parse-repository-url-3.0.2.tgz", - "integrity": "sha512-H9XAx3hc0BQHY6l+IFSWHDySypcXsvsuLhgYLUGywmJ5pswRVQJUHpOsobnLYp2ZUaUlKiKDrgWWhosOwAEM8Q==", - "dev": true - }, - "@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, - "requires": { - "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" - }, - "dependencies": { - "argparse": { - "version": "1.0.10", - "resolved": "https://registry.npmjs.org/argparse/-/argparse-1.0.10.tgz", - "integrity": "sha512-o5Roy6tNG4SL/FOkCAN6RzjiakZS25RLYFrcMttJqbdd8BWrnA+fGz57iN5Pb06pvBGvl5gQ0B48dJlslXvoTg==", - "dev": true, - "requires": { - "sprintf-js": "~1.0.2" - } - }, - "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, - "requires": { - "locate-path": "^5.0.0", - "path-exists": "^4.0.0" - } - }, - "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, - "requires": { - "argparse": "^1.0.7", - "esprima": "^4.0.0" - } - }, - "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, - "requires": { - "p-locate": "^4.1.0" - } - }, - "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, - "requires": { - "p-try": "^2.0.0" - } - }, - "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, - "requires": { - "p-limit": "^2.2.0" - } - }, - "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 - }, - "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 - } - } - }, - "@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 - }, - "@lerna/add": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/@lerna/add/-/add-4.0.0.tgz", - "integrity": "sha512-cpmAH1iS3k8JBxNvnMqrGTTjbY/ZAiKa1ChJzFevMYY3eeqbvhsBKnBcxjRXtdrJ6bd3dCQM+ZtK+0i682Fhng==", - "dev": true, - "requires": { - "@lerna/bootstrap": "4.0.0", - "@lerna/command": "4.0.0", - "@lerna/filter-options": "4.0.0", - "@lerna/npm-conf": "4.0.0", - "@lerna/validation-error": "4.0.0", - "dedent": "^0.7.0", - "npm-package-arg": "^8.1.0", - "p-map": "^4.0.0", - "pacote": "^11.2.6", - "semver": "^7.3.4" - } - }, - "@lerna/bootstrap": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/@lerna/bootstrap/-/bootstrap-4.0.0.tgz", - "integrity": "sha512-RkS7UbeM2vu+kJnHzxNRCLvoOP9yGNgkzRdy4UV2hNalD7EP41bLvRVOwRYQ7fhc2QcbhnKNdOBihYRL0LcKtw==", - "dev": true, - "requires": { - "@lerna/command": "4.0.0", - "@lerna/filter-options": "4.0.0", - "@lerna/has-npm-version": "4.0.0", - "@lerna/npm-install": "4.0.0", - "@lerna/package-graph": "4.0.0", - "@lerna/pulse-till-done": "4.0.0", - "@lerna/rimraf-dir": "4.0.0", - "@lerna/run-lifecycle": "4.0.0", - "@lerna/run-topologically": "4.0.0", - "@lerna/symlink-binary": "4.0.0", - "@lerna/symlink-dependencies": "4.0.0", - "@lerna/validation-error": "4.0.0", - "dedent": "^0.7.0", - "get-port": "^5.1.1", - "multimatch": "^5.0.0", - "npm-package-arg": "^8.1.0", - "npmlog": "^4.1.2", - "p-map": "^4.0.0", - "p-map-series": "^2.1.0", - "p-waterfall": "^2.1.1", - "read-package-tree": "^5.3.1", - "semver": "^7.3.4" - } - }, - "@lerna/changed": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/@lerna/changed/-/changed-4.0.0.tgz", - "integrity": "sha512-cD+KuPRp6qiPOD+BO6S6SN5cARspIaWSOqGBpGnYzLb4uWT8Vk4JzKyYtc8ym1DIwyoFXHosXt8+GDAgR8QrgQ==", - "dev": true, - "requires": { - "@lerna/collect-updates": "4.0.0", - "@lerna/command": "4.0.0", - "@lerna/listable": "4.0.0", - "@lerna/output": "4.0.0" - } - }, - "@lerna/check-working-tree": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/@lerna/check-working-tree/-/check-working-tree-4.0.0.tgz", - "integrity": "sha512-/++bxM43jYJCshBiKP5cRlCTwSJdRSxVmcDAXM+1oUewlZJVSVlnks5eO0uLxokVFvLhHlC5kHMc7gbVFPHv6Q==", - "dev": true, - "requires": { - "@lerna/collect-uncommitted": "4.0.0", - "@lerna/describe-ref": "4.0.0", - "@lerna/validation-error": "4.0.0" - } - }, - "@lerna/child-process": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/@lerna/child-process/-/child-process-4.0.0.tgz", - "integrity": "sha512-XtCnmCT9eyVsUUHx6y/CTBYdV9g2Cr/VxyseTWBgfIur92/YKClfEtJTbOh94jRT62hlKLqSvux/UhxXVh613Q==", - "dev": true, - "requires": { - "chalk": "^4.1.0", - "execa": "^5.0.0", - "strong-log-transformer": "^2.1.0" - } - }, - "@lerna/clean": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/@lerna/clean/-/clean-4.0.0.tgz", - "integrity": "sha512-uugG2iN9k45ITx2jtd8nEOoAtca8hNlDCUM0N3lFgU/b1mEQYAPRkqr1qs4FLRl/Y50ZJ41wUz1eazS+d/0osA==", - "dev": true, - "requires": { - "@lerna/command": "4.0.0", - "@lerna/filter-options": "4.0.0", - "@lerna/prompt": "4.0.0", - "@lerna/pulse-till-done": "4.0.0", - "@lerna/rimraf-dir": "4.0.0", - "p-map": "^4.0.0", - "p-map-series": "^2.1.0", - "p-waterfall": "^2.1.1" - } - }, - "@lerna/cli": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/@lerna/cli/-/cli-4.0.0.tgz", - "integrity": "sha512-Neaw3GzFrwZiRZv2g7g6NwFjs3er1vhraIniEs0jjVLPMNC4eata0na3GfE5yibkM/9d3gZdmihhZdZ3EBdvYA==", - "dev": true, - "requires": { - "@lerna/global-options": "4.0.0", - "dedent": "^0.7.0", - "npmlog": "^4.1.2", - "yargs": "^16.2.0" - } - }, - "@lerna/collect-uncommitted": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/@lerna/collect-uncommitted/-/collect-uncommitted-4.0.0.tgz", - "integrity": "sha512-ufSTfHZzbx69YNj7KXQ3o66V4RC76ffOjwLX0q/ab//61bObJ41n03SiQEhSlmpP+gmFbTJ3/7pTe04AHX9m/g==", - "dev": true, - "requires": { - "@lerna/child-process": "4.0.0", - "chalk": "^4.1.0", - "npmlog": "^4.1.2" - } - }, - "@lerna/collect-updates": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/@lerna/collect-updates/-/collect-updates-4.0.0.tgz", - "integrity": "sha512-bnNGpaj4zuxsEkyaCZLka9s7nMs58uZoxrRIPJ+nrmrZYp1V5rrd+7/NYTuunOhY2ug1sTBvTAxj3NZQ+JKnOw==", - "dev": true, - "requires": { - "@lerna/child-process": "4.0.0", - "@lerna/describe-ref": "4.0.0", - "minimatch": "^3.0.4", - "npmlog": "^4.1.2", - "slash": "^3.0.0" - } - }, - "@lerna/command": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/@lerna/command/-/command-4.0.0.tgz", - "integrity": "sha512-LM9g3rt5FsPNFqIHUeRwWXLNHJ5NKzOwmVKZ8anSp4e1SPrv2HNc1V02/9QyDDZK/w+5POXH5lxZUI1CHaOK/A==", - "dev": true, - "requires": { - "@lerna/child-process": "4.0.0", - "@lerna/package-graph": "4.0.0", - "@lerna/project": "4.0.0", - "@lerna/validation-error": "4.0.0", - "@lerna/write-log-file": "4.0.0", - "clone-deep": "^4.0.1", - "dedent": "^0.7.0", - "execa": "^5.0.0", - "is-ci": "^2.0.0", - "npmlog": "^4.1.2" - } - }, - "@lerna/conventional-commits": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/@lerna/conventional-commits/-/conventional-commits-4.0.0.tgz", - "integrity": "sha512-CSUQRjJHFrH8eBn7+wegZLV3OrNc0Y1FehYfYGhjLE2SIfpCL4bmfu/ViYuHh9YjwHaA+4SX6d3hR+xkeseKmw==", - "dev": true, - "requires": { - "@lerna/validation-error": "4.0.0", - "conventional-changelog-angular": "^5.0.12", - "conventional-changelog-core": "^4.2.2", - "conventional-recommended-bump": "^6.1.0", - "fs-extra": "^9.1.0", - "get-stream": "^6.0.0", - "lodash.template": "^4.5.0", - "npm-package-arg": "^8.1.0", - "npmlog": "^4.1.2", - "pify": "^5.0.0", - "semver": "^7.3.4" - } - }, - "@lerna/create": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/@lerna/create/-/create-4.0.0.tgz", - "integrity": "sha512-mVOB1niKByEUfxlbKTM1UNECWAjwUdiioIbRQZEeEabtjCL69r9rscIsjlGyhGWCfsdAG5wfq4t47nlDXdLLag==", - "dev": true, - "requires": { - "@lerna/child-process": "4.0.0", - "@lerna/command": "4.0.0", - "@lerna/npm-conf": "4.0.0", - "@lerna/validation-error": "4.0.0", - "dedent": "^0.7.0", - "fs-extra": "^9.1.0", - "globby": "^11.0.2", - "init-package-json": "^2.0.2", - "npm-package-arg": "^8.1.0", - "p-reduce": "^2.1.0", - "pacote": "^11.2.6", - "pify": "^5.0.0", - "semver": "^7.3.4", - "slash": "^3.0.0", - "validate-npm-package-license": "^3.0.4", - "validate-npm-package-name": "^3.0.0", - "whatwg-url": "^8.4.0", - "yargs-parser": "20.2.4" - } - }, - "@lerna/create-symlink": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/@lerna/create-symlink/-/create-symlink-4.0.0.tgz", - "integrity": "sha512-I0phtKJJdafUiDwm7BBlEUOtogmu8+taxq6PtIrxZbllV9hWg59qkpuIsiFp+no7nfRVuaasNYHwNUhDAVQBig==", - "dev": true, - "requires": { - "cmd-shim": "^4.1.0", - "fs-extra": "^9.1.0", - "npmlog": "^4.1.2" - } - }, - "@lerna/describe-ref": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/@lerna/describe-ref/-/describe-ref-4.0.0.tgz", - "integrity": "sha512-eTU5+xC4C5Gcgz+Ey4Qiw9nV2B4JJbMulsYJMW8QjGcGh8zudib7Sduj6urgZXUYNyhYpRs+teci9M2J8u+UvQ==", - "dev": true, - "requires": { - "@lerna/child-process": "4.0.0", - "npmlog": "^4.1.2" - } - }, - "@lerna/diff": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/@lerna/diff/-/diff-4.0.0.tgz", - "integrity": "sha512-jYPKprQVg41+MUMxx6cwtqsNm0Yxx9GDEwdiPLwcUTFx+/qKCEwifKNJ1oGIPBxyEHX2PFCOjkK39lHoj2qiag==", - "dev": true, - "requires": { - "@lerna/child-process": "4.0.0", - "@lerna/command": "4.0.0", - "@lerna/validation-error": "4.0.0", - "npmlog": "^4.1.2" - } - }, - "@lerna/exec": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/@lerna/exec/-/exec-4.0.0.tgz", - "integrity": "sha512-VGXtL/b/JfY84NB98VWZpIExfhLOzy0ozm/0XaS4a2SmkAJc5CeUfrhvHxxkxiTBLkU+iVQUyYEoAT0ulQ8PCw==", - "dev": true, - "requires": { - "@lerna/child-process": "4.0.0", - "@lerna/command": "4.0.0", - "@lerna/filter-options": "4.0.0", - "@lerna/profiler": "4.0.0", - "@lerna/run-topologically": "4.0.0", - "@lerna/validation-error": "4.0.0", - "p-map": "^4.0.0" - } - }, - "@lerna/filter-options": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/@lerna/filter-options/-/filter-options-4.0.0.tgz", - "integrity": "sha512-vV2ANOeZhOqM0rzXnYcFFCJ/kBWy/3OA58irXih9AMTAlQLymWAK0akWybl++sUJ4HB9Hx12TOqaXbYS2NM5uw==", - "dev": true, - "requires": { - "@lerna/collect-updates": "4.0.0", - "@lerna/filter-packages": "4.0.0", - "dedent": "^0.7.0", - "npmlog": "^4.1.2" - } - }, - "@lerna/filter-packages": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/@lerna/filter-packages/-/filter-packages-4.0.0.tgz", - "integrity": "sha512-+4AJIkK7iIiOaqCiVTYJxh/I9qikk4XjNQLhE3kixaqgMuHl1NQ99qXRR0OZqAWB9mh8Z1HA9bM5K1HZLBTOqA==", - "dev": true, - "requires": { - "@lerna/validation-error": "4.0.0", - "multimatch": "^5.0.0", - "npmlog": "^4.1.2" - } - }, - "@lerna/get-npm-exec-opts": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/@lerna/get-npm-exec-opts/-/get-npm-exec-opts-4.0.0.tgz", - "integrity": "sha512-yvmkerU31CTWS2c7DvmAWmZVeclPBqI7gPVr5VATUKNWJ/zmVcU4PqbYoLu92I9Qc4gY1TuUplMNdNuZTSL7IQ==", - "dev": true, - "requires": { - "npmlog": "^4.1.2" - } - }, - "@lerna/get-packed": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/@lerna/get-packed/-/get-packed-4.0.0.tgz", - "integrity": "sha512-rfWONRsEIGyPJTxFzC8ECb3ZbsDXJbfqWYyeeQQDrJRPnEJErlltRLPLgC2QWbxFgFPsoDLeQmFHJnf0iDfd8w==", - "dev": true, - "requires": { - "fs-extra": "^9.1.0", - "ssri": "^8.0.1", - "tar": "^6.1.0" - } - }, - "@lerna/github-client": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/@lerna/github-client/-/github-client-4.0.0.tgz", - "integrity": "sha512-2jhsldZtTKXYUBnOm23Lb0Fx8G4qfSXF9y7UpyUgWUj+YZYd+cFxSuorwQIgk5P4XXrtVhsUesIsli+BYSThiw==", - "dev": true, - "requires": { - "@lerna/child-process": "4.0.0", - "@octokit/plugin-enterprise-rest": "^6.0.1", - "@octokit/rest": "^18.1.0", - "git-url-parse": "^11.4.4", - "npmlog": "^4.1.2" - } - }, - "@lerna/gitlab-client": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/@lerna/gitlab-client/-/gitlab-client-4.0.0.tgz", - "integrity": "sha512-OMUpGSkeDWFf7BxGHlkbb35T7YHqVFCwBPSIR6wRsszY8PAzCYahtH3IaJzEJyUg6vmZsNl0FSr3pdA2skhxqA==", - "dev": true, - "requires": { - "node-fetch": "^2.6.1", - "npmlog": "^4.1.2", - "whatwg-url": "^8.4.0" - } - }, - "@lerna/global-options": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/@lerna/global-options/-/global-options-4.0.0.tgz", - "integrity": "sha512-TRMR8afAHxuYBHK7F++Ogop2a82xQjoGna1dvPOY6ltj/pEx59pdgcJfYcynYqMkFIk8bhLJJN9/ndIfX29FTQ==", - "dev": true - }, - "@lerna/has-npm-version": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/@lerna/has-npm-version/-/has-npm-version-4.0.0.tgz", - "integrity": "sha512-LQ3U6XFH8ZmLCsvsgq1zNDqka0Xzjq5ibVN+igAI5ccRWNaUsE/OcmsyMr50xAtNQMYMzmpw5GVLAivT2/YzCg==", - "dev": true, - "requires": { - "@lerna/child-process": "4.0.0", - "semver": "^7.3.4" - } - }, - "@lerna/import": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/@lerna/import/-/import-4.0.0.tgz", - "integrity": "sha512-FaIhd+4aiBousKNqC7TX1Uhe97eNKf5/SC7c5WZANVWtC7aBWdmswwDt3usrzCNpj6/Wwr9EtEbYROzxKH8ffg==", - "dev": true, - "requires": { - "@lerna/child-process": "4.0.0", - "@lerna/command": "4.0.0", - "@lerna/prompt": "4.0.0", - "@lerna/pulse-till-done": "4.0.0", - "@lerna/validation-error": "4.0.0", - "dedent": "^0.7.0", - "fs-extra": "^9.1.0", - "p-map-series": "^2.1.0" - } - }, - "@lerna/info": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/@lerna/info/-/info-4.0.0.tgz", - "integrity": "sha512-8Uboa12kaCSZEn4XRfPz5KU9XXoexSPS4oeYGj76s2UQb1O1GdnEyfjyNWoUl1KlJ2i/8nxUskpXIftoFYH0/Q==", - "dev": true, - "requires": { - "@lerna/command": "4.0.0", - "@lerna/output": "4.0.0", - "envinfo": "^7.7.4" - } - }, - "@lerna/init": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/@lerna/init/-/init-4.0.0.tgz", - "integrity": "sha512-wY6kygop0BCXupzWj5eLvTUqdR7vIAm0OgyV9WHpMYQGfs1V22jhztt8mtjCloD/O0nEe4tJhdG62XU5aYmPNQ==", - "dev": true, - "requires": { - "@lerna/child-process": "4.0.0", - "@lerna/command": "4.0.0", - "fs-extra": "^9.1.0", - "p-map": "^4.0.0", - "write-json-file": "^4.3.0" - } - }, - "@lerna/link": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/@lerna/link/-/link-4.0.0.tgz", - "integrity": "sha512-KlvPi7XTAcVOByfaLlOeYOfkkDcd+bejpHMCd1KcArcFTwijOwXOVi24DYomIeHvy6HsX/IUquJ4PPUJIeB4+w==", - "dev": true, - "requires": { - "@lerna/command": "4.0.0", - "@lerna/package-graph": "4.0.0", - "@lerna/symlink-dependencies": "4.0.0", - "p-map": "^4.0.0", - "slash": "^3.0.0" - } - }, - "@lerna/list": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/@lerna/list/-/list-4.0.0.tgz", - "integrity": "sha512-L2B5m3P+U4Bif5PultR4TI+KtW+SArwq1i75QZ78mRYxPc0U/piau1DbLOmwrdqr99wzM49t0Dlvl6twd7GHFg==", - "dev": true, - "requires": { - "@lerna/command": "4.0.0", - "@lerna/filter-options": "4.0.0", - "@lerna/listable": "4.0.0", - "@lerna/output": "4.0.0" - } - }, - "@lerna/listable": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/@lerna/listable/-/listable-4.0.0.tgz", - "integrity": "sha512-/rPOSDKsOHs5/PBLINZOkRIX1joOXUXEtyUs5DHLM8q6/RP668x/1lFhw6Dx7/U+L0+tbkpGtZ1Yt0LewCLgeQ==", - "dev": true, - "requires": { - "@lerna/query-graph": "4.0.0", - "chalk": "^4.1.0", - "columnify": "^1.5.4" - } - }, - "@lerna/log-packed": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/@lerna/log-packed/-/log-packed-4.0.0.tgz", - "integrity": "sha512-+dpCiWbdzgMAtpajLToy9PO713IHoE6GV/aizXycAyA07QlqnkpaBNZ8DW84gHdM1j79TWockGJo9PybVhrrZQ==", - "dev": true, - "requires": { - "byte-size": "^7.0.0", - "columnify": "^1.5.4", - "has-unicode": "^2.0.1", - "npmlog": "^4.1.2" - } - }, - "@lerna/npm-conf": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/@lerna/npm-conf/-/npm-conf-4.0.0.tgz", - "integrity": "sha512-uS7H02yQNq3oejgjxAxqq/jhwGEE0W0ntr8vM3EfpCW1F/wZruwQw+7bleJQ9vUBjmdXST//tk8mXzr5+JXCfw==", - "dev": true, - "requires": { - "config-chain": "^1.1.12", - "pify": "^5.0.0" - } - }, - "@lerna/npm-dist-tag": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/@lerna/npm-dist-tag/-/npm-dist-tag-4.0.0.tgz", - "integrity": "sha512-F20sg28FMYTgXqEQihgoqSfwmq+Id3zT23CnOwD+XQMPSy9IzyLf1fFVH319vXIw6NF6Pgs4JZN2Qty6/CQXGw==", - "dev": true, - "requires": { - "@lerna/otplease": "4.0.0", - "npm-package-arg": "^8.1.0", - "npm-registry-fetch": "^9.0.0", - "npmlog": "^4.1.2" - } - }, - "@lerna/npm-install": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/@lerna/npm-install/-/npm-install-4.0.0.tgz", - "integrity": "sha512-aKNxq2j3bCH3eXl3Fmu4D54s/YLL9WSwV8W7X2O25r98wzrO38AUN6AB9EtmAx+LV/SP15et7Yueg9vSaanRWg==", - "dev": true, - "requires": { - "@lerna/child-process": "4.0.0", - "@lerna/get-npm-exec-opts": "4.0.0", - "fs-extra": "^9.1.0", - "npm-package-arg": "^8.1.0", - "npmlog": "^4.1.2", - "signal-exit": "^3.0.3", - "write-pkg": "^4.0.0" - } - }, - "@lerna/npm-publish": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/@lerna/npm-publish/-/npm-publish-4.0.0.tgz", - "integrity": "sha512-vQb7yAPRo5G5r77DRjHITc9piR9gvEKWrmfCH7wkfBnGWEqu7n8/4bFQ7lhnkujvc8RXOsYpvbMQkNfkYibD/w==", - "dev": true, - "requires": { - "@lerna/otplease": "4.0.0", - "@lerna/run-lifecycle": "4.0.0", - "fs-extra": "^9.1.0", - "libnpmpublish": "^4.0.0", - "npm-package-arg": "^8.1.0", - "npmlog": "^4.1.2", - "pify": "^5.0.0", - "read-package-json": "^3.0.0" - } - }, - "@lerna/npm-run-script": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/@lerna/npm-run-script/-/npm-run-script-4.0.0.tgz", - "integrity": "sha512-Jmyh9/IwXJjOXqKfIgtxi0bxi1pUeKe5bD3S81tkcy+kyng/GNj9WSqD5ZggoNP2NP//s4CLDAtUYLdP7CU9rA==", - "dev": true, - "requires": { - "@lerna/child-process": "4.0.0", - "@lerna/get-npm-exec-opts": "4.0.0", - "npmlog": "^4.1.2" - } - }, - "@lerna/otplease": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/@lerna/otplease/-/otplease-4.0.0.tgz", - "integrity": "sha512-Sgzbqdk1GH4psNiT6hk+BhjOfIr/5KhGBk86CEfHNJTk9BK4aZYyJD4lpDbDdMjIV4g03G7pYoqHzH765T4fxw==", - "dev": true, - "requires": { - "@lerna/prompt": "4.0.0" - } - }, - "@lerna/output": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/@lerna/output/-/output-4.0.0.tgz", - "integrity": "sha512-Un1sHtO1AD7buDQrpnaYTi2EG6sLF+KOPEAMxeUYG5qG3khTs2Zgzq5WE3dt2N/bKh7naESt20JjIW6tBELP0w==", - "dev": true, - "requires": { - "npmlog": "^4.1.2" - } - }, - "@lerna/pack-directory": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/@lerna/pack-directory/-/pack-directory-4.0.0.tgz", - "integrity": "sha512-NJrmZNmBHS+5aM+T8N6FVbaKFScVqKlQFJNY2k7nsJ/uklNKsLLl6VhTQBPwMTbf6Tf7l6bcKzpy7aePuq9UiQ==", - "dev": true, - "requires": { - "@lerna/get-packed": "4.0.0", - "@lerna/package": "4.0.0", - "@lerna/run-lifecycle": "4.0.0", - "npm-packlist": "^2.1.4", - "npmlog": "^4.1.2", - "tar": "^6.1.0", - "temp-write": "^4.0.0" - } - }, - "@lerna/package": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/@lerna/package/-/package-4.0.0.tgz", - "integrity": "sha512-l0M/izok6FlyyitxiQKr+gZLVFnvxRQdNhzmQ6nRnN9dvBJWn+IxxpM+cLqGACatTnyo9LDzNTOj2Db3+s0s8Q==", - "dev": true, - "requires": { - "load-json-file": "^6.2.0", - "npm-package-arg": "^8.1.0", - "write-pkg": "^4.0.0" - } - }, - "@lerna/package-graph": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/@lerna/package-graph/-/package-graph-4.0.0.tgz", - "integrity": "sha512-QED2ZCTkfXMKFoTGoccwUzjHtZMSf3UKX14A4/kYyBms9xfFsesCZ6SLI5YeySEgcul8iuIWfQFZqRw+Qrjraw==", - "dev": true, - "requires": { - "@lerna/prerelease-id-from-version": "4.0.0", - "@lerna/validation-error": "4.0.0", - "npm-package-arg": "^8.1.0", - "npmlog": "^4.1.2", - "semver": "^7.3.4" - } - }, - "@lerna/prerelease-id-from-version": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/@lerna/prerelease-id-from-version/-/prerelease-id-from-version-4.0.0.tgz", - "integrity": "sha512-GQqguzETdsYRxOSmdFZ6zDBXDErIETWOqomLERRY54f4p+tk4aJjoVdd9xKwehC9TBfIFvlRbL1V9uQGHh1opg==", - "dev": true, - "requires": { - "semver": "^7.3.4" - } - }, - "@lerna/profiler": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/@lerna/profiler/-/profiler-4.0.0.tgz", - "integrity": "sha512-/BaEbqnVh1LgW/+qz8wCuI+obzi5/vRE8nlhjPzdEzdmWmZXuCKyWSEzAyHOJWw1ntwMiww5dZHhFQABuoFz9Q==", - "dev": true, - "requires": { - "fs-extra": "^9.1.0", - "npmlog": "^4.1.2", - "upath": "^2.0.1" - } - }, - "@lerna/project": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/@lerna/project/-/project-4.0.0.tgz", - "integrity": "sha512-o0MlVbDkD5qRPkFKlBZsXZjoNTWPyuL58564nSfZJ6JYNmgAptnWPB2dQlAc7HWRZkmnC2fCkEdoU+jioPavbg==", - "dev": true, - "requires": { - "@lerna/package": "4.0.0", - "@lerna/validation-error": "4.0.0", - "cosmiconfig": "^7.0.0", - "dedent": "^0.7.0", - "dot-prop": "^6.0.1", - "glob-parent": "^5.1.1", - "globby": "^11.0.2", - "load-json-file": "^6.2.0", - "npmlog": "^4.1.2", - "p-map": "^4.0.0", - "resolve-from": "^5.0.0", - "write-json-file": "^4.3.0" - }, - "dependencies": { - "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, - "requires": { - "is-glob": "^4.0.1" - } - }, - "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 - } - } - }, - "@lerna/prompt": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/@lerna/prompt/-/prompt-4.0.0.tgz", - "integrity": "sha512-4Ig46oCH1TH5M7YyTt53fT6TuaKMgqUUaqdgxvp6HP6jtdak6+amcsqB8YGz2eQnw/sdxunx84DfI9XpoLj4bQ==", - "dev": true, - "requires": { - "inquirer": "^7.3.3", - "npmlog": "^4.1.2" - } - }, - "@lerna/publish": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/@lerna/publish/-/publish-4.0.0.tgz", - "integrity": "sha512-K8jpqjHrChH22qtkytA5GRKIVFEtqBF6JWj1I8dWZtHs4Jywn8yB1jQ3BAMLhqmDJjWJtRck0KXhQQKzDK2UPg==", - "dev": true, - "requires": { - "@lerna/check-working-tree": "4.0.0", - "@lerna/child-process": "4.0.0", - "@lerna/collect-updates": "4.0.0", - "@lerna/command": "4.0.0", - "@lerna/describe-ref": "4.0.0", - "@lerna/log-packed": "4.0.0", - "@lerna/npm-conf": "4.0.0", - "@lerna/npm-dist-tag": "4.0.0", - "@lerna/npm-publish": "4.0.0", - "@lerna/otplease": "4.0.0", - "@lerna/output": "4.0.0", - "@lerna/pack-directory": "4.0.0", - "@lerna/prerelease-id-from-version": "4.0.0", - "@lerna/prompt": "4.0.0", - "@lerna/pulse-till-done": "4.0.0", - "@lerna/run-lifecycle": "4.0.0", - "@lerna/run-topologically": "4.0.0", - "@lerna/validation-error": "4.0.0", - "@lerna/version": "4.0.0", - "fs-extra": "^9.1.0", - "libnpmaccess": "^4.0.1", - "npm-package-arg": "^8.1.0", - "npm-registry-fetch": "^9.0.0", - "npmlog": "^4.1.2", - "p-map": "^4.0.0", - "p-pipe": "^3.1.0", - "pacote": "^11.2.6", - "semver": "^7.3.4" - } - }, - "@lerna/pulse-till-done": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/@lerna/pulse-till-done/-/pulse-till-done-4.0.0.tgz", - "integrity": "sha512-Frb4F7QGckaybRhbF7aosLsJ5e9WuH7h0KUkjlzSByVycxY91UZgaEIVjS2oN9wQLrheLMHl6SiFY0/Pvo0Cxg==", - "dev": true, - "requires": { - "npmlog": "^4.1.2" - } - }, - "@lerna/query-graph": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/@lerna/query-graph/-/query-graph-4.0.0.tgz", - "integrity": "sha512-YlP6yI3tM4WbBmL9GCmNDoeQyzcyg1e4W96y/PKMZa5GbyUvkS2+Jc2kwPD+5KcXou3wQZxSPzR3Te5OenaDdg==", - "dev": true, - "requires": { - "@lerna/package-graph": "4.0.0" - } - }, - "@lerna/resolve-symlink": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/@lerna/resolve-symlink/-/resolve-symlink-4.0.0.tgz", - "integrity": "sha512-RtX8VEUzqT+uLSCohx8zgmjc6zjyRlh6i/helxtZTMmc4+6O4FS9q5LJas2uGO2wKvBlhcD6siibGt7dIC3xZA==", - "dev": true, - "requires": { - "fs-extra": "^9.1.0", - "npmlog": "^4.1.2", - "read-cmd-shim": "^2.0.0" - } - }, - "@lerna/rimraf-dir": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/@lerna/rimraf-dir/-/rimraf-dir-4.0.0.tgz", - "integrity": "sha512-QNH9ABWk9mcMJh2/muD9iYWBk1oQd40y6oH+f3wwmVGKYU5YJD//+zMiBI13jxZRtwBx0vmBZzkBkK1dR11cBg==", - "dev": true, - "requires": { - "@lerna/child-process": "4.0.0", - "npmlog": "^4.1.2", - "path-exists": "^4.0.0", - "rimraf": "^3.0.2" - } - }, - "@lerna/run": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/@lerna/run/-/run-4.0.0.tgz", - "integrity": "sha512-9giulCOzlMPzcZS/6Eov6pxE9gNTyaXk0Man+iCIdGJNMrCnW7Dme0Z229WWP/UoxDKg71F2tMsVVGDiRd8fFQ==", - "dev": true, - "requires": { - "@lerna/command": "4.0.0", - "@lerna/filter-options": "4.0.0", - "@lerna/npm-run-script": "4.0.0", - "@lerna/output": "4.0.0", - "@lerna/profiler": "4.0.0", - "@lerna/run-topologically": "4.0.0", - "@lerna/timer": "4.0.0", - "@lerna/validation-error": "4.0.0", - "p-map": "^4.0.0" - } - }, - "@lerna/run-lifecycle": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/@lerna/run-lifecycle/-/run-lifecycle-4.0.0.tgz", - "integrity": "sha512-IwxxsajjCQQEJAeAaxF8QdEixfI7eLKNm4GHhXHrgBu185JcwScFZrj9Bs+PFKxwb+gNLR4iI5rpUdY8Y0UdGQ==", - "dev": true, - "requires": { - "@lerna/npm-conf": "4.0.0", - "npm-lifecycle": "^3.1.5", - "npmlog": "^4.1.2" - } - }, - "@lerna/run-topologically": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/@lerna/run-topologically/-/run-topologically-4.0.0.tgz", - "integrity": "sha512-EVZw9hGwo+5yp+VL94+NXRYisqgAlj0jWKWtAIynDCpghRxCE5GMO3xrQLmQgqkpUl9ZxQFpICgYv5DW4DksQA==", - "dev": true, - "requires": { - "@lerna/query-graph": "4.0.0", - "p-queue": "^6.6.2" - } - }, - "@lerna/symlink-binary": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/@lerna/symlink-binary/-/symlink-binary-4.0.0.tgz", - "integrity": "sha512-zualodWC4q1QQc1pkz969hcFeWXOsVYZC5AWVtAPTDfLl+TwM7eG/O6oP+Rr3fFowspxo6b1TQ6sYfDV6HXNWA==", - "dev": true, - "requires": { - "@lerna/create-symlink": "4.0.0", - "@lerna/package": "4.0.0", - "fs-extra": "^9.1.0", - "p-map": "^4.0.0" - } - }, - "@lerna/symlink-dependencies": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/@lerna/symlink-dependencies/-/symlink-dependencies-4.0.0.tgz", - "integrity": "sha512-BABo0MjeUHNAe2FNGty1eantWp8u83BHSeIMPDxNq0MuW2K3CiQRaeWT3EGPAzXpGt0+hVzBrA6+OT0GPn7Yuw==", - "dev": true, - "requires": { - "@lerna/create-symlink": "4.0.0", - "@lerna/resolve-symlink": "4.0.0", - "@lerna/symlink-binary": "4.0.0", - "fs-extra": "^9.1.0", - "p-map": "^4.0.0", - "p-map-series": "^2.1.0" - } - }, - "@lerna/timer": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/@lerna/timer/-/timer-4.0.0.tgz", - "integrity": "sha512-WFsnlaE7SdOvjuyd05oKt8Leg3ENHICnvX3uYKKdByA+S3g+TCz38JsNs7OUZVt+ba63nC2nbXDlUnuT2Xbsfg==", - "dev": true - }, - "@lerna/validation-error": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/@lerna/validation-error/-/validation-error-4.0.0.tgz", - "integrity": "sha512-1rBOM5/koiVWlRi3V6dB863E1YzJS8v41UtsHgMr6gB2ncJ2LsQtMKlJpi3voqcgh41H8UsPXR58RrrpPpufyw==", - "dev": true, - "requires": { - "npmlog": "^4.1.2" - } - }, - "@lerna/version": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/@lerna/version/-/version-4.0.0.tgz", - "integrity": "sha512-otUgiqs5W9zGWJZSCCMRV/2Zm2A9q9JwSDS7s/tlKq4mWCYriWo7+wsHEA/nPTMDyYyBO5oyZDj+3X50KDUzeA==", - "dev": true, - "requires": { - "@lerna/check-working-tree": "4.0.0", - "@lerna/child-process": "4.0.0", - "@lerna/collect-updates": "4.0.0", - "@lerna/command": "4.0.0", - "@lerna/conventional-commits": "4.0.0", - "@lerna/github-client": "4.0.0", - "@lerna/gitlab-client": "4.0.0", - "@lerna/output": "4.0.0", - "@lerna/prerelease-id-from-version": "4.0.0", - "@lerna/prompt": "4.0.0", - "@lerna/run-lifecycle": "4.0.0", - "@lerna/run-topologically": "4.0.0", - "@lerna/validation-error": "4.0.0", - "chalk": "^4.1.0", - "dedent": "^0.7.0", - "load-json-file": "^6.2.0", - "minimatch": "^3.0.4", - "npmlog": "^4.1.2", - "p-map": "^4.0.0", - "p-pipe": "^3.1.0", - "p-reduce": "^2.1.0", - "p-waterfall": "^2.1.1", - "semver": "^7.3.4", - "slash": "^3.0.0", - "temp-write": "^4.0.0", - "write-json-file": "^4.3.0" - } - }, - "@lerna/write-log-file": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/@lerna/write-log-file/-/write-log-file-4.0.0.tgz", - "integrity": "sha512-XRG5BloiArpXRakcnPHmEHJp+4AtnhRtpDIHSghmXD5EichI1uD73J7FgPp30mm2pDRq3FdqB0NbwSEsJ9xFQg==", - "dev": true, - "requires": { - "npmlog": "^4.1.2", - "write-file-atomic": "^3.0.3" - } - }, - "@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, - "requires": { - "@nodelib/fs.stat": "2.0.5", - "run-parallel": "^1.1.9" - } - }, - "@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 - }, - "@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, - "requires": { - "@nodelib/fs.scandir": "2.1.5", - "fastq": "^1.6.0" - } - }, - "@npmcli/ci-detect": { - "version": "1.4.0", - "resolved": "https://registry.npmjs.org/@npmcli/ci-detect/-/ci-detect-1.4.0.tgz", - "integrity": "sha512-3BGrt6FLjqM6br5AhWRKTr3u5GIVkjRYeAFrMp3HjnfICrg4xOrVRwFavKT6tsp++bq5dluL5t8ME/Nha/6c1Q==", - "dev": true - }, - "@npmcli/fs": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/@npmcli/fs/-/fs-1.1.0.tgz", - "integrity": "sha512-VhP1qZLXcrXRIaPoqb4YA55JQxLNF3jNR4T55IdOJa3+IFJKNYHtPvtXx8slmeMavj37vCzCfrqQM1vWLsYKLA==", - "dev": true, - "requires": { - "@gar/promisify": "^1.0.1", - "semver": "^7.3.5" - } - }, - "@npmcli/git": { - "version": "2.1.0", - "resolved": "https://registry.npmjs.org/@npmcli/git/-/git-2.1.0.tgz", - "integrity": "sha512-/hBFX/QG1b+N7PZBFs0bi+evgRZcK9nWBxQKZkGoXUT5hJSwl5c4d7y8/hm+NQZRPhQ67RzFaj5UM9YeyKoryw==", - "dev": true, - "requires": { - "@npmcli/promise-spawn": "^1.3.2", - "lru-cache": "^6.0.0", - "mkdirp": "^1.0.4", - "npm-pick-manifest": "^6.1.1", - "promise-inflight": "^1.0.1", - "promise-retry": "^2.0.1", - "semver": "^7.3.5", - "which": "^2.0.2" - } - }, - "@npmcli/installed-package-contents": { - "version": "1.0.7", - "resolved": "https://registry.npmjs.org/@npmcli/installed-package-contents/-/installed-package-contents-1.0.7.tgz", - "integrity": "sha512-9rufe0wnJusCQoLpV9ZPKIVP55itrM5BxOXs10DmdbRfgWtHy1LDyskbwRnBghuB0PrF7pNPOqREVtpz4HqzKw==", - "dev": true, - "requires": { - "npm-bundled": "^1.1.1", - "npm-normalize-package-bin": "^1.0.1" - } - }, - "@npmcli/move-file": { - "version": "1.1.2", - "resolved": "https://registry.npmjs.org/@npmcli/move-file/-/move-file-1.1.2.tgz", - "integrity": "sha512-1SUf/Cg2GzGDyaf15aR9St9TWlb+XvbZXWpDx8YKs7MLzMH/BCeopv+y9vzrzgkfykCGuWOlSu3mZhj2+FQcrg==", - "dev": true, - "requires": { - "mkdirp": "^1.0.4", - "rimraf": "^3.0.2" - } - }, - "@npmcli/node-gyp": { - "version": "1.0.3", - "resolved": "https://registry.npmjs.org/@npmcli/node-gyp/-/node-gyp-1.0.3.tgz", - "integrity": "sha512-fnkhw+fmX65kiLqk6E3BFLXNC26rUhK90zVwe2yncPliVT/Qos3xjhTLE59Df8KnPlcwIERXKVlU1bXoUQ+liA==", - "dev": true - }, - "@npmcli/promise-spawn": { - "version": "1.3.2", - "resolved": "https://registry.npmjs.org/@npmcli/promise-spawn/-/promise-spawn-1.3.2.tgz", - "integrity": "sha512-QyAGYo/Fbj4MXeGdJcFzZ+FkDkomfRBrPM+9QYJSg+PxgAUL+LU3FneQk37rKR2/zjqkCV1BLHccX98wRXG3Sg==", - "dev": true, - "requires": { - "infer-owner": "^1.0.4" - } - }, - "@npmcli/run-script": { - "version": "1.8.6", - "resolved": "https://registry.npmjs.org/@npmcli/run-script/-/run-script-1.8.6.tgz", - "integrity": "sha512-e42bVZnC6VluBZBAFEr3YrdqSspG3bgilyg4nSLBJ7TRGNCzxHa92XAHxQBLYg0BmgwO4b2mf3h/l5EkEWRn3g==", - "dev": true, - "requires": { - "@npmcli/node-gyp": "^1.0.2", - "@npmcli/promise-spawn": "^1.3.2", - "node-gyp": "^7.1.0", - "read-package-json-fast": "^2.0.1" - }, - "dependencies": { - "node-gyp": { - "version": "7.1.2", - "resolved": "https://registry.npmjs.org/node-gyp/-/node-gyp-7.1.2.tgz", - "integrity": "sha512-CbpcIo7C3eMu3dL1c3d0xw449fHIGALIJsRP4DDPHpyiW8vcriNY7ubh9TE4zEKfSxscY7PjeFnshE7h75ynjQ==", - "dev": true, - "requires": { - "env-paths": "^2.2.0", - "glob": "^7.1.4", - "graceful-fs": "^4.2.3", - "nopt": "^5.0.0", - "npmlog": "^4.1.2", - "request": "^2.88.2", - "rimraf": "^3.0.2", - "semver": "^7.3.2", - "tar": "^6.0.2", - "which": "^2.0.2" - } - }, - "nopt": { - "version": "5.0.0", - "resolved": "https://registry.npmjs.org/nopt/-/nopt-5.0.0.tgz", - "integrity": "sha512-Tbj67rffqceeLpcRXrT7vKAN8CwfPeIBgM7E6iBkmKLV7bEMwpGgYLGv0jACUsECaa/vuxP0IjEont6umdMgtQ==", - "dev": true, - "requires": { - "abbrev": "1" - } - } - } - }, - "@octokit/auth-token": { - "version": "2.5.0", - "resolved": "https://registry.npmjs.org/@octokit/auth-token/-/auth-token-2.5.0.tgz", - "integrity": "sha512-r5FVUJCOLl19AxiuZD2VRZ/ORjp/4IN98Of6YJoJOkY75CIBuYfmiNHGrDwXr+aLGG55igl9QrxX3hbiXlLb+g==", - "dev": true, - "requires": { - "@octokit/types": "^6.0.3" - } - }, - "@octokit/core": { - "version": "3.5.1", - "resolved": "https://registry.npmjs.org/@octokit/core/-/core-3.5.1.tgz", - "integrity": "sha512-omncwpLVxMP+GLpLPgeGJBF6IWJFjXDS5flY5VbppePYX9XehevbDykRH9PdCdvqt9TS5AOTiDide7h0qrkHjw==", - "dev": true, - "requires": { - "@octokit/auth-token": "^2.4.4", - "@octokit/graphql": "^4.5.8", - "@octokit/request": "^5.6.0", - "@octokit/request-error": "^2.0.5", - "@octokit/types": "^6.0.3", - "before-after-hook": "^2.2.0", - "universal-user-agent": "^6.0.0" - } - }, - "@octokit/endpoint": { - "version": "6.0.12", - "resolved": "https://registry.npmjs.org/@octokit/endpoint/-/endpoint-6.0.12.tgz", - "integrity": "sha512-lF3puPwkQWGfkMClXb4k/eUT/nZKQfxinRWJrdZaJO85Dqwo/G0yOC434Jr2ojwafWJMYqFGFa5ms4jJUgujdA==", - "dev": true, - "requires": { - "@octokit/types": "^6.0.3", - "is-plain-object": "^5.0.0", - "universal-user-agent": "^6.0.0" - } - }, - "@octokit/graphql": { - "version": "4.8.0", - "resolved": "https://registry.npmjs.org/@octokit/graphql/-/graphql-4.8.0.tgz", - "integrity": "sha512-0gv+qLSBLKF0z8TKaSKTsS39scVKF9dbMxJpj3U0vC7wjNWFuIpL/z76Qe2fiuCbDRcJSavkXsVtMS6/dtQQsg==", - "dev": true, - "requires": { - "@octokit/request": "^5.6.0", - "@octokit/types": "^6.0.3", - "universal-user-agent": "^6.0.0" - } - }, - "@octokit/openapi-types": { - "version": "11.2.0", - "resolved": "https://registry.npmjs.org/@octokit/openapi-types/-/openapi-types-11.2.0.tgz", - "integrity": "sha512-PBsVO+15KSlGmiI8QAzaqvsNlZlrDlyAJYcrXBCvVUxCp7VnXjkwPoFHgjEJXx3WF9BAwkA6nfCUA7i9sODzKA==", - "dev": true - }, - "@octokit/plugin-enterprise-rest": { - "version": "6.0.1", - "resolved": "https://registry.npmjs.org/@octokit/plugin-enterprise-rest/-/plugin-enterprise-rest-6.0.1.tgz", - "integrity": "sha512-93uGjlhUD+iNg1iWhUENAtJata6w5nE+V4urXOAlIXdco6xNZtUSfYY8dzp3Udy74aqO/B5UZL80x/YMa5PKRw==", - "dev": true - }, - "@octokit/plugin-paginate-rest": { - "version": "2.17.0", - "resolved": "https://registry.npmjs.org/@octokit/plugin-paginate-rest/-/plugin-paginate-rest-2.17.0.tgz", - "integrity": "sha512-tzMbrbnam2Mt4AhuyCHvpRkS0oZ5MvwwcQPYGtMv4tUa5kkzG58SVB0fcsLulOZQeRnOgdkZWkRUiyBlh0Bkyw==", - "dev": true, - "requires": { - "@octokit/types": "^6.34.0" - } - }, - "@octokit/plugin-request-log": { - "version": "1.0.4", - "resolved": "https://registry.npmjs.org/@octokit/plugin-request-log/-/plugin-request-log-1.0.4.tgz", - "integrity": "sha512-mLUsMkgP7K/cnFEw07kWqXGF5LKrOkD+lhCrKvPHXWDywAwuDUeDwWBpc69XK3pNX0uKiVt8g5z96PJ6z9xCFA==", - "dev": true, - "requires": {} - }, - "@octokit/plugin-rest-endpoint-methods": { - "version": "5.13.0", - "resolved": "https://registry.npmjs.org/@octokit/plugin-rest-endpoint-methods/-/plugin-rest-endpoint-methods-5.13.0.tgz", - "integrity": "sha512-uJjMTkN1KaOIgNtUPMtIXDOjx6dGYysdIFhgA52x4xSadQCz3b/zJexvITDVpANnfKPW/+E0xkOvLntqMYpviA==", - "dev": true, - "requires": { - "@octokit/types": "^6.34.0", - "deprecation": "^2.3.1" - } - }, - "@octokit/request": { - "version": "5.6.2", - "resolved": "https://registry.npmjs.org/@octokit/request/-/request-5.6.2.tgz", - "integrity": "sha512-je66CvSEVf0jCpRISxkUcCa0UkxmFs6eGDRSbfJtAVwbLH5ceqF+YEyC8lj8ystKyZTy8adWr0qmkY52EfOeLA==", - "dev": true, - "requires": { - "@octokit/endpoint": "^6.0.1", - "@octokit/request-error": "^2.1.0", - "@octokit/types": "^6.16.1", - "is-plain-object": "^5.0.0", - "node-fetch": "^2.6.1", - "universal-user-agent": "^6.0.0" - } - }, - "@octokit/request-error": { - "version": "2.1.0", - "resolved": "https://registry.npmjs.org/@octokit/request-error/-/request-error-2.1.0.tgz", - "integrity": "sha512-1VIvgXxs9WHSjicsRwq8PlR2LR2x6DwsJAaFgzdi0JfJoGSO8mYI/cHJQ+9FbN21aa+DrgNLnwObmyeSC8Rmpg==", - "dev": true, - "requires": { - "@octokit/types": "^6.0.3", - "deprecation": "^2.0.0", - "once": "^1.4.0" - } - }, - "@octokit/rest": { - "version": "18.12.0", - "resolved": "https://registry.npmjs.org/@octokit/rest/-/rest-18.12.0.tgz", - "integrity": "sha512-gDPiOHlyGavxr72y0guQEhLsemgVjwRePayJ+FcKc2SJqKUbxbkvf5kAZEWA/MKvsfYlQAMVzNJE3ezQcxMJ2Q==", - "dev": true, - "requires": { - "@octokit/core": "^3.5.1", - "@octokit/plugin-paginate-rest": "^2.16.8", - "@octokit/plugin-request-log": "^1.0.4", - "@octokit/plugin-rest-endpoint-methods": "^5.12.0" - } - }, - "@octokit/types": { - "version": "6.34.0", - "resolved": "https://registry.npmjs.org/@octokit/types/-/types-6.34.0.tgz", - "integrity": "sha512-s1zLBjWhdEI2zwaoSgyOFoKSl109CUcVBCc7biPJ3aAf6LGLU6szDvi31JPU7bxfla2lqfhjbbg/5DdFNxOwHw==", - "dev": true, - "requires": { - "@octokit/openapi-types": "^11.2.0" - } - }, - "@sindresorhus/is": { - "version": "0.14.0", - "resolved": "https://registry.npmjs.org/@sindresorhus/is/-/is-0.14.0.tgz", - "integrity": "sha512-9NET910DNaIPngYnLLPeg+Ogzqsi9uM4mSboU5y6p8S5DzMTVEsJZrawi+BoDNUVBa2DhJqQYUFvMDfgU062LQ==", - "dev": true - }, - "@socket.io/component-emitter": { - "version": "3.0.0", - "resolved": "https://registry.npmjs.org/@socket.io/component-emitter/-/component-emitter-3.0.0.tgz", - "integrity": "sha512-2pTGuibAXJswAPJjaKisthqS/NOK5ypG4LYT6tEAV0S/mxW0zOIvYvGK0V8w8+SHxAm6vRMSjqSalFXeBAqs+Q==" - }, - "@szmarczak/http-timer": { - "version": "1.1.2", - "resolved": "https://registry.npmjs.org/@szmarczak/http-timer/-/http-timer-1.1.2.tgz", - "integrity": "sha512-XIB2XbzHTN6ieIjfIMV9hlVcfPU26s2vafYWQcZHWXHOxiaRZYEDKEwdl129Zyg50+foYV2jCgtrqSA6qNuNSA==", - "dev": true, - "requires": { - "defer-to-connect": "^1.0.1" - } - }, - "@tootallnate/once": { - "version": "1.1.2", - "resolved": "https://registry.npmjs.org/@tootallnate/once/-/once-1.1.2.tgz", - "integrity": "sha512-RbzJvlNzmRq5c3O09UipeuXno4tA1FE6ikOjxZK0tuxVv3412l64l5t1W5pj4+rJq9vpkm/kwiR07aZXnsKPxw==", - "dev": true - }, - "@tsconfig/node10": { - "version": "1.0.8", - "resolved": "https://registry.npmjs.org/@tsconfig/node10/-/node10-1.0.8.tgz", - "integrity": "sha512-6XFfSQmMgq0CFLY1MslA/CPUfhIL919M1rMsa5lP2P097N2Wd1sSX0tx1u4olM16fLNhtHZpRhedZJphNJqmZg==" - }, - "@tsconfig/node12": { - "version": "1.0.9", - "resolved": "https://registry.npmjs.org/@tsconfig/node12/-/node12-1.0.9.tgz", - "integrity": "sha512-/yBMcem+fbvhSREH+s14YJi18sp7J9jpuhYByADT2rypfajMZZN4WQ6zBGgBKp53NKmqI36wFYDb3yaMPurITw==" - }, - "@tsconfig/node14": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/@tsconfig/node14/-/node14-1.0.1.tgz", - "integrity": "sha512-509r2+yARFfHHE7T6Puu2jjkoycftovhXRqW328PDXTVGKihlb1P8Z9mMZH04ebyajfRY7dedfGynlrFHJUQCg==" - }, - "@tsconfig/node16": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/@tsconfig/node16/-/node16-1.0.2.tgz", - "integrity": "sha512-eZxlbI8GZscaGS7kkc/trHTT5xgrjH3/1n2JDwusC9iahPKWMRvRjJSAN5mCXviuTGQ/lHnhvv8Q1YTpnfz9gA==" - }, - "@types/accepts": { - "version": "1.3.5", - "resolved": "https://registry.npmjs.org/@types/accepts/-/accepts-1.3.5.tgz", - "integrity": "sha512-jOdnI/3qTpHABjM5cx1Hc0sKsPoYCp+DP/GJRGtDlPd7fiV9oXGGIcjW/ZOxLIvjGz8MA+uMZI9metHlgqbgwQ==", - "requires": { - "@types/node": "*" - } - }, - "@types/axios": { - "version": "0.14.0", - "resolved": "https://registry.npmjs.org/@types/axios/-/axios-0.14.0.tgz", - "integrity": "sha1-7CMA++fX3d1+udOr+HmZlkyvzkY=", - "requires": { - "axios": "*" - } - }, - "@types/bcryptjs": { - "version": "2.4.2", - "resolved": "https://registry.npmjs.org/@types/bcryptjs/-/bcryptjs-2.4.2.tgz", - "integrity": "sha512-LiMQ6EOPob/4yUL66SZzu6Yh77cbzJFYll+ZfaPiPPFswtIlA/Fs1MzdKYA7JApHU49zQTbJGX3PDmCpIdDBRQ==" - }, - "@types/body-parser": { - "version": "1.19.2", - "resolved": "https://registry.npmjs.org/@types/body-parser/-/body-parser-1.19.2.tgz", - "integrity": "sha512-ALYone6pm6QmwZoAgeyNksccT9Q4AWZQ6PvfwR37GT6r6FWUPguq6sUmNGSMV2Wr761oQoBxwGGa6DR5o1DC9g==", - "requires": { - "@types/connect": "*", - "@types/node": "*" - } - }, - "@types/component-emitter": { - "version": "1.2.11", - "resolved": "https://registry.npmjs.org/@types/component-emitter/-/component-emitter-1.2.11.tgz", - "integrity": "sha512-SRXjM+tfsSlA9VuG8hGO2nft2p8zjXCK1VcC6N4NXbBbYbSia9kzCChYQajIjzIqOOOuh5Ock6MmV2oux4jDZQ==" - }, - "@types/config": { - "version": "0.0.40", - "resolved": "https://registry.npmjs.org/@types/config/-/config-0.0.40.tgz", - "integrity": "sha512-4s7JAciBzCJVy0fp7LPsMj0v3F+IeTdjpwMQ6owOx67UjcyurjP+8DO556u5/8PUhifAYp7H5b7D88RKFDBGEg==" - }, - "@types/connect": { - "version": "3.4.35", - "resolved": "https://registry.npmjs.org/@types/connect/-/connect-3.4.35.tgz", - "integrity": "sha512-cdeYyv4KWoEgpBISTxWvqYsVy444DOqehiF3fM3ne10AmJ62RSyNkUnxMJXHQWRQQX2eR94m5y1IZyDwBjV9FQ==", - "requires": { - "@types/node": "*" - } - }, - "@types/content-disposition": { - "version": "0.5.4", - "resolved": "https://registry.npmjs.org/@types/content-disposition/-/content-disposition-0.5.4.tgz", - "integrity": "sha512-0mPF08jn9zYI0n0Q/Pnz7C4kThdSt+6LD4amsrYDDpgBfrVWa3TcCOxKX1zkGgYniGagRv8heN2cbh+CAn+uuQ==" - }, - "@types/cookie": { - "version": "0.4.1", - "resolved": "https://registry.npmjs.org/@types/cookie/-/cookie-0.4.1.tgz", - "integrity": "sha512-XW/Aa8APYr6jSVVA1y/DEIZX0/GMKLEVekNG727R8cs56ahETkRAy/3DR7+fJyh7oUgGwNQaRfXCun0+KbWY7Q==" - }, - "@types/cookiejar": { - "version": "2.1.2", - "resolved": "https://registry.npmjs.org/@types/cookiejar/-/cookiejar-2.1.2.tgz", - "integrity": "sha512-t73xJJrvdTjXrn4jLS9VSGRbz0nUY3cl2DMGDU48lKl+HR9dbbjW2A9r3g40VA++mQpy6uuHg33gy7du2BKpog==" - }, - "@types/cookies": { - "version": "0.7.7", - "resolved": "https://registry.npmjs.org/@types/cookies/-/cookies-0.7.7.tgz", - "integrity": "sha512-h7BcvPUogWbKCzBR2lY4oqaZbO3jXZksexYJVFvkrFeLgbZjQkU4x8pRq6eg2MHXQhY0McQdqmmsxRWlVAHooA==", - "requires": { - "@types/connect": "*", - "@types/express": "*", - "@types/keygrip": "*", - "@types/node": "*" - } - }, - "@types/cors": { - "version": "2.8.12", - "resolved": "https://registry.npmjs.org/@types/cors/-/cors-2.8.12.tgz", - "integrity": "sha512-vt+kDhq/M2ayberEtJcIN/hxXy1Pk+59g2FV/ZQceeaTyCtCucjL2Q7FXlFjtWn4n15KCr1NE2lNNFhp0lEThw==" - }, - "@types/eslint": { - "version": "8.2.1", - "resolved": "https://registry.npmjs.org/@types/eslint/-/eslint-8.2.1.tgz", - "integrity": "sha512-UP9rzNn/XyGwb5RQ2fok+DzcIRIYwc16qTXse5+Smsy8MOIccCChT15KAwnsgQx4PzJkaMq4myFyZ4CL5TjhIQ==", - "requires": { - "@types/estree": "*", - "@types/json-schema": "*" - } - }, - "@types/eslint-scope": { - "version": "3.7.2", - "resolved": "https://registry.npmjs.org/@types/eslint-scope/-/eslint-scope-3.7.2.tgz", - "integrity": "sha512-TzgYCWoPiTeRg6RQYgtuW7iODtVoKu3RVL72k3WohqhjfaOLK5Mg2T4Tg1o2bSfu0vPkoI48wdQFv5b/Xe04wQ==", - "requires": { - "@types/eslint": "*", - "@types/estree": "*" - } - }, - "@types/estree": { - "version": "0.0.50", - "resolved": "https://registry.npmjs.org/@types/estree/-/estree-0.0.50.tgz", - "integrity": "sha512-C6N5s2ZFtuZRj54k2/zyRhNDjJwwcViAM3Nbm8zjBpbqAdZ00mr0CFxvSKeO8Y/e03WVFLpQMdHYVfUd6SB+Hw==" - }, - "@types/express": { - "version": "4.17.13", - "resolved": "https://registry.npmjs.org/@types/express/-/express-4.17.13.tgz", - "integrity": "sha512-6bSZTPaTIACxn48l50SR+axgrqm6qXFIxrdAKaG6PaJk3+zuUr35hBlgT7vOmJcum+OEaIBLtHV/qloEAFITeA==", - "requires": { - "@types/body-parser": "*", - "@types/express-serve-static-core": "^4.17.18", - "@types/qs": "*", - "@types/serve-static": "*" - } - }, - "@types/express-serve-static-core": { - "version": "4.17.27", - "resolved": "https://registry.npmjs.org/@types/express-serve-static-core/-/express-serve-static-core-4.17.27.tgz", - "integrity": "sha512-e/sVallzUTPdyOTiqi8O8pMdBBphscvI6E4JYaKlja4Lm+zh7UFSSdW5VMkRbhDtmrONqOUHOXRguPsDckzxNA==", - "requires": { - "@types/node": "*", - "@types/qs": "*", - "@types/range-parser": "*" - } - }, - "@types/express-session": { - "version": "1.17.4", - "resolved": "https://registry.npmjs.org/@types/express-session/-/express-session-1.17.4.tgz", - "integrity": "sha512-7cNlSI8+oOBUHTfPXMwDxF/Lchx5aJ3ho7+p9jJZYVg9dVDJFh3qdMXmJtRsysnvS+C6x46k9DRYmrmCkE+MVg==", - "requires": { - "@types/express": "*" - } - }, - "@types/http-assert": { - "version": "1.5.3", - "resolved": "https://registry.npmjs.org/@types/http-assert/-/http-assert-1.5.3.tgz", - "integrity": "sha512-FyAOrDuQmBi8/or3ns4rwPno7/9tJTijVW6aQQjK02+kOQ8zmoNg2XJtAuQhvQcy1ASJq38wirX5//9J1EqoUA==" - }, - "@types/http-errors": { - "version": "1.8.1", - "resolved": "https://registry.npmjs.org/@types/http-errors/-/http-errors-1.8.1.tgz", - "integrity": "sha512-e+2rjEwK6KDaNOm5Aa9wNGgyS9oSZU/4pfSMMPYNOfjvFI0WVXm29+ITRFr6aKDvvKo7uU1jV68MW4ScsfDi7Q==" - }, - "@types/json-schema": { - "version": "7.0.9", - "resolved": "https://registry.npmjs.org/@types/json-schema/-/json-schema-7.0.9.tgz", - "integrity": "sha512-qcUXuemtEu+E5wZSJHNxUXeCZhAfXKQ41D+duX+VYPde7xyEVZci+/oXKJL13tnRs9lR2pr4fod59GT6/X1/yQ==" - }, - "@types/json5": { - "version": "0.0.29", - "resolved": "https://registry.npmjs.org/@types/json5/-/json5-0.0.29.tgz", - "integrity": "sha1-7ihweulOEdK4J7y+UnC86n8+ce4=", - "dev": true - }, - "@types/jsonwebtoken": { - "version": "8.5.6", - "resolved": "https://registry.npmjs.org/@types/jsonwebtoken/-/jsonwebtoken-8.5.6.tgz", - "integrity": "sha512-+P3O/xC7nzVizIi5VbF34YtqSonFsdnbXBnWUCYRiKOi1f9gA4sEFvXkrGr/QVV23IbMYvcoerI7nnhDUiWXRQ==", - "requires": { - "@types/node": "*" - } - }, - "@types/keygrip": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/@types/keygrip/-/keygrip-1.0.2.tgz", - "integrity": "sha512-GJhpTepz2udxGexqos8wgaBx4I/zWIDPh/KOGEwAqtuGDkOUJu5eFvwmdBX4AmB8Odsr+9pHCQqiAqDL/yKMKw==" - }, - "@types/koa": { - "version": "2.13.4", - "resolved": "https://registry.npmjs.org/@types/koa/-/koa-2.13.4.tgz", - "integrity": "sha512-dfHYMfU+z/vKtQB7NUrthdAEiSvnLebvBjwHtfFmpZmB7em2N3WVQdHgnFq+xvyVgxW5jKDmjWfLD3lw4g4uTw==", - "requires": { - "@types/accepts": "*", - "@types/content-disposition": "*", - "@types/cookies": "*", - "@types/http-assert": "*", - "@types/http-errors": "*", - "@types/keygrip": "*", - "@types/koa-compose": "*", - "@types/node": "*" - } - }, - "@types/koa-bodyparser": { - "version": "4.3.5", - "resolved": "https://registry.npmjs.org/@types/koa-bodyparser/-/koa-bodyparser-4.3.5.tgz", - "integrity": "sha512-NRqqoTtt7cfdDk/KNo+EwCIKRuzPAu/wsaZ7tgIvSIBtNfxuZHYueaLoWdxX3ZftWavQv07NE46TcpyoZGqpgQ==", - "requires": { - "@types/koa": "*" - } - }, - "@types/koa-compose": { - "version": "3.2.5", - "resolved": "https://registry.npmjs.org/@types/koa-compose/-/koa-compose-3.2.5.tgz", - "integrity": "sha512-B8nG/OoE1ORZqCkBVsup/AKcvjdgoHnfi4pZMn5UwAPCbhk/96xyv284eBYW8JlQbQ7zDmnpFr68I/40mFoIBQ==", - "requires": { - "@types/koa": "*" - } - }, - "@types/koa-qs": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/@types/koa-qs/-/koa-qs-2.0.0.tgz", - "integrity": "sha512-cBfbUvW70JsU2FCgUCFOoretdvayGzRJ2vEyNQbnZ7vb2pZ/QA+gcNzE6nVxxCcrcnRtGB7tXIRHqHPXS51utA==", - "requires": { - "@types/koa": "*" - } - }, - "@types/lodash": { - "version": "4.14.178", - "resolved": "https://registry.npmjs.org/@types/lodash/-/lodash-4.14.178.tgz", - "integrity": "sha512-0d5Wd09ItQWH1qFbEyQ7oTQ3GZrMfth5JkbN3EvTKLXcHLRDSXeLnlvlOn0wvxVIwK5o2M8JzP/OWz7T3NRsbw==" - }, - "@types/mime": { - "version": "1.3.2", - "resolved": "https://registry.npmjs.org/@types/mime/-/mime-1.3.2.tgz", - "integrity": "sha512-YATxVxgRqNH6nHEIsvg6k2Boc1JHI9ZbH5iWFFv/MTkchz3b1ieGDa5T0a9RznNdI0KhVbdbWSN+KWWrQZRxTw==" - }, - "@types/minimatch": { - "version": "3.0.5", - "resolved": "https://registry.npmjs.org/@types/minimatch/-/minimatch-3.0.5.tgz", - "integrity": "sha512-Klz949h02Gz2uZCMGwDUSDS1YBlTdDDgbWHi+81l29tQALUtvz4rAYi5uoVhE5Lagoq6DeqAUlbrHvW/mXDgdQ==", - "dev": true - }, - "@types/minimist": { - "version": "1.2.2", - "resolved": "https://registry.npmjs.org/@types/minimist/-/minimist-1.2.2.tgz", - "integrity": "sha512-jhuKLIRrhvCPLqwPcx6INqmKeiA5EWrsCOPhrlFSrbrmU4ZMPjj5Ul/oLCMDO98XRUIwVm78xICz4EPCektzeQ==", - "dev": true - }, - "@types/mocha": { - "version": "9.0.0", - "resolved": "https://registry.npmjs.org/@types/mocha/-/mocha-9.0.0.tgz", - "integrity": "sha512-scN0hAWyLVAvLR9AyW7HoFF5sJZglyBsbPuHO4fv7JRvfmPBMfp1ozWqOf/e4wwPNxezBZXRfWzMb6iFLgEVRA==" - }, - "@types/mongodb": { - "version": "4.0.7", - "resolved": "https://registry.npmjs.org/@types/mongodb/-/mongodb-4.0.7.tgz", - "integrity": "sha512-lPUYPpzA43baXqnd36cZ9xxorprybxXDzteVKCPAdp14ppHtFJHnXYvNpmBvtMUTb5fKXVv6sVbzo1LHkWhJlw==", - "requires": { - "mongodb": "*" - } - }, - "@types/node": { - "version": "17.0.7", - "resolved": "https://registry.npmjs.org/@types/node/-/node-17.0.7.tgz", - "integrity": "sha512-1QUk+WAUD4t8iR+Oj+UgI8oJa6yyxaB8a8pHaC8uqM6RrS1qbL7bf3Pwl5rHv0psm2CuDErgho6v5N+G+5fwtQ==" - }, - "@types/node-fetch": { - "version": "3.0.3", - "resolved": "https://registry.npmjs.org/@types/node-fetch/-/node-fetch-3.0.3.tgz", - "integrity": "sha512-HhggYPH5N+AQe/OmN6fmhKmRRt2XuNJow+R3pQwJxOOF9GuwM7O2mheyGeIrs5MOIeNjDEdgdoyHBOrFeJBR3g==", - "requires": { - "node-fetch": "*" - } - }, - "@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 - }, - "@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 - }, - "@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==" - }, - "@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==" - }, - "@types/serve-static": { - "version": "1.13.10", - "resolved": "https://registry.npmjs.org/@types/serve-static/-/serve-static-1.13.10.tgz", - "integrity": "sha512-nCkHGI4w7ZgAdNkrEu0bv+4xNV/XDqW+DydknebMOQwkpDGx8G+HTlj7R7ABI8i8nKxVw0wtKPi1D+lPOkh4YQ==", - "requires": { - "@types/mime": "^1", - "@types/node": "*" - } - }, - "@types/superagent": { - "version": "4.1.14", - "resolved": "https://registry.npmjs.org/@types/superagent/-/superagent-4.1.14.tgz", - "integrity": "sha512-iiXaOL2wSbnSY4qg0mFPWJHL9iwyEsoNYwaHF2w58/fsVAQJlj+KUfFAFZu+nzbz+b7dUprJEAc+O9vhHHhQTA==", - "requires": { - "@types/cookiejar": "*", - "@types/node": "*" - } - }, - "@types/uuid": { - "version": "8.3.3", - "resolved": "https://registry.npmjs.org/@types/uuid/-/uuid-8.3.3.tgz", - "integrity": "sha512-0LbEEx1zxrYB3pgpd1M5lEhLcXjKJnYghvhTRgaBeUivLHMDM1TzF3IJ6hXU2+8uA4Xz+5BA63mtZo5DjVT8iA==" - }, - "@types/webidl-conversions": { - "version": "6.1.1", - "resolved": "https://registry.npmjs.org/@types/webidl-conversions/-/webidl-conversions-6.1.1.tgz", - "integrity": "sha512-XAahCdThVuCFDQLT7R7Pk/vqeObFNL3YqRyFZg+AqAP/W1/w3xHaIxuW7WszQqTbIBOPRcItYJIou3i/mppu3Q==" - }, - "@types/whatwg-url": { - "version": "8.2.1", - "resolved": "https://registry.npmjs.org/@types/whatwg-url/-/whatwg-url-8.2.1.tgz", - "integrity": "sha512-2YubE1sjj5ifxievI5Ge1sckb9k/Er66HyR2c+3+I6VDUUg1TLPdYYTEbQ+DjRkS4nTxMJhgWfSfMRD2sl2EYQ==", - "requires": { - "@types/node": "*", - "@types/webidl-conversions": "*" - } - }, - "@typescript-eslint/eslint-plugin": { - "version": "5.9.0", - "resolved": "https://registry.npmjs.org/@typescript-eslint/eslint-plugin/-/eslint-plugin-5.9.0.tgz", - "integrity": "sha512-qT4lr2jysDQBQOPsCCvpPUZHjbABoTJW8V9ZzIYKHMfppJtpdtzszDYsldwhFxlhvrp7aCHeXD1Lb9M1zhwWwQ==", - "dev": true, - "requires": { - "@typescript-eslint/experimental-utils": "5.9.0", - "@typescript-eslint/scope-manager": "5.9.0", - "@typescript-eslint/type-utils": "5.9.0", - "debug": "^4.3.2", - "functional-red-black-tree": "^1.0.1", - "ignore": "^5.1.8", - "regexpp": "^3.2.0", - "semver": "^7.3.5", - "tsutils": "^3.21.0" - } - }, - "@typescript-eslint/experimental-utils": { - "version": "5.9.0", - "resolved": "https://registry.npmjs.org/@typescript-eslint/experimental-utils/-/experimental-utils-5.9.0.tgz", - "integrity": "sha512-ZnLVjBrf26dn7ElyaSKa6uDhqwvAi4jBBmHK1VxuFGPRAxhdi18ubQYSGA7SRiFiES3q9JiBOBHEBStOFkwD2g==", - "dev": true, - "requires": { - "@types/json-schema": "^7.0.9", - "@typescript-eslint/scope-manager": "5.9.0", - "@typescript-eslint/types": "5.9.0", - "@typescript-eslint/typescript-estree": "5.9.0", - "eslint-scope": "^5.1.1", - "eslint-utils": "^3.0.0" - } - }, - "@typescript-eslint/parser": { - "version": "5.9.0", - "resolved": "https://registry.npmjs.org/@typescript-eslint/parser/-/parser-5.9.0.tgz", - "integrity": "sha512-/6pOPz8yAxEt4PLzgbFRDpZmHnXCeZgPDrh/1DaVKOjvn/UPMlWhbx/gA96xRi2JxY1kBl2AmwVbyROUqys5xQ==", - "dev": true, - "requires": { - "@typescript-eslint/scope-manager": "5.9.0", - "@typescript-eslint/types": "5.9.0", - "@typescript-eslint/typescript-estree": "5.9.0", - "debug": "^4.3.2" - } - }, - "@typescript-eslint/scope-manager": { - "version": "5.9.0", - "resolved": "https://registry.npmjs.org/@typescript-eslint/scope-manager/-/scope-manager-5.9.0.tgz", - "integrity": "sha512-DKtdIL49Qxk2a8icF6whRk7uThuVz4A6TCXfjdJSwOsf+9ree7vgQWcx0KOyCdk0i9ETX666p4aMhrRhxhUkyg==", - "dev": true, - "requires": { - "@typescript-eslint/types": "5.9.0", - "@typescript-eslint/visitor-keys": "5.9.0" - } - }, - "@typescript-eslint/type-utils": { - "version": "5.9.0", - "resolved": "https://registry.npmjs.org/@typescript-eslint/type-utils/-/type-utils-5.9.0.tgz", - "integrity": "sha512-uVCb9dJXpBrK1071ri5aEW7ZHdDHAiqEjYznF3HSSvAJXyrkxGOw2Ejibz/q6BXdT8lea8CMI0CzKNFTNI6TEQ==", - "dev": true, - "requires": { - "@typescript-eslint/experimental-utils": "5.9.0", - "debug": "^4.3.2", - "tsutils": "^3.21.0" - } - }, - "@typescript-eslint/types": { - "version": "5.9.0", - "resolved": "https://registry.npmjs.org/@typescript-eslint/types/-/types-5.9.0.tgz", - "integrity": "sha512-mWp6/b56Umo1rwyGCk8fPIzb9Migo8YOniBGPAQDNC6C52SeyNGN4gsVwQTAR+RS2L5xyajON4hOLwAGwPtUwg==", - "dev": true - }, - "@typescript-eslint/typescript-estree": { - "version": "5.9.0", - "resolved": "https://registry.npmjs.org/@typescript-eslint/typescript-estree/-/typescript-estree-5.9.0.tgz", - "integrity": "sha512-kxo3xL2mB7XmiVZcECbaDwYCt3qFXz99tBSuVJR4L/sR7CJ+UNAPrYILILktGj1ppfZ/jNt/cWYbziJUlHl1Pw==", - "dev": true, - "requires": { - "@typescript-eslint/types": "5.9.0", - "@typescript-eslint/visitor-keys": "5.9.0", - "debug": "^4.3.2", - "globby": "^11.0.4", - "is-glob": "^4.0.3", - "semver": "^7.3.5", - "tsutils": "^3.21.0" - } - }, - "@typescript-eslint/visitor-keys": { - "version": "5.9.0", - "resolved": "https://registry.npmjs.org/@typescript-eslint/visitor-keys/-/visitor-keys-5.9.0.tgz", - "integrity": "sha512-6zq0mb7LV0ThExKlecvpfepiB+XEtFv/bzx7/jKSgyXTFD7qjmSu1FoiS0x3OZaiS+UIXpH2vd9O89f02RCtgw==", - "dev": true, - "requires": { - "@typescript-eslint/types": "5.9.0", - "eslint-visitor-keys": "^3.0.0" - } - }, - "@ungap/promise-all-settled": { - "version": "1.1.2", - "resolved": "https://registry.npmjs.org/@ungap/promise-all-settled/-/promise-all-settled-1.1.2.tgz", - "integrity": "sha512-sL/cEvJWAnClXw0wHk85/2L0G6Sj8UB0Ctc1TEMbKSsmpRosqhwj9gWgFRZSrBr2f9tiXISwNhCPmlfqUqyb9Q==" - }, - "@webassemblyjs/ast": { - "version": "1.11.1", - "resolved": "https://registry.npmjs.org/@webassemblyjs/ast/-/ast-1.11.1.tgz", - "integrity": "sha512-ukBh14qFLjxTQNTXocdyksN5QdM28S1CxHt2rdskFyL+xFV7VremuBLVbmCePj+URalXBENx/9Lm7lnhihtCSw==", - "requires": { - "@webassemblyjs/helper-numbers": "1.11.1", - "@webassemblyjs/helper-wasm-bytecode": "1.11.1" - } - }, - "@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==" - }, - "@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==" - }, - "@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==" - }, - "@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==", - "requires": { - "@webassemblyjs/floating-point-hex-parser": "1.11.1", - "@webassemblyjs/helper-api-error": "1.11.1", - "@xtuc/long": "4.2.2" - } - }, - "@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==" - }, - "@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==", - "requires": { - "@webassemblyjs/ast": "1.11.1", - "@webassemblyjs/helper-buffer": "1.11.1", - "@webassemblyjs/helper-wasm-bytecode": "1.11.1", - "@webassemblyjs/wasm-gen": "1.11.1" - } - }, - "@webassemblyjs/ieee754": { - "version": "1.11.1", - "resolved": "https://registry.npmjs.org/@webassemblyjs/ieee754/-/ieee754-1.11.1.tgz", - "integrity": "sha512-hJ87QIPtAMKbFq6CGTkZYJivEwZDbQUgYd3qKSadTNOhVY7p+gfP6Sr0lLRVTaG1JjFj+r3YchoqRYxNH3M0GQ==", - "requires": { - "@xtuc/ieee754": "^1.2.0" - } - }, - "@webassemblyjs/leb128": { - "version": "1.11.1", - "resolved": "https://registry.npmjs.org/@webassemblyjs/leb128/-/leb128-1.11.1.tgz", - "integrity": "sha512-BJ2P0hNZ0u+Th1YZXJpzW6miwqQUGcIHT1G/sf72gLVD9DZ5AdYTqPNbHZh6K1M5VmKvFXwGSWZADz+qBWxeRw==", - "requires": { - "@xtuc/long": "4.2.2" - } - }, - "@webassemblyjs/utf8": { - "version": "1.11.1", - "resolved": "https://registry.npmjs.org/@webassemblyjs/utf8/-/utf8-1.11.1.tgz", - "integrity": "sha512-9kqcxAEdMhiwQkHpkNiorZzqpGrodQQ2IGrHHxCy+Ozng0ofyMA0lTqiLkVs1uzTRejX+/O0EOT7KxqVPuXosQ==" - }, - "@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==", - "requires": { - "@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" - } - }, - "@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==", - "requires": { - "@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" - } - }, - "@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==", - "requires": { - "@webassemblyjs/ast": "1.11.1", - "@webassemblyjs/helper-buffer": "1.11.1", - "@webassemblyjs/wasm-gen": "1.11.1", - "@webassemblyjs/wasm-parser": "1.11.1" - } - }, - "@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==", - "requires": { - "@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" - } - }, - "@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==", - "requires": { - "@webassemblyjs/ast": "1.11.1", - "@xtuc/long": "4.2.2" - } - }, - "@webpack-cli/configtest": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/@webpack-cli/configtest/-/configtest-1.1.0.tgz", - "integrity": "sha512-ttOkEkoalEHa7RaFYpM0ErK1xc4twg3Am9hfHhL7MVqlHebnkYd2wuI/ZqTDj0cVzZho6PdinY0phFZV3O0Mzg==", - "requires": {} - }, - "@webpack-cli/info": { - "version": "1.4.0", - "resolved": "https://registry.npmjs.org/@webpack-cli/info/-/info-1.4.0.tgz", - "integrity": "sha512-F6b+Man0rwE4n0409FyAJHStYA5OIZERxmnUfLVwv0mc0V1wLad3V7jqRlMkgKBeAq07jUvglacNaa6g9lOpuw==", - "requires": { - "envinfo": "^7.7.3" - } - }, - "@webpack-cli/serve": { - "version": "1.6.0", - "resolved": "https://registry.npmjs.org/@webpack-cli/serve/-/serve-1.6.0.tgz", - "integrity": "sha512-ZkVeqEmRpBV2GHvjjUZqEai2PpUbuq8Bqd//vEYsp63J8WyexI8ppCqVS3Zs0QADf6aWuPdU+0XsPI647PVlQA==", - "requires": {} - }, - "@xtuc/ieee754": { - "version": "1.2.0", - "resolved": "https://registry.npmjs.org/@xtuc/ieee754/-/ieee754-1.2.0.tgz", - "integrity": "sha512-DX8nKgqcGwsc0eJSqYt5lwP4DH5FlHnmuWWBRy7X0NcaGR0ZtuyeESgMwTYVEtxmsNGY+qit4QYT/MIYTOTPeA==" - }, - "@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==" - }, - "abbrev": { - "version": "1.1.1", - "resolved": "https://registry.npmjs.org/abbrev/-/abbrev-1.1.1.tgz", - "integrity": "sha512-nne9/IiQ/hzIhY6pdDnbBtz7DjPTKrY00P/zvPSm5pOFkl6xuGrGnXn/VtTNNfNtAfZ9/1RtehkszU9qcTii0Q==", - "dev": true - }, - "accepts": { - "version": "1.3.7", - "resolved": "https://registry.npmjs.org/accepts/-/accepts-1.3.7.tgz", - "integrity": "sha512-Il80Qs2WjYlJIBNzNkK6KYqlVMTbZLXgHx2oT0pU/fjRHyEp+PEfEPY0R3WCwAGVOtauxh1hOxNgIf5bv7dQpA==", - "requires": { - "mime-types": "~2.1.24", - "negotiator": "0.6.2" - } - }, - "acorn": { - "version": "8.7.0", - "resolved": "https://registry.npmjs.org/acorn/-/acorn-8.7.0.tgz", - "integrity": "sha512-V/LGr1APy+PXIwKebEWrkZPwoeoF+w1jiOBUmuxuiUIaOHtob8Qc9BTrYo7VuI5fR8tqsy+buA2WFooR5olqvQ==" - }, - "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==", - "requires": {} - }, - "acorn-jsx": { - "version": "5.3.2", - "resolved": "https://registry.npmjs.org/acorn-jsx/-/acorn-jsx-5.3.2.tgz", - "integrity": "sha512-rq9s+JNhf0IChjtDXxllJ7g41oZk5SlXtp0LHwyA5cejwn7vKmKp4pPri6YEePv2PU65sAsegbXtIinmDFDXgQ==", - "requires": {} - }, - "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==" - }, - "add-stream": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/add-stream/-/add-stream-1.0.0.tgz", - "integrity": "sha1-anmQQ3ynNtXhKI25K9MmbV9csqo=", - "dev": true - }, - "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==", - "dev": true, - "requires": { - "debug": "4" - } - }, - "agentkeepalive": { - "version": "4.2.0", - "resolved": "https://registry.npmjs.org/agentkeepalive/-/agentkeepalive-4.2.0.tgz", - "integrity": "sha512-0PhAp58jZNw13UJv7NVdTGb0ZcghHUb3DrZ046JiiJY/BOaTTpbwdHq2VObPCBV8M2GPh7sgrJ3AQ8Ey468LJw==", - "dev": true, - "requires": { - "debug": "^4.1.0", - "depd": "^1.1.2", - "humanize-ms": "^1.2.1" - } - }, - "aggregate-error": { - "version": "3.1.0", - "resolved": "https://registry.npmjs.org/aggregate-error/-/aggregate-error-3.1.0.tgz", - "integrity": "sha512-4I7Td01quW/RpocfNayFdFVk1qSuoh0E7JrbRJ16nH01HhKFQ88INq9Sd+nd72zqRySlr9BmDA8xlEJ6vJMrYA==", - "dev": true, - "requires": { - "clean-stack": "^2.0.0", - "indent-string": "^4.0.0" - } - }, - "ajv": { - "version": "8.8.2", - "resolved": "https://registry.npmjs.org/ajv/-/ajv-8.8.2.tgz", - "integrity": "sha512-x9VuX+R/jcFj1DHo/fCp99esgGDWiHENrKxaCENuCxpoMCmAt/COCGVDwA7kleEpEzJjDnvh3yGoOuLu0Dtllw==", - "requires": { - "fast-deep-equal": "^3.1.1", - "json-schema-traverse": "^1.0.0", - "require-from-string": "^2.0.2", - "uri-js": "^4.2.2" - } - }, - "ajv-formats": { - "version": "2.1.1", - "resolved": "https://registry.npmjs.org/ajv-formats/-/ajv-formats-2.1.1.tgz", - "integrity": "sha512-Wx0Kx52hxE7C18hkMEggYlEifqWZtYaRgouJor+WMdPnQyEK13vgEWyVNup7SoeeoLMsr4kf5h6dOW11I15MUA==", - "requires": { - "ajv": "^8.0.0" - } - }, - "align-text": { - "version": "0.1.4", - "resolved": "https://registry.npmjs.org/align-text/-/align-text-0.1.4.tgz", - "integrity": "sha1-DNkKVhCT810KmSVsIrcGlDP60Rc=", - "requires": { - "kind-of": "^3.0.2", - "longest": "^1.0.1", - "repeat-string": "^1.5.2" - }, - "dependencies": { - "kind-of": { - "version": "3.2.2", - "resolved": "https://registry.npmjs.org/kind-of/-/kind-of-3.2.2.tgz", - "integrity": "sha1-MeohpzS6ubuw8yRm2JOupR5KPGQ=", - "requires": { - "is-buffer": "^1.1.5" - } - } - } - }, - "ansi-align": { - "version": "3.0.1", - "resolved": "https://registry.npmjs.org/ansi-align/-/ansi-align-3.0.1.tgz", - "integrity": "sha512-IOfwwBF5iczOjp/WeY4YxyjqAFMQoZufdQWDd19SEExbVLNXqvpzSJ/M7Za4/sCPmQ0+GRquoA7bGcINcxew6w==", - "dev": true, - "requires": { - "string-width": "^4.1.0" - } - }, - "ansi-colors": { - "version": "4.1.1", - "resolved": "https://registry.npmjs.org/ansi-colors/-/ansi-colors-4.1.1.tgz", - "integrity": "sha512-JoX0apGbHaUJBNl6yF+p6JAFYZ666/hhCGKN5t9QFjbJQKUU/g8MNbFDbvfrgKXvI1QpZplPOnwIo99lX/AAmA==" - }, - "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, - "requires": { - "type-fest": "^0.21.3" - }, - "dependencies": { - "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 - } - } - }, - "ansi-regex": { - "version": "5.0.1", - "resolved": "https://registry.npmjs.org/ansi-regex/-/ansi-regex-5.0.1.tgz", - "integrity": "sha512-quJQXlTSUGL2LH9SUXo8VwsY4soanhgo6LNSm84E1LBcE8s3O0wpdiRzyR9z/ZZJMlMWv37qOOb9pdJlMUEKFQ==" - }, - "ansi-styles": { - "version": "4.3.0", - "resolved": "https://registry.npmjs.org/ansi-styles/-/ansi-styles-4.3.0.tgz", - "integrity": "sha512-zbB9rCJAT1rbjiVDb2hqKFHNYLxgtk8NURxZ3IZwD3F6NtxbXZQCnnSi1Lkx+IDohdPlFp222wVALIheZJQSEg==", - "requires": { - "color-convert": "^2.0.1" - } - }, - "anymatch": { - "version": "3.1.2", - "resolved": "https://registry.npmjs.org/anymatch/-/anymatch-3.1.2.tgz", - "integrity": "sha512-P43ePfOAIupkguHUycrc4qJ9kz8ZiuOUijaETwX7THt0Y/GNK7v0aa8rY816xWjZ7rJdA5XdMcpVFTKMq+RvWg==", - "requires": { - "normalize-path": "^3.0.0", - "picomatch": "^2.0.4" - } - }, - "app-module-path": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/app-module-path/-/app-module-path-1.1.0.tgz", - "integrity": "sha1-pqxTaEUPIJufW4bpo+Smq2/nUxw=" - }, - "app-root-dir": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/app-root-dir/-/app-root-dir-1.0.2.tgz", - "integrity": "sha1-OBh+wt6nV3//Az/8sSFyaS/24Rg=" - }, - "append-transform": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/append-transform/-/append-transform-2.0.0.tgz", - "integrity": "sha512-7yeyCEurROLQJFv5Xj4lEGTy0borxepjFv1g22oAdqFu//SrAlDl1O1Nxx15SH1RoliUml6p8dwJW9jvZughhg==", - "dev": true, - "requires": { - "default-require-extensions": "^3.0.0" - } - }, - "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==", - "dev": true - }, - "archy": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/archy/-/archy-1.0.0.tgz", - "integrity": "sha1-+cjBN1fMHde8N5rHeyxipcKGjEA=", - "dev": true - }, - "are-we-there-yet": { - "version": "1.1.7", - "resolved": "https://registry.npmjs.org/are-we-there-yet/-/are-we-there-yet-1.1.7.tgz", - "integrity": "sha512-nxwy40TuMiUGqMyRHgCSWZ9FM4VAoRP4xUYSTv5ImRog+h9yISPbVH7H8fASCIzYn9wlEv4zvFL7uKDMCFQm3g==", - "dev": true, - "requires": { - "delegates": "^1.0.0", - "readable-stream": "^2.0.6" - }, - "dependencies": { - "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, - "requires": { - "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" - } - }, - "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, - "requires": { - "safe-buffer": "~5.1.0" - } - } - } - }, - "arg": { - "version": "4.1.3", - "resolved": "https://registry.npmjs.org/arg/-/arg-4.1.3.tgz", - "integrity": "sha512-58S9QDqG0Xx27YwPSt9fJxivjYl432YCwfDMfZ+71RAqUrZef7LrKQZ3LHLOwCS4FLNBplP533Zx895SeOCHvA==" - }, - "argly": { - "version": "1.2.0", - "resolved": "https://registry.npmjs.org/argly/-/argly-1.2.0.tgz", - "integrity": "sha1-KydORVGin/XnGZ0u2XiOtm7TbmA=" - }, - "argparse": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/argparse/-/argparse-2.0.1.tgz", - "integrity": "sha512-8+9WqebbFzpX9OR+Wa6O29asIogeRMzcGtAINdpMHHyAg10f05aSFVBbcEqGf/PXw1EjAZ+q2/bEBg3DvurK3Q==" - }, - "arr-diff": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/arr-diff/-/arr-diff-2.0.0.tgz", - "integrity": "sha1-jzuCf5Vai9ZpaX5KQlasPOrjVs8=", - "requires": { - "arr-flatten": "^1.0.1" - } - }, - "arr-flatten": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/arr-flatten/-/arr-flatten-1.1.0.tgz", - "integrity": "sha512-L3hKV5R/p5o81R7O02IGnwpDmkp6E982XhtbuwSe3O4qOtMMMtodicASA1Cny2U+aCXcNpml+m4dPsvsJ3jatg==" - }, - "array-differ": { - "version": "3.0.0", - "resolved": "https://registry.npmjs.org/array-differ/-/array-differ-3.0.0.tgz", - "integrity": "sha512-THtfYS6KtME/yIAhKjZ2ul7XI96lQGHRputJQHO80LAWQnuGP4iCIN8vdMRboGbIEYBwU33q8Tch1os2+X0kMg==", - "dev": true - }, - "array-flatten": { - "version": "1.1.1", - "resolved": "https://registry.npmjs.org/array-flatten/-/array-flatten-1.1.1.tgz", - "integrity": "sha1-ml9pkFGx5wczKPKgCJaLZOopVdI=" - }, - "array-ify": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/array-ify/-/array-ify-1.0.0.tgz", - "integrity": "sha1-nlKHYrSpBmrRY6aWKjZEGOlibs4=", - "dev": true - }, - "array-includes": { - "version": "3.1.4", - "resolved": "https://registry.npmjs.org/array-includes/-/array-includes-3.1.4.tgz", - "integrity": "sha512-ZTNSQkmWumEbiHO2GF4GmWxYVTiQyJy2XOTa15sdQSrvKn7l+180egQMqlrMOUMCyLMD7pmyQe4mMDUT6Behrw==", - "dev": true, - "requires": { - "call-bind": "^1.0.2", - "define-properties": "^1.1.3", - "es-abstract": "^1.19.1", - "get-intrinsic": "^1.1.1", - "is-string": "^1.0.7" - } - }, - "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 - }, - "array-unique": { - "version": "0.2.1", - "resolved": "https://registry.npmjs.org/array-unique/-/array-unique-0.2.1.tgz", - "integrity": "sha1-odl8yvy8JiXMcPrc6zalDFiwGlM=" - }, - "array.prototype.flat": { - "version": "1.2.5", - "resolved": "https://registry.npmjs.org/array.prototype.flat/-/array.prototype.flat-1.2.5.tgz", - "integrity": "sha512-KaYU+S+ndVqyUnignHftkwc58o3uVU1jzczILJ1tN2YaIZpFIKBiP/x/j97E5MVPsaCloPbqWLB/8qCTVvT2qg==", - "dev": true, - "requires": { - "call-bind": "^1.0.2", - "define-properties": "^1.1.3", - "es-abstract": "^1.19.0" - } - }, - "arrify": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/arrify/-/arrify-1.0.1.tgz", - "integrity": "sha1-iYUI2iIm84DfkEcoRWhJwVAaSw0=" - }, - "asap": { - "version": "2.0.6", - "resolved": "https://registry.npmjs.org/asap/-/asap-2.0.6.tgz", - "integrity": "sha1-5QNHYR1+aQlDIIu9r+vLwvuGbUY=", - "dev": true - }, - "asn1": { - "version": "0.2.6", - "resolved": "https://registry.npmjs.org/asn1/-/asn1-0.2.6.tgz", - "integrity": "sha512-ix/FxPn0MDjeyJ7i/yoHGFt/EX6LyNbxSEhPPXODPL+KB0VPk86UYfL0lMdy+KCnv+fmvIzySwaK5COwqVbWTQ==", - "dev": true, - "requires": { - "safer-buffer": "~2.1.0" - } - }, - "asn1.js": { - "version": "5.4.1", - "resolved": "https://registry.npmjs.org/asn1.js/-/asn1.js-5.4.1.tgz", - "integrity": "sha512-+I//4cYPccV8LdmBLiX8CYvf9Sp3vQsrqu2QNXRcrbiWvcx/UdlFiqUJJzxRQxgsZmvhXhn4cSKeSmoFjVdupA==", - "optional": true, - "requires": { - "bn.js": "^4.0.0", - "inherits": "^2.0.1", - "minimalistic-assert": "^1.0.0", - "safer-buffer": "^2.1.0" - } - }, - "assert": { - "version": "1.5.0", - "resolved": "https://registry.npmjs.org/assert/-/assert-1.5.0.tgz", - "integrity": "sha512-EDsgawzwoun2CZkCgtxJbv392v4nbk9XDD06zI+kQYoBM/3RBWLlEyJARDOmhAAosBjWACEkKL6S+lIZtcAubA==", - "requires": { - "object-assign": "^4.1.1", - "util": "0.10.3" - }, - "dependencies": { - "inherits": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/inherits/-/inherits-2.0.1.tgz", - "integrity": "sha1-sX0I0ya0Qj5Wjv9xn5GwscvfafE=" - }, - "util": { - "version": "0.10.3", - "resolved": "https://registry.npmjs.org/util/-/util-0.10.3.tgz", - "integrity": "sha1-evsa/lCAUkZInj23/g7TeTNqwPk=", - "requires": { - "inherits": "2.0.1" - } - } - } - }, - "assert-plus": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/assert-plus/-/assert-plus-1.0.0.tgz", - "integrity": "sha1-8S4PPF13sLHN2RRpQuTpbB5N1SU=", - "dev": true - }, - "assertion-error": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/assertion-error/-/assertion-error-1.1.0.tgz", - "integrity": "sha512-jgsaNduz+ndvGyFt3uSuWqvy4lCnIJiovtouQN5JZHOKCS2QuhEdbcQHFhVksz2N2U9hXJo8odG7ETyWlEeuDw==" - }, - "async": { - "version": "3.2.2", - "resolved": "https://registry.npmjs.org/async/-/async-3.2.2.tgz", - "integrity": "sha512-H0E+qZaDEfx/FY4t7iLRv1W2fFI6+pyCeTw1uN20AQPiwqwM6ojPxHxdLv4z8hi2DtnW9BOckSspLucW7pIE5g==" - }, - "async-limiter": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/async-limiter/-/async-limiter-1.0.1.tgz", - "integrity": "sha512-csOlWGAcRFJaI6m+F2WKdnMKr4HhdhFVBk0H/QbJFMCr+uO2kwohwXQPxw/9OCxp05r5ghVBFSyioixx3gfkNQ==" - }, - "asynckit": { - "version": "0.4.0", - "resolved": "https://registry.npmjs.org/asynckit/-/asynckit-0.4.0.tgz", - "integrity": "sha1-x57Zf380y48robyXkLzDZkdLS3k=" - }, - "at-least-node": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/at-least-node/-/at-least-node-1.0.0.tgz", - "integrity": "sha512-+q/t7Ekv1EDY2l6Gda6LLiX14rU9TV20Wa3ofeQmwPFZbOMo9DXrLbOjFaaclkXKWidIaopwAObQDqwWtGUjqg==", - "dev": true - }, - "aws-sign2": { - "version": "0.7.0", - "resolved": "https://registry.npmjs.org/aws-sign2/-/aws-sign2-0.7.0.tgz", - "integrity": "sha1-tG6JCTSpWR8tL2+G1+ap8bP+dqg=", - "dev": true - }, - "aws4": { - "version": "1.11.0", - "resolved": "https://registry.npmjs.org/aws4/-/aws4-1.11.0.tgz", - "integrity": "sha512-xh1Rl34h6Fi1DC2WWKfxUTVqRsNnr6LsKz2+hfwDxQJWmrx8+c7ylaqBMcHfl1U1r2dsifOvKX3LQuLNZ+XSvA==", - "dev": true - }, - "axios": { - "version": "0.24.0", - "resolved": "https://registry.npmjs.org/axios/-/axios-0.24.0.tgz", - "integrity": "sha512-Q6cWsys88HoPgAaFAVUb0WpPk0O8iTeisR9IMqy9G8AbO4NlpVknrnQS03zzF9PGAWgO3cgletO3VjV/P7VztA==", - "requires": { - "follow-redirects": "^1.14.4" - } - }, - "babel-code-frame": { - "version": "6.26.0", - "resolved": "https://registry.npmjs.org/babel-code-frame/-/babel-code-frame-6.26.0.tgz", - "integrity": "sha1-Y/1D99weO7fONZR9uP42mj9Yx0s=", - "requires": { - "chalk": "^1.1.3", - "esutils": "^2.0.2", - "js-tokens": "^3.0.2" - }, - "dependencies": { - "ansi-regex": { - "version": "2.1.1", - "resolved": "https://registry.npmjs.org/ansi-regex/-/ansi-regex-2.1.1.tgz", - "integrity": "sha1-w7M6te42DYbg5ijwRorn7yfWVN8=" - }, - "ansi-styles": { - "version": "2.2.1", - "resolved": "https://registry.npmjs.org/ansi-styles/-/ansi-styles-2.2.1.tgz", - "integrity": "sha1-tDLdM1i2NM914eRmQ2gkBTPB3b4=" - }, - "chalk": { - "version": "1.1.3", - "resolved": "https://registry.npmjs.org/chalk/-/chalk-1.1.3.tgz", - "integrity": "sha1-qBFcVeSnAv5NFQq9OHKCKn4J/Jg=", - "requires": { - "ansi-styles": "^2.2.1", - "escape-string-regexp": "^1.0.2", - "has-ansi": "^2.0.0", - "strip-ansi": "^3.0.0", - "supports-color": "^2.0.0" - } - }, - "escape-string-regexp": { - "version": "1.0.5", - "resolved": "https://registry.npmjs.org/escape-string-regexp/-/escape-string-regexp-1.0.5.tgz", - "integrity": "sha1-G2HAViGQqN/2rjuyzwIAyhMLhtQ=" - }, - "js-tokens": { - "version": "3.0.2", - "resolved": "https://registry.npmjs.org/js-tokens/-/js-tokens-3.0.2.tgz", - "integrity": "sha1-mGbfOVECEw449/mWvOtlRDIJwls=" - }, - "strip-ansi": { - "version": "3.0.1", - "resolved": "https://registry.npmjs.org/strip-ansi/-/strip-ansi-3.0.1.tgz", - "integrity": "sha1-ajhfuIU9lS1f8F0Oiq+UJ43GPc8=", - "requires": { - "ansi-regex": "^2.0.0" - } - }, - "supports-color": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/supports-color/-/supports-color-2.0.0.tgz", - "integrity": "sha1-U10EXOa2Nj+kARcIRimZXp3zJMc=" - } - } - }, - "babel-core": { - "version": "6.26.3", - "resolved": "https://registry.npmjs.org/babel-core/-/babel-core-6.26.3.tgz", - "integrity": "sha512-6jyFLuDmeidKmUEb3NM+/yawG0M2bDZ9Z1qbZP59cyHLz8kYGKYwpJP0UwUKKUiTRNvxfLesJnTedqczP7cTDA==", - "requires": { - "babel-code-frame": "^6.26.0", - "babel-generator": "^6.26.0", - "babel-helpers": "^6.24.1", - "babel-messages": "^6.23.0", - "babel-register": "^6.26.0", - "babel-runtime": "^6.26.0", - "babel-template": "^6.26.0", - "babel-traverse": "^6.26.0", - "babel-types": "^6.26.0", - "babylon": "^6.18.0", - "convert-source-map": "^1.5.1", - "debug": "^2.6.9", - "json5": "^0.5.1", - "lodash": "^4.17.4", - "minimatch": "^3.0.4", - "path-is-absolute": "^1.0.1", - "private": "^0.1.8", - "slash": "^1.0.0", - "source-map": "^0.5.7" - }, - "dependencies": { - "debug": { - "version": "2.6.9", - "resolved": "https://registry.npmjs.org/debug/-/debug-2.6.9.tgz", - "integrity": "sha512-bC7ElrdJaJnPbAP+1EotYvqZsb3ecl5wi6Bfi6BJTUcNowp6cvspg0jXznRTKDjm/E7AdgFBVeAPVMNcKGsHMA==", - "requires": { - "ms": "2.0.0" - } - }, - "json5": { - "version": "0.5.1", - "resolved": "https://registry.npmjs.org/json5/-/json5-0.5.1.tgz", - "integrity": "sha1-Hq3nrMASA0rYTiOWdn6tn6VJWCE=" - }, - "ms": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/ms/-/ms-2.0.0.tgz", - "integrity": "sha1-VgiurfwAvmwpAd9fmGF4jeDVl8g=" - }, - "slash": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/slash/-/slash-1.0.0.tgz", - "integrity": "sha1-xB8vbDn8FtHNF61LXYlhFK5HDVU=" - }, - "source-map": { - "version": "0.5.7", - "resolved": "https://registry.npmjs.org/source-map/-/source-map-0.5.7.tgz", - "integrity": "sha1-igOdLRAh0i0eoUyA2OpGi6LvP8w=" - } - } - }, - "babel-generator": { - "version": "6.26.1", - "resolved": "https://registry.npmjs.org/babel-generator/-/babel-generator-6.26.1.tgz", - "integrity": "sha512-HyfwY6ApZj7BYTcJURpM5tznulaBvyio7/0d4zFOeMPUmfxkCjHocCuoLa2SAGzBI8AREcH3eP3758F672DppA==", - "requires": { - "babel-messages": "^6.23.0", - "babel-runtime": "^6.26.0", - "babel-types": "^6.26.0", - "detect-indent": "^4.0.0", - "jsesc": "^1.3.0", - "lodash": "^4.17.4", - "source-map": "^0.5.7", - "trim-right": "^1.0.1" - }, - "dependencies": { - "detect-indent": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/detect-indent/-/detect-indent-4.0.0.tgz", - "integrity": "sha1-920GQ1LN9Docts5hnE7jqUdd4gg=", - "requires": { - "repeating": "^2.0.0" - } - }, - "jsesc": { - "version": "1.3.0", - "resolved": "https://registry.npmjs.org/jsesc/-/jsesc-1.3.0.tgz", - "integrity": "sha1-RsP+yMGJKxKwgz25vHYiF226s0s=" - }, - "source-map": { - "version": "0.5.7", - "resolved": "https://registry.npmjs.org/source-map/-/source-map-0.5.7.tgz", - "integrity": "sha1-igOdLRAh0i0eoUyA2OpGi6LvP8w=" - } - } - }, - "babel-helper-builder-binary-assignment-operator-visitor": { - "version": "6.24.1", - "resolved": "https://registry.npmjs.org/babel-helper-builder-binary-assignment-operator-visitor/-/babel-helper-builder-binary-assignment-operator-visitor-6.24.1.tgz", - "integrity": "sha1-zORReto1b0IgvK6KAsKzRvmlZmQ=", - "requires": { - "babel-helper-explode-assignable-expression": "^6.24.1", - "babel-runtime": "^6.22.0", - "babel-types": "^6.24.1" - } - }, - "babel-helper-call-delegate": { - "version": "6.24.1", - "resolved": "https://registry.npmjs.org/babel-helper-call-delegate/-/babel-helper-call-delegate-6.24.1.tgz", - "integrity": "sha1-7Oaqzdx25Bw0YfiL/Fdb0Nqi340=", - "requires": { - "babel-helper-hoist-variables": "^6.24.1", - "babel-runtime": "^6.22.0", - "babel-traverse": "^6.24.1", - "babel-types": "^6.24.1" - } - }, - "babel-helper-define-map": { - "version": "6.26.0", - "resolved": "https://registry.npmjs.org/babel-helper-define-map/-/babel-helper-define-map-6.26.0.tgz", - "integrity": "sha1-pfVtq0GiX5fstJjH66ypgZ+Vvl8=", - "requires": { - "babel-helper-function-name": "^6.24.1", - "babel-runtime": "^6.26.0", - "babel-types": "^6.26.0", - "lodash": "^4.17.4" - } - }, - "babel-helper-explode-assignable-expression": { - "version": "6.24.1", - "resolved": "https://registry.npmjs.org/babel-helper-explode-assignable-expression/-/babel-helper-explode-assignable-expression-6.24.1.tgz", - "integrity": "sha1-8luCz33BBDPFX3BZLVdGQArCLKo=", - "requires": { - "babel-runtime": "^6.22.0", - "babel-traverse": "^6.24.1", - "babel-types": "^6.24.1" - } - }, - "babel-helper-function-name": { - "version": "6.24.1", - "resolved": "https://registry.npmjs.org/babel-helper-function-name/-/babel-helper-function-name-6.24.1.tgz", - "integrity": "sha1-00dbjAPtmCQqJbSDUasYOZ01gKk=", - "requires": { - "babel-helper-get-function-arity": "^6.24.1", - "babel-runtime": "^6.22.0", - "babel-template": "^6.24.1", - "babel-traverse": "^6.24.1", - "babel-types": "^6.24.1" - } - }, - "babel-helper-get-function-arity": { - "version": "6.24.1", - "resolved": "https://registry.npmjs.org/babel-helper-get-function-arity/-/babel-helper-get-function-arity-6.24.1.tgz", - "integrity": "sha1-j3eCqpNAfEHTqlCQj4mwMbG2hT0=", - "requires": { - "babel-runtime": "^6.22.0", - "babel-types": "^6.24.1" - } - }, - "babel-helper-hoist-variables": { - "version": "6.24.1", - "resolved": "https://registry.npmjs.org/babel-helper-hoist-variables/-/babel-helper-hoist-variables-6.24.1.tgz", - "integrity": "sha1-HssnaJydJVE+rbyZFKc/VAi+enY=", - "requires": { - "babel-runtime": "^6.22.0", - "babel-types": "^6.24.1" - } - }, - "babel-helper-optimise-call-expression": { - "version": "6.24.1", - "resolved": "https://registry.npmjs.org/babel-helper-optimise-call-expression/-/babel-helper-optimise-call-expression-6.24.1.tgz", - "integrity": "sha1-96E0J7qfc/j0+pk8VKl4gtEkQlc=", - "requires": { - "babel-runtime": "^6.22.0", - "babel-types": "^6.24.1" - } - }, - "babel-helper-regex": { - "version": "6.26.0", - "resolved": "https://registry.npmjs.org/babel-helper-regex/-/babel-helper-regex-6.26.0.tgz", - "integrity": "sha1-MlxZ+QL4LyS3T6zu0DY5VPZJXnI=", - "requires": { - "babel-runtime": "^6.26.0", - "babel-types": "^6.26.0", - "lodash": "^4.17.4" - } - }, - "babel-helper-remap-async-to-generator": { - "version": "6.24.1", - "resolved": "https://registry.npmjs.org/babel-helper-remap-async-to-generator/-/babel-helper-remap-async-to-generator-6.24.1.tgz", - "integrity": "sha1-XsWBgnrXI/7N04HxySg5BnbkVRs=", - "requires": { - "babel-helper-function-name": "^6.24.1", - "babel-runtime": "^6.22.0", - "babel-template": "^6.24.1", - "babel-traverse": "^6.24.1", - "babel-types": "^6.24.1" - } - }, - "babel-helper-replace-supers": { - "version": "6.24.1", - "resolved": "https://registry.npmjs.org/babel-helper-replace-supers/-/babel-helper-replace-supers-6.24.1.tgz", - "integrity": "sha1-v22/5Dk40XNpohPKiov3S2qQqxo=", - "requires": { - "babel-helper-optimise-call-expression": "^6.24.1", - "babel-messages": "^6.23.0", - "babel-runtime": "^6.22.0", - "babel-template": "^6.24.1", - "babel-traverse": "^6.24.1", - "babel-types": "^6.24.1" - } - }, - "babel-helpers": { - "version": "6.24.1", - "resolved": "https://registry.npmjs.org/babel-helpers/-/babel-helpers-6.24.1.tgz", - "integrity": "sha1-NHHenK7DiOXIUOWX5Yom3fN2ArI=", - "requires": { - "babel-runtime": "^6.22.0", - "babel-template": "^6.24.1" - } - }, - "babel-loader": { - "version": "8.2.3", - "resolved": "https://registry.npmjs.org/babel-loader/-/babel-loader-8.2.3.tgz", - "integrity": "sha512-n4Zeta8NC3QAsuyiizu0GkmRcQ6clkV9WFUnUf1iXP//IeSKbWjofW3UHyZVwlOB4y039YQKefawyTn64Zwbuw==", - "requires": { - "find-cache-dir": "^3.3.1", - "loader-utils": "^1.4.0", - "make-dir": "^3.1.0", - "schema-utils": "^2.6.5" - } - }, - "babel-messages": { - "version": "6.23.0", - "resolved": "https://registry.npmjs.org/babel-messages/-/babel-messages-6.23.0.tgz", - "integrity": "sha1-8830cDhYA1sqKVHG7F7fbGLyYw4=", - "requires": { - "babel-runtime": "^6.22.0" - } - }, - "babel-plugin-check-es2015-constants": { - "version": "6.22.0", - "resolved": "https://registry.npmjs.org/babel-plugin-check-es2015-constants/-/babel-plugin-check-es2015-constants-6.22.0.tgz", - "integrity": "sha1-NRV7EBQm/S/9PaP3XH0ekYNbv4o=", - "requires": { - "babel-runtime": "^6.22.0" - } - }, - "babel-plugin-dynamic-import-node": { - "version": "2.3.3", - "resolved": "https://registry.npmjs.org/babel-plugin-dynamic-import-node/-/babel-plugin-dynamic-import-node-2.3.3.tgz", - "integrity": "sha512-jZVI+s9Zg3IqA/kdi0i6UDCybUI3aSBLnglhYbSSjKlV7yF1F/5LWv8MakQmvYpnbJDS6fcBL2KzHSxNCMtWSQ==", - "requires": { - "object.assign": "^4.1.0" - } - }, - "babel-plugin-istanbul": { - "version": "4.1.6", - "resolved": "https://registry.npmjs.org/babel-plugin-istanbul/-/babel-plugin-istanbul-4.1.6.tgz", - "integrity": "sha512-PWP9FQ1AhZhS01T/4qLSKoHGY/xvkZdVBGlKM/HuxxS3+sC66HhTNR7+MpbO/so/cz/wY94MeSWJuP1hXIPfwQ==", - "requires": { - "babel-plugin-syntax-object-rest-spread": "^6.13.0", - "find-up": "^2.1.0", - "istanbul-lib-instrument": "^1.10.1", - "test-exclude": "^4.2.1" - }, - "dependencies": { - "braces": { - "version": "1.8.5", - "resolved": "https://registry.npmjs.org/braces/-/braces-1.8.5.tgz", - "integrity": "sha1-uneWLhLf+WnWt2cR6RS3N4V79qc=", - "requires": { - "expand-range": "^1.8.1", - "preserve": "^0.2.0", - "repeat-element": "^1.1.2" - } - }, - "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==" - }, - "is-extglob": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/is-extglob/-/is-extglob-1.0.0.tgz", - "integrity": "sha1-rEaBd8SUNAWgkvyPKXYMb/xiBsA=" - }, - "is-glob": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/is-glob/-/is-glob-2.0.1.tgz", - "integrity": "sha1-0Jb5JqPe1WAPP9/ZEZjLCIjC2GM=", - "requires": { - "is-extglob": "^1.0.0" - } - }, - "istanbul-lib-coverage": { - "version": "1.2.1", - "resolved": "https://registry.npmjs.org/istanbul-lib-coverage/-/istanbul-lib-coverage-1.2.1.tgz", - "integrity": "sha512-PzITeunAgyGbtY1ibVIUiV679EFChHjoMNRibEIobvmrCRaIgwLxNucOSimtNWUhEib/oO7QY2imD75JVgCJWQ==" - }, - "istanbul-lib-instrument": { - "version": "1.10.2", - "resolved": "https://registry.npmjs.org/istanbul-lib-instrument/-/istanbul-lib-instrument-1.10.2.tgz", - "integrity": "sha512-aWHxfxDqvh/ZlxR8BBaEPVSWDPUkGD63VjGQn3jcw8jCp7sHEMKcrj4xfJn/ABzdMEHiQNyvDQhqm5o8+SQg7A==", - "requires": { - "babel-generator": "^6.18.0", - "babel-template": "^6.16.0", - "babel-traverse": "^6.18.0", - "babel-types": "^6.18.0", - "babylon": "^6.18.0", - "istanbul-lib-coverage": "^1.2.1", - "semver": "^5.3.0" - } - }, - "kind-of": { - "version": "3.2.2", - "resolved": "https://registry.npmjs.org/kind-of/-/kind-of-3.2.2.tgz", - "integrity": "sha1-MeohpzS6ubuw8yRm2JOupR5KPGQ=", - "requires": { - "is-buffer": "^1.1.5" - } - }, - "load-json-file": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/load-json-file/-/load-json-file-1.1.0.tgz", - "integrity": "sha1-lWkFcI1YtLq0wiYbBPWfMcmTdMA=", - "requires": { - "graceful-fs": "^4.1.2", - "parse-json": "^2.2.0", - "pify": "^2.0.0", - "pinkie-promise": "^2.0.0", - "strip-bom": "^2.0.0" - } - }, - "micromatch": { - "version": "2.3.11", - "resolved": "https://registry.npmjs.org/micromatch/-/micromatch-2.3.11.tgz", - "integrity": "sha1-hmd8l9FyCzY0MdBNDRUpO9OMFWU=", - "requires": { - "arr-diff": "^2.0.0", - "array-unique": "^0.2.1", - "braces": "^1.8.2", - "expand-brackets": "^0.1.4", - "extglob": "^0.3.1", - "filename-regex": "^2.0.0", - "is-extglob": "^1.0.0", - "is-glob": "^2.0.1", - "kind-of": "^3.0.2", - "normalize-path": "^2.0.1", - "object.omit": "^2.0.0", - "parse-glob": "^3.0.4", - "regex-cache": "^0.4.2" - } - }, - "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==", - "requires": { - "hosted-git-info": "^2.1.4", - "resolve": "^1.10.0", - "semver": "2 || 3 || 4 || 5", - "validate-npm-package-license": "^3.0.1" - } - }, - "normalize-path": { - "version": "2.1.1", - "resolved": "https://registry.npmjs.org/normalize-path/-/normalize-path-2.1.1.tgz", - "integrity": "sha1-GrKLVW4Zg2Oowab35vogE3/mrtk=", - "requires": { - "remove-trailing-separator": "^1.0.1" - } - }, - "parse-json": { - "version": "2.2.0", - "resolved": "https://registry.npmjs.org/parse-json/-/parse-json-2.2.0.tgz", - "integrity": "sha1-9ID0BDTvgHQfhGkJn43qGPVaTck=", - "requires": { - "error-ex": "^1.2.0" - } - }, - "path-exists": { - "version": "2.1.0", - "resolved": "https://registry.npmjs.org/path-exists/-/path-exists-2.1.0.tgz", - "integrity": "sha1-D+tsZPD8UY2adU3V77YscCJ2H0s=", - "requires": { - "pinkie-promise": "^2.0.0" - } - }, - "path-type": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/path-type/-/path-type-1.1.0.tgz", - "integrity": "sha1-WcRPfuSR2nBNpBXaWkBwuk+P5EE=", - "requires": { - "graceful-fs": "^4.1.2", - "pify": "^2.0.0", - "pinkie-promise": "^2.0.0" - } - }, - "pify": { - "version": "2.3.0", - "resolved": "https://registry.npmjs.org/pify/-/pify-2.3.0.tgz", - "integrity": "sha1-7RQaasBDqEnqWISY59yosVMw6Qw=" - }, - "read-pkg": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/read-pkg/-/read-pkg-1.1.0.tgz", - "integrity": "sha1-9f+qXs0pyzHAR0vKfXVra7KePyg=", - "requires": { - "load-json-file": "^1.0.0", - "normalize-package-data": "^2.3.2", - "path-type": "^1.0.0" - } - }, - "read-pkg-up": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/read-pkg-up/-/read-pkg-up-1.0.1.tgz", - "integrity": "sha1-nWPBMnbAZZGNV/ACpX9AobZD+wI=", - "requires": { - "find-up": "^1.0.0", - "read-pkg": "^1.0.0" - }, - "dependencies": { - "find-up": { - "version": "1.1.2", - "resolved": "https://registry.npmjs.org/find-up/-/find-up-1.1.2.tgz", - "integrity": "sha1-ay6YIrGizgpgq2TWEOzK1TyyTQ8=", - "requires": { - "path-exists": "^2.0.0", - "pinkie-promise": "^2.0.0" - } - } - } - }, - "require-main-filename": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/require-main-filename/-/require-main-filename-1.0.1.tgz", - "integrity": "sha1-l/cXtp1IeE9fUmpsWqj/3aBVpNE=" - }, - "semver": { - "version": "5.7.1", - "resolved": "https://registry.npmjs.org/semver/-/semver-5.7.1.tgz", - "integrity": "sha512-sauaDf/PZdVgrLTNYHRtpXa1iRiKcaebiKQ1BJdpQlWH2lCvexQdX55snPFyK7QzpudqbCI0qXFfOasHdyNDGQ==" - }, - "strip-bom": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/strip-bom/-/strip-bom-2.0.0.tgz", - "integrity": "sha1-YhmoVhZSBJHzV4i9vxRHqZx+aw4=", - "requires": { - "is-utf8": "^0.2.0" - } - }, - "test-exclude": { - "version": "4.2.3", - "resolved": "https://registry.npmjs.org/test-exclude/-/test-exclude-4.2.3.tgz", - "integrity": "sha512-SYbXgY64PT+4GAL2ocI3HwPa4Q4TBKm0cwAVeKOt/Aoc0gSpNRjJX8w0pA1LMKZ3LBmd8pYBqApFNQLII9kavA==", - "requires": { - "arrify": "^1.0.1", - "micromatch": "^2.3.11", - "object-assign": "^4.1.0", - "read-pkg-up": "^1.0.1", - "require-main-filename": "^1.0.1" - } - } - } - }, - "babel-plugin-polyfill-corejs2": { - "version": "0.3.0", - "resolved": "https://registry.npmjs.org/babel-plugin-polyfill-corejs2/-/babel-plugin-polyfill-corejs2-0.3.0.tgz", - "integrity": "sha512-wMDoBJ6uG4u4PNFh72Ty6t3EgfA91puCuAwKIazbQlci+ENb/UU9A3xG5lutjUIiXCIn1CY5L15r9LimiJyrSA==", - "requires": { - "@babel/compat-data": "^7.13.11", - "@babel/helper-define-polyfill-provider": "^0.3.0", - "semver": "^6.1.1" - }, - "dependencies": { - "semver": { - "version": "6.3.0", - "resolved": "https://registry.npmjs.org/semver/-/semver-6.3.0.tgz", - "integrity": "sha512-b39TBaTSfV6yBrapU89p5fKekE2m/NwnDocOVruQFS1/veMgdzuPcnOM34M6CwxW8jH/lxEa5rBoDeUwu5HHTw==" - } - } - }, - "babel-plugin-polyfill-corejs3": { - "version": "0.4.0", - "resolved": "https://registry.npmjs.org/babel-plugin-polyfill-corejs3/-/babel-plugin-polyfill-corejs3-0.4.0.tgz", - "integrity": "sha512-YxFreYwUfglYKdLUGvIF2nJEsGwj+RhWSX/ije3D2vQPOXuyMLMtg/cCGMDpOA7Nd+MwlNdnGODbd2EwUZPlsw==", - "requires": { - "@babel/helper-define-polyfill-provider": "^0.3.0", - "core-js-compat": "^3.18.0" - } - }, - "babel-plugin-polyfill-regenerator": { - "version": "0.3.0", - "resolved": "https://registry.npmjs.org/babel-plugin-polyfill-regenerator/-/babel-plugin-polyfill-regenerator-0.3.0.tgz", - "integrity": "sha512-dhAPTDLGoMW5/84wkgwiLRwMnio2i1fUe53EuvtKMv0pn2p3S8OCoV1xAzfJPl0KOX7IB89s2ib85vbYiea3jg==", - "requires": { - "@babel/helper-define-polyfill-provider": "^0.3.0" - } - }, - "babel-plugin-syntax-async-functions": { - "version": "6.13.0", - "resolved": "https://registry.npmjs.org/babel-plugin-syntax-async-functions/-/babel-plugin-syntax-async-functions-6.13.0.tgz", - "integrity": "sha1-ytnK0RkbWtY0vzCuCHI5HgZHvpU=" - }, - "babel-plugin-syntax-exponentiation-operator": { - "version": "6.13.0", - "resolved": "https://registry.npmjs.org/babel-plugin-syntax-exponentiation-operator/-/babel-plugin-syntax-exponentiation-operator-6.13.0.tgz", - "integrity": "sha1-nufoM3KQ2pUoggGmpX9BcDF4MN4=" - }, - "babel-plugin-syntax-object-rest-spread": { - "version": "6.13.0", - "resolved": "https://registry.npmjs.org/babel-plugin-syntax-object-rest-spread/-/babel-plugin-syntax-object-rest-spread-6.13.0.tgz", - "integrity": "sha1-/WU28rzhODb/o6VFjEkDpZe7O/U=" - }, - "babel-plugin-syntax-trailing-function-commas": { - "version": "6.22.0", - "resolved": "https://registry.npmjs.org/babel-plugin-syntax-trailing-function-commas/-/babel-plugin-syntax-trailing-function-commas-6.22.0.tgz", - "integrity": "sha1-ugNgk3+NBuQBgKQ/4NVhb/9TLPM=" - }, - "babel-plugin-transform-async-to-generator": { - "version": "6.24.1", - "resolved": "https://registry.npmjs.org/babel-plugin-transform-async-to-generator/-/babel-plugin-transform-async-to-generator-6.24.1.tgz", - "integrity": "sha1-ZTbjeK/2yx1VF6wOQOs+n8jQh2E=", - "requires": { - "babel-helper-remap-async-to-generator": "^6.24.1", - "babel-plugin-syntax-async-functions": "^6.8.0", - "babel-runtime": "^6.22.0" - } - }, - "babel-plugin-transform-es2015-arrow-functions": { - "version": "6.22.0", - "resolved": "https://registry.npmjs.org/babel-plugin-transform-es2015-arrow-functions/-/babel-plugin-transform-es2015-arrow-functions-6.22.0.tgz", - "integrity": "sha1-RSaSy3EdX3ncf4XkQM5BufJE0iE=", - "requires": { - "babel-runtime": "^6.22.0" - } - }, - "babel-plugin-transform-es2015-block-scoped-functions": { - "version": "6.22.0", - "resolved": "https://registry.npmjs.org/babel-plugin-transform-es2015-block-scoped-functions/-/babel-plugin-transform-es2015-block-scoped-functions-6.22.0.tgz", - "integrity": "sha1-u8UbSflk1wy42OC5ToICRs46YUE=", - "requires": { - "babel-runtime": "^6.22.0" - } - }, - "babel-plugin-transform-es2015-block-scoping": { - "version": "6.26.0", - "resolved": "https://registry.npmjs.org/babel-plugin-transform-es2015-block-scoping/-/babel-plugin-transform-es2015-block-scoping-6.26.0.tgz", - "integrity": "sha1-1w9SmcEwjQXBL0Y4E7CgnnOxiV8=", - "requires": { - "babel-runtime": "^6.26.0", - "babel-template": "^6.26.0", - "babel-traverse": "^6.26.0", - "babel-types": "^6.26.0", - "lodash": "^4.17.4" - } - }, - "babel-plugin-transform-es2015-classes": { - "version": "6.24.1", - "resolved": "https://registry.npmjs.org/babel-plugin-transform-es2015-classes/-/babel-plugin-transform-es2015-classes-6.24.1.tgz", - "integrity": "sha1-WkxYpQyclGHlZLSyo7+ryXolhNs=", - "requires": { - "babel-helper-define-map": "^6.24.1", - "babel-helper-function-name": "^6.24.1", - "babel-helper-optimise-call-expression": "^6.24.1", - "babel-helper-replace-supers": "^6.24.1", - "babel-messages": "^6.23.0", - "babel-runtime": "^6.22.0", - "babel-template": "^6.24.1", - "babel-traverse": "^6.24.1", - "babel-types": "^6.24.1" - } - }, - "babel-plugin-transform-es2015-computed-properties": { - "version": "6.24.1", - "resolved": "https://registry.npmjs.org/babel-plugin-transform-es2015-computed-properties/-/babel-plugin-transform-es2015-computed-properties-6.24.1.tgz", - "integrity": "sha1-b+Ko0WiV1WNPTNmZttNICjCBWbM=", - "requires": { - "babel-runtime": "^6.22.0", - "babel-template": "^6.24.1" - } - }, - "babel-plugin-transform-es2015-destructuring": { - "version": "6.23.0", - "resolved": "https://registry.npmjs.org/babel-plugin-transform-es2015-destructuring/-/babel-plugin-transform-es2015-destructuring-6.23.0.tgz", - "integrity": "sha1-mXux8auWf2gtKwh2/jWNYOdlxW0=", - "requires": { - "babel-runtime": "^6.22.0" - } - }, - "babel-plugin-transform-es2015-duplicate-keys": { - "version": "6.24.1", - "resolved": "https://registry.npmjs.org/babel-plugin-transform-es2015-duplicate-keys/-/babel-plugin-transform-es2015-duplicate-keys-6.24.1.tgz", - "integrity": "sha1-c+s9MQypaePvnskcU3QabxV2Qj4=", - "requires": { - "babel-runtime": "^6.22.0", - "babel-types": "^6.24.1" - } - }, - "babel-plugin-transform-es2015-for-of": { - "version": "6.23.0", - "resolved": "https://registry.npmjs.org/babel-plugin-transform-es2015-for-of/-/babel-plugin-transform-es2015-for-of-6.23.0.tgz", - "integrity": "sha1-9HyVsrYT3x0+zC/bdXNiPHUkhpE=", - "requires": { - "babel-runtime": "^6.22.0" - } - }, - "babel-plugin-transform-es2015-function-name": { - "version": "6.24.1", - "resolved": "https://registry.npmjs.org/babel-plugin-transform-es2015-function-name/-/babel-plugin-transform-es2015-function-name-6.24.1.tgz", - "integrity": "sha1-g0yJhTvDaxrw86TF26qU/Y6sqos=", - "requires": { - "babel-helper-function-name": "^6.24.1", - "babel-runtime": "^6.22.0", - "babel-types": "^6.24.1" - } - }, - "babel-plugin-transform-es2015-literals": { - "version": "6.22.0", - "resolved": "https://registry.npmjs.org/babel-plugin-transform-es2015-literals/-/babel-plugin-transform-es2015-literals-6.22.0.tgz", - "integrity": "sha1-T1SgLWzWbPkVKAAZox0xklN3yi4=", - "requires": { - "babel-runtime": "^6.22.0" - } - }, - "babel-plugin-transform-es2015-modules-amd": { - "version": "6.24.1", - "resolved": "https://registry.npmjs.org/babel-plugin-transform-es2015-modules-amd/-/babel-plugin-transform-es2015-modules-amd-6.24.1.tgz", - "integrity": "sha1-Oz5UAXI5hC1tGcMBHEvS8AoA0VQ=", - "requires": { - "babel-plugin-transform-es2015-modules-commonjs": "^6.24.1", - "babel-runtime": "^6.22.0", - "babel-template": "^6.24.1" - } - }, - "babel-plugin-transform-es2015-modules-commonjs": { - "version": "6.26.2", - "resolved": "https://registry.npmjs.org/babel-plugin-transform-es2015-modules-commonjs/-/babel-plugin-transform-es2015-modules-commonjs-6.26.2.tgz", - "integrity": "sha512-CV9ROOHEdrjcwhIaJNBGMBCodN+1cfkwtM1SbUHmvyy35KGT7fohbpOxkE2uLz1o6odKK2Ck/tz47z+VqQfi9Q==", - "requires": { - "babel-plugin-transform-strict-mode": "^6.24.1", - "babel-runtime": "^6.26.0", - "babel-template": "^6.26.0", - "babel-types": "^6.26.0" - } - }, - "babel-plugin-transform-es2015-modules-systemjs": { - "version": "6.24.1", - "resolved": "https://registry.npmjs.org/babel-plugin-transform-es2015-modules-systemjs/-/babel-plugin-transform-es2015-modules-systemjs-6.24.1.tgz", - "integrity": "sha1-/4mhQrkRmpBhlfXxBuzzBdlAfSM=", - "requires": { - "babel-helper-hoist-variables": "^6.24.1", - "babel-runtime": "^6.22.0", - "babel-template": "^6.24.1" - } - }, - "babel-plugin-transform-es2015-modules-umd": { - "version": "6.24.1", - "resolved": "https://registry.npmjs.org/babel-plugin-transform-es2015-modules-umd/-/babel-plugin-transform-es2015-modules-umd-6.24.1.tgz", - "integrity": "sha1-rJl+YoXNGO1hdq22B9YCNErThGg=", - "requires": { - "babel-plugin-transform-es2015-modules-amd": "^6.24.1", - "babel-runtime": "^6.22.0", - "babel-template": "^6.24.1" - } - }, - "babel-plugin-transform-es2015-object-super": { - "version": "6.24.1", - "resolved": "https://registry.npmjs.org/babel-plugin-transform-es2015-object-super/-/babel-plugin-transform-es2015-object-super-6.24.1.tgz", - "integrity": "sha1-JM72muIcuDp/hgPa0CH1cusnj40=", - "requires": { - "babel-helper-replace-supers": "^6.24.1", - "babel-runtime": "^6.22.0" - } - }, - "babel-plugin-transform-es2015-parameters": { - "version": "6.24.1", - "resolved": "https://registry.npmjs.org/babel-plugin-transform-es2015-parameters/-/babel-plugin-transform-es2015-parameters-6.24.1.tgz", - "integrity": "sha1-V6w1GrScrxSpfNE7CfZv3wpiXys=", - "requires": { - "babel-helper-call-delegate": "^6.24.1", - "babel-helper-get-function-arity": "^6.24.1", - "babel-runtime": "^6.22.0", - "babel-template": "^6.24.1", - "babel-traverse": "^6.24.1", - "babel-types": "^6.24.1" - } - }, - "babel-plugin-transform-es2015-shorthand-properties": { - "version": "6.24.1", - "resolved": "https://registry.npmjs.org/babel-plugin-transform-es2015-shorthand-properties/-/babel-plugin-transform-es2015-shorthand-properties-6.24.1.tgz", - "integrity": "sha1-JPh11nIch2YbvZmkYi5R8U3jiqA=", - "requires": { - "babel-runtime": "^6.22.0", - "babel-types": "^6.24.1" - } - }, - "babel-plugin-transform-es2015-spread": { - "version": "6.22.0", - "resolved": "https://registry.npmjs.org/babel-plugin-transform-es2015-spread/-/babel-plugin-transform-es2015-spread-6.22.0.tgz", - "integrity": "sha1-1taKmfia7cRTbIGlQujdnxdG+NE=", - "requires": { - "babel-runtime": "^6.22.0" - } - }, - "babel-plugin-transform-es2015-sticky-regex": { - "version": "6.24.1", - "resolved": "https://registry.npmjs.org/babel-plugin-transform-es2015-sticky-regex/-/babel-plugin-transform-es2015-sticky-regex-6.24.1.tgz", - "integrity": "sha1-AMHNsaynERLN8M9hJsLta0V8zbw=", - "requires": { - "babel-helper-regex": "^6.24.1", - "babel-runtime": "^6.22.0", - "babel-types": "^6.24.1" - } - }, - "babel-plugin-transform-es2015-template-literals": { - "version": "6.22.0", - "resolved": "https://registry.npmjs.org/babel-plugin-transform-es2015-template-literals/-/babel-plugin-transform-es2015-template-literals-6.22.0.tgz", - "integrity": "sha1-qEs0UPfp+PH2g51taH2oS7EjbY0=", - "requires": { - "babel-runtime": "^6.22.0" - } - }, - "babel-plugin-transform-es2015-typeof-symbol": { - "version": "6.23.0", - "resolved": "https://registry.npmjs.org/babel-plugin-transform-es2015-typeof-symbol/-/babel-plugin-transform-es2015-typeof-symbol-6.23.0.tgz", - "integrity": "sha1-3sCfHN3/lLUqxz1QXITfWdzOs3I=", - "requires": { - "babel-runtime": "^6.22.0" - } - }, - "babel-plugin-transform-es2015-unicode-regex": { - "version": "6.24.1", - "resolved": "https://registry.npmjs.org/babel-plugin-transform-es2015-unicode-regex/-/babel-plugin-transform-es2015-unicode-regex-6.24.1.tgz", - "integrity": "sha1-04sS9C6nMj9yk4fxinxa4frrNek=", - "requires": { - "babel-helper-regex": "^6.24.1", - "babel-runtime": "^6.22.0", - "regexpu-core": "^2.0.0" - }, - "dependencies": { - "jsesc": { - "version": "0.5.0", - "resolved": "https://registry.npmjs.org/jsesc/-/jsesc-0.5.0.tgz", - "integrity": "sha1-597mbjXW/Bb3EP6R1c9p9w8IkR0=" - }, - "regexpu-core": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/regexpu-core/-/regexpu-core-2.0.0.tgz", - "integrity": "sha1-SdA4g3uNz4v6W5pCE5k45uoq4kA=", - "requires": { - "regenerate": "^1.2.1", - "regjsgen": "^0.2.0", - "regjsparser": "^0.1.4" - } - }, - "regjsgen": { - "version": "0.2.0", - "resolved": "https://registry.npmjs.org/regjsgen/-/regjsgen-0.2.0.tgz", - "integrity": "sha1-bAFq3qxVT3WCP+N6wFuS1aTtsfc=" - }, - "regjsparser": { - "version": "0.1.5", - "resolved": "https://registry.npmjs.org/regjsparser/-/regjsparser-0.1.5.tgz", - "integrity": "sha1-fuj4Tcb6eS0/0K4ijSS9lJ6tIFw=", - "requires": { - "jsesc": "~0.5.0" - } - } - } - }, - "babel-plugin-transform-exponentiation-operator": { - "version": "6.24.1", - "resolved": "https://registry.npmjs.org/babel-plugin-transform-exponentiation-operator/-/babel-plugin-transform-exponentiation-operator-6.24.1.tgz", - "integrity": "sha1-KrDJx/MJj6SJB3cruBP+QejeOg4=", - "requires": { - "babel-helper-builder-binary-assignment-operator-visitor": "^6.24.1", - "babel-plugin-syntax-exponentiation-operator": "^6.8.0", - "babel-runtime": "^6.22.0" - } - }, - "babel-plugin-transform-regenerator": { - "version": "6.26.0", - "resolved": "https://registry.npmjs.org/babel-plugin-transform-regenerator/-/babel-plugin-transform-regenerator-6.26.0.tgz", - "integrity": "sha1-4HA2lvveJ/Cj78rPi03KL3s6jy8=", - "requires": { - "regenerator-transform": "^0.10.0" - }, - "dependencies": { - "regenerator-transform": { - "version": "0.10.1", - "resolved": "https://registry.npmjs.org/regenerator-transform/-/regenerator-transform-0.10.1.tgz", - "integrity": "sha512-PJepbvDbuK1xgIgnau7Y90cwaAmO/LCLMI2mPvaXq2heGMR3aWW5/BQvYrhJ8jgmQjXewXvBjzfqKcVOmhjZ6Q==", - "requires": { - "babel-runtime": "^6.18.0", - "babel-types": "^6.19.0", - "private": "^0.1.6" - } - } - } - }, - "babel-plugin-transform-strict-mode": { - "version": "6.24.1", - "resolved": "https://registry.npmjs.org/babel-plugin-transform-strict-mode/-/babel-plugin-transform-strict-mode-6.24.1.tgz", - "integrity": "sha1-1fr3qleKZbvlkc9e2uBKDGcCB1g=", - "requires": { - "babel-runtime": "^6.22.0", - "babel-types": "^6.24.1" - } - }, - "babel-polyfill": { - "version": "6.26.0", - "resolved": "https://registry.npmjs.org/babel-polyfill/-/babel-polyfill-6.26.0.tgz", - "integrity": "sha1-N5k3q8Z9eJWXCtxiHyhM2WbPIVM=", - "requires": { - "babel-runtime": "^6.26.0", - "core-js": "^2.5.0", - "regenerator-runtime": "^0.10.5" - } - }, - "babel-preset-env": { - "version": "1.7.0", - "resolved": "https://registry.npmjs.org/babel-preset-env/-/babel-preset-env-1.7.0.tgz", - "integrity": "sha512-9OR2afuKDneX2/q2EurSftUYM0xGu4O2D9adAhVfADDhrYDaxXV0rBbevVYoY9n6nyX1PmQW/0jtpJvUNr9CHg==", - "requires": { - "babel-plugin-check-es2015-constants": "^6.22.0", - "babel-plugin-syntax-trailing-function-commas": "^6.22.0", - "babel-plugin-transform-async-to-generator": "^6.22.0", - "babel-plugin-transform-es2015-arrow-functions": "^6.22.0", - "babel-plugin-transform-es2015-block-scoped-functions": "^6.22.0", - "babel-plugin-transform-es2015-block-scoping": "^6.23.0", - "babel-plugin-transform-es2015-classes": "^6.23.0", - "babel-plugin-transform-es2015-computed-properties": "^6.22.0", - "babel-plugin-transform-es2015-destructuring": "^6.23.0", - "babel-plugin-transform-es2015-duplicate-keys": "^6.22.0", - "babel-plugin-transform-es2015-for-of": "^6.23.0", - "babel-plugin-transform-es2015-function-name": "^6.22.0", - "babel-plugin-transform-es2015-literals": "^6.22.0", - "babel-plugin-transform-es2015-modules-amd": "^6.22.0", - "babel-plugin-transform-es2015-modules-commonjs": "^6.23.0", - "babel-plugin-transform-es2015-modules-systemjs": "^6.23.0", - "babel-plugin-transform-es2015-modules-umd": "^6.23.0", - "babel-plugin-transform-es2015-object-super": "^6.22.0", - "babel-plugin-transform-es2015-parameters": "^6.23.0", - "babel-plugin-transform-es2015-shorthand-properties": "^6.22.0", - "babel-plugin-transform-es2015-spread": "^6.22.0", - "babel-plugin-transform-es2015-sticky-regex": "^6.22.0", - "babel-plugin-transform-es2015-template-literals": "^6.22.0", - "babel-plugin-transform-es2015-typeof-symbol": "^6.23.0", - "babel-plugin-transform-es2015-unicode-regex": "^6.22.0", - "babel-plugin-transform-exponentiation-operator": "^6.22.0", - "babel-plugin-transform-regenerator": "^6.22.0", - "browserslist": "^3.2.6", - "invariant": "^2.2.2", - "semver": "^5.3.0" - }, - "dependencies": { - "browserslist": { - "version": "3.2.8", - "resolved": "https://registry.npmjs.org/browserslist/-/browserslist-3.2.8.tgz", - "integrity": "sha512-WHVocJYavUwVgVViC0ORikPHQquXwVh939TaelZ4WDqpWgTX/FsGhl/+P4qBUAGcRvtOgDgC+xftNWWp2RUTAQ==", - "requires": { - "caniuse-lite": "^1.0.30000844", - "electron-to-chromium": "^1.3.47" - } - }, - "semver": { - "version": "5.7.1", - "resolved": "https://registry.npmjs.org/semver/-/semver-5.7.1.tgz", - "integrity": "sha512-sauaDf/PZdVgrLTNYHRtpXa1iRiKcaebiKQ1BJdpQlWH2lCvexQdX55snPFyK7QzpudqbCI0qXFfOasHdyNDGQ==" - } - } - }, - "babel-register": { - "version": "6.26.0", - "resolved": "https://registry.npmjs.org/babel-register/-/babel-register-6.26.0.tgz", - "integrity": "sha1-btAhFz4vy0htestFxgCahW9kcHE=", - "requires": { - "babel-core": "^6.26.0", - "babel-runtime": "^6.26.0", - "core-js": "^2.5.0", - "home-or-tmp": "^2.0.0", - "lodash": "^4.17.4", - "mkdirp": "^0.5.1", - "source-map-support": "^0.4.15" - }, - "dependencies": { - "mkdirp": { - "version": "0.5.5", - "resolved": "https://registry.npmjs.org/mkdirp/-/mkdirp-0.5.5.tgz", - "integrity": "sha512-NKmAlESf6jMGym1++R0Ra7wvhV+wFW63FaSOFPwRahvea0gMUcGUhVeAg/0BC0wiv9ih5NYPB1Wn1UEI1/L+xQ==", - "requires": { - "minimist": "^1.2.5" - } - }, - "source-map": { - "version": "0.5.7", - "resolved": "https://registry.npmjs.org/source-map/-/source-map-0.5.7.tgz", - "integrity": "sha1-igOdLRAh0i0eoUyA2OpGi6LvP8w=" - }, - "source-map-support": { - "version": "0.4.18", - "resolved": "https://registry.npmjs.org/source-map-support/-/source-map-support-0.4.18.tgz", - "integrity": "sha512-try0/JqxPLF9nOjvSta7tVondkP5dwgyLDjVoyMDlmjugT2lRZ1OfsrYTkCd2hkDnJTKRbO/Rl3orm8vlsUzbA==", - "requires": { - "source-map": "^0.5.6" - } - } - } - }, - "babel-runtime": { - "version": "6.26.0", - "resolved": "https://registry.npmjs.org/babel-runtime/-/babel-runtime-6.26.0.tgz", - "integrity": "sha1-llxwWGaOgrVde/4E/yM3vItWR/4=", - "requires": { - "core-js": "^2.4.0", - "regenerator-runtime": "^0.11.0" - }, - "dependencies": { - "regenerator-runtime": { - "version": "0.11.1", - "resolved": "https://registry.npmjs.org/regenerator-runtime/-/regenerator-runtime-0.11.1.tgz", - "integrity": "sha512-MguG95oij0fC3QV3URf4V2SDYGJhJnJGqvIIgdECeODCT98wSWDAJ94SSuVpYQUoTcGUIL6L4yNB7j1DFFHSBg==" - } - } - }, - "babel-template": { - "version": "6.26.0", - "resolved": "https://registry.npmjs.org/babel-template/-/babel-template-6.26.0.tgz", - "integrity": "sha1-3gPi0WOWsGn0bdn/+FIfsaDjXgI=", - "requires": { - "babel-runtime": "^6.26.0", - "babel-traverse": "^6.26.0", - "babel-types": "^6.26.0", - "babylon": "^6.18.0", - "lodash": "^4.17.4" - } - }, - "babel-traverse": { - "version": "6.26.0", - "resolved": "https://registry.npmjs.org/babel-traverse/-/babel-traverse-6.26.0.tgz", - "integrity": "sha1-RqnL1+3MYsjlwGTi0tjQ9ANXZu4=", - "requires": { - "babel-code-frame": "^6.26.0", - "babel-messages": "^6.23.0", - "babel-runtime": "^6.26.0", - "babel-types": "^6.26.0", - "babylon": "^6.18.0", - "debug": "^2.6.8", - "globals": "^9.18.0", - "invariant": "^2.2.2", - "lodash": "^4.17.4" - }, - "dependencies": { - "debug": { - "version": "2.6.9", - "resolved": "https://registry.npmjs.org/debug/-/debug-2.6.9.tgz", - "integrity": "sha512-bC7ElrdJaJnPbAP+1EotYvqZsb3ecl5wi6Bfi6BJTUcNowp6cvspg0jXznRTKDjm/E7AdgFBVeAPVMNcKGsHMA==", - "requires": { - "ms": "2.0.0" - } - }, - "globals": { - "version": "9.18.0", - "resolved": "https://registry.npmjs.org/globals/-/globals-9.18.0.tgz", - "integrity": "sha512-S0nG3CLEQiY/ILxqtztTWH/3iRRdyBLw6KMDxnKMchrtbj2OFmehVh0WUCfW3DUrIgx/qFrJPICrq4Z4sTR9UQ==" - }, - "ms": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/ms/-/ms-2.0.0.tgz", - "integrity": "sha1-VgiurfwAvmwpAd9fmGF4jeDVl8g=" - } - } - }, - "babel-types": { - "version": "6.26.0", - "resolved": "https://registry.npmjs.org/babel-types/-/babel-types-6.26.0.tgz", - "integrity": "sha1-o7Bz+Uq0nrb6Vc1lInozQ4BjJJc=", - "requires": { - "babel-runtime": "^6.26.0", - "esutils": "^2.0.2", - "lodash": "^4.17.4", - "to-fast-properties": "^1.0.3" - }, - "dependencies": { - "to-fast-properties": { - "version": "1.0.3", - "resolved": "https://registry.npmjs.org/to-fast-properties/-/to-fast-properties-1.0.3.tgz", - "integrity": "sha1-uDVx+k2MJbguIxsG46MFXeTKGkc=" - } - } - }, - "babylon": { - "version": "6.18.0", - "resolved": "https://registry.npmjs.org/babylon/-/babylon-6.18.0.tgz", - "integrity": "sha512-q/UEjfGJ2Cm3oKV71DJz9d25TPnq5rhBVL2Q4fA5wcC3jcrdn7+SssEybFIxwAvvP+YCsCYNKughoF33GxgycQ==" - }, - "backo2": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/backo2/-/backo2-1.0.2.tgz", - "integrity": "sha1-MasayLEpNjRj41s+u2n038+6eUc=" - }, - "balanced-match": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/balanced-match/-/balanced-match-1.0.2.tgz", - "integrity": "sha512-3oSeUO0TMV67hN1AmbXsK4yaqU7tjiHlbxRDZOpH0KW9+CeX4bRAaX0Anxt0tx2MrpRpWwQaPwIlISEJhYU5Pw==" - }, - "base64-arraybuffer": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/base64-arraybuffer/-/base64-arraybuffer-1.0.1.tgz", - "integrity": "sha512-vFIUq7FdLtjZMhATwDul5RZWv2jpXQ09Pd6jcVEOvIsqCWTRFD/ONHNfyOS8dA/Ippi5dsIgpyKWKZaAKZltbA==" - }, - "base64-js": { - "version": "1.5.1", - "resolved": "https://registry.npmjs.org/base64-js/-/base64-js-1.5.1.tgz", - "integrity": "sha512-AKpaYlHn8t4SVbOHCy+b5+KKgvR4vrsD8vbvrbiQJps7fKDTkjkDry6ji0rUJjC0kzbNePLwzxq8iypo41qeWA==" - }, - "base64id": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/base64id/-/base64id-2.0.0.tgz", - "integrity": "sha512-lGe34o6EHj9y3Kts9R4ZYs/Gr+6N7MCaMlIFA3F1R2O5/m7K06AxfSeO5530PEERE6/WyEg3lsuyw4GHlPZHog==" - }, - "bcrypt-pbkdf": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/bcrypt-pbkdf/-/bcrypt-pbkdf-1.0.2.tgz", - "integrity": "sha1-pDAdOJtqQ/m2f/PKEaP2Y342Dp4=", - "dev": true, - "requires": { - "tweetnacl": "^0.14.3" - } - }, - "bcryptjs": { - "version": "2.4.3", - "resolved": "https://registry.npmjs.org/bcryptjs/-/bcryptjs-2.4.3.tgz", - "integrity": "sha1-mrVie5PmBiH/fNrF2pczAn3x0Ms=" - }, - "before-after-hook": { - "version": "2.2.2", - "resolved": "https://registry.npmjs.org/before-after-hook/-/before-after-hook-2.2.2.tgz", - "integrity": "sha512-3pZEU3NT5BFUo/AD5ERPWOgQOCZITni6iavr5AUw5AUwQjMlI0kzu5btnyD39AF0gUEsDPwJT+oY1ORBJijPjQ==", - "dev": true - }, - "big.js": { - "version": "5.2.2", - "resolved": "https://registry.npmjs.org/big.js/-/big.js-5.2.2.tgz", - "integrity": "sha512-vyL2OymJxmarO8gxMr0mhChsO9QGwhynfuu4+MHTAW6czfq9humCB7rKpUjDd9YUiDPU4mzpyupFSvOClAwbmQ==" - }, - "binary-extensions": { - "version": "2.2.0", - "resolved": "https://registry.npmjs.org/binary-extensions/-/binary-extensions-2.2.0.tgz", - "integrity": "sha512-jDctJ/IVQbZoJykoeHbhXpOlNBqGNcwXJKJog42E5HDPUwQTSdjCHdihjj0DlnheQ7blbT6dHOafNAiS8ooQKA==" - }, - "bl": { - "version": "0.7.0", - "resolved": "https://registry.npmjs.org/bl/-/bl-0.7.0.tgz", - "integrity": "sha1-P7BnBgKsKHjrdw3CA58YNr5irls=", - "requires": { - "readable-stream": "~1.0.2" - }, - "dependencies": { - "isarray": { - "version": "0.0.1", - "resolved": "https://registry.npmjs.org/isarray/-/isarray-0.0.1.tgz", - "integrity": "sha1-ihis/Kmo9Bd+Cav8YDiTmwXR7t8=" - }, - "readable-stream": { - "version": "1.0.34", - "resolved": "https://registry.npmjs.org/readable-stream/-/readable-stream-1.0.34.tgz", - "integrity": "sha1-Elgg40vIQtLyqq+v5MKRbuMsFXw=", - "requires": { - "core-util-is": "~1.0.0", - "inherits": "~2.0.1", - "isarray": "0.0.1", - "string_decoder": "~0.10.x" - } - }, - "string_decoder": { - "version": "0.10.31", - "resolved": "https://registry.npmjs.org/string_decoder/-/string_decoder-0.10.31.tgz", - "integrity": "sha1-YuIDvEF2bGwoyfyEMB2rHFMQ+pQ=" - } - } - }, - "bluebird": { - "version": "3.7.2", - "resolved": "https://registry.npmjs.org/bluebird/-/bluebird-3.7.2.tgz", - "integrity": "sha512-XpNj6GDQzdfW+r2Wnn7xiSAd7TM3jzkxGXBGTtWKuSXv1xUV+azxAm8jdWZN06QTQk+2N2XB9jRDkvbmQmcRtg==" - }, - "bn.js": { - "version": "4.12.0", - "resolved": "https://registry.npmjs.org/bn.js/-/bn.js-4.12.0.tgz", - "integrity": "sha512-c98Bf3tPniI+scsdk237ku1Dc3ujXQTSgyiPUDEOe7tRkhrqridvh8klBv0HCEso1OLOYcHuCv/cS6DNxKH+ZA==", - "optional": true - }, - "body-parser": { - "version": "1.19.1", - "resolved": "https://registry.npmjs.org/body-parser/-/body-parser-1.19.1.tgz", - "integrity": "sha512-8ljfQi5eBk8EJfECMrgqNGWPEY5jWP+1IzkzkGdFFEwFQZZyaZ21UqdaHktgiMlH0xLHqIFtE/u2OYE5dOtViA==", - "requires": { - "bytes": "3.1.1", - "content-type": "~1.0.4", - "debug": "2.6.9", - "depd": "~1.1.2", - "http-errors": "1.8.1", - "iconv-lite": "0.4.24", - "on-finished": "~2.3.0", - "qs": "6.9.6", - "raw-body": "2.4.2", - "type-is": "~1.6.18" - }, - "dependencies": { - "debug": { - "version": "2.6.9", - "resolved": "https://registry.npmjs.org/debug/-/debug-2.6.9.tgz", - "integrity": "sha512-bC7ElrdJaJnPbAP+1EotYvqZsb3ecl5wi6Bfi6BJTUcNowp6cvspg0jXznRTKDjm/E7AdgFBVeAPVMNcKGsHMA==", - "requires": { - "ms": "2.0.0" - } - }, - "ms": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/ms/-/ms-2.0.0.tgz", - "integrity": "sha1-VgiurfwAvmwpAd9fmGF4jeDVl8g=" - }, - "qs": { - "version": "6.9.6", - "resolved": "https://registry.npmjs.org/qs/-/qs-6.9.6.tgz", - "integrity": "sha512-TIRk4aqYLNoJUbd+g2lEdz5kLWIuTMRagAXxl78Q0RiVjAOugHmeKNGdd3cwo/ktpf9aL9epCfFqWDEKysUlLQ==" - } - } - }, - "boxen": { - "version": "5.1.2", - "resolved": "https://registry.npmjs.org/boxen/-/boxen-5.1.2.tgz", - "integrity": "sha512-9gYgQKXx+1nP8mP7CzFyaUARhg7D3n1dF/FnErWmu9l6JvGpNUN278h0aSb+QjoiKSWG+iZ3uHrcqk0qrY9RQQ==", - "dev": true, - "requires": { - "ansi-align": "^3.0.0", - "camelcase": "^6.2.0", - "chalk": "^4.1.0", - "cli-boxes": "^2.2.1", - "string-width": "^4.2.2", - "type-fest": "^0.20.2", - "widest-line": "^3.1.0", - "wrap-ansi": "^7.0.0" - }, - "dependencies": { - "camelcase": { - "version": "6.3.0", - "resolved": "https://registry.npmjs.org/camelcase/-/camelcase-6.3.0.tgz", - "integrity": "sha512-Gmy6FhYlCY7uOElZUSbxo2UCDH8owEk996gkbrpsgGtrJLM3J7jGxl9Ic7Qwwj4ivOE5AWZWRMecDdF7hqGjFA==", - "dev": true - } - } - }, - "brace-expansion": { - "version": "1.1.11", - "resolved": "https://registry.npmjs.org/brace-expansion/-/brace-expansion-1.1.11.tgz", - "integrity": "sha512-iCuPHDFgrHX7H2vEI/5xpz07zSHB00TpugqhmYtVmMO6518mCuRMoOYFldEBl0g187ufozdaHgWKcYFb61qGiA==", - "requires": { - "balanced-match": "^1.0.0", - "concat-map": "0.0.1" - } - }, - "braces": { - "version": "3.0.2", - "resolved": "https://registry.npmjs.org/braces/-/braces-3.0.2.tgz", - "integrity": "sha512-b8um+L1RzM3WDSzvhm6gIz1yfTbBt6YTlcEKAvsmqCZZFw46z626lVj9j1yEPW33H5H+lBQpZMP1k8l+78Ha0A==", - "requires": { - "fill-range": "^7.0.1" - } - }, - "brorand": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/brorand/-/brorand-1.1.0.tgz", - "integrity": "sha1-EsJe/kCkXjwyPrhnWgoM5XsiNx8=", - "optional": true - }, - "browser-refresh-client": { - "version": "1.1.4", - "resolved": "https://registry.npmjs.org/browser-refresh-client/-/browser-refresh-client-1.1.4.tgz", - "integrity": "sha1-jl/4R1/h1UHSroH3oa6gWuIaYhc=" - }, - "browser-stdout": { - "version": "1.3.1", - "resolved": "https://registry.npmjs.org/browser-stdout/-/browser-stdout-1.3.1.tgz", - "integrity": "sha512-qhAVI1+Av2X7qelOfAIYwXONood6XlZE/fXaBSmW/T5SzLAmCgzi+eiWE7fUvbHaeNBQH13UftjpXxsfLkMpgw==" - }, - "browserslist": { - "version": "4.19.1", - "resolved": "https://registry.npmjs.org/browserslist/-/browserslist-4.19.1.tgz", - "integrity": "sha512-u2tbbG5PdKRTUoctO3NBD8FQ5HdPh1ZXPHzp1rwaa5jTc+RV9/+RlWiAIKmjRPQF+xbGM9Kklj5bZQFa2s/38A==", - "requires": { - "caniuse-lite": "^1.0.30001286", - "electron-to-chromium": "^1.4.17", - "escalade": "^3.1.1", - "node-releases": "^2.0.1", - "picocolors": "^1.0.0" - } - }, - "bson": { - "version": "4.6.0", - "resolved": "https://registry.npmjs.org/bson/-/bson-4.6.0.tgz", - "integrity": "sha512-8jw1NU1hglS+Da1jDOUYuNcBJ4cNHCFIqzlwoFNnsTOg2R/ox0aTYcTiBN4dzRa9q7Cvy6XErh3L8ReTEb9AQQ==", - "requires": { - "buffer": "^5.6.0" - } - }, - "buffer": { - "version": "5.7.1", - "resolved": "https://registry.npmjs.org/buffer/-/buffer-5.7.1.tgz", - "integrity": "sha512-EHcyIPBQ4BSGlvjB16k5KgAJ27CIsHY/2JBmCRReo48y9rQ3MaUzWX3KVlBa4U7MyX02HdVj0K7C3WaB3ju7FQ==", - "requires": { - "base64-js": "^1.3.1", - "ieee754": "^1.1.13" - } - }, - "buffer-crc32": { - "version": "0.2.13", - "resolved": "https://registry.npmjs.org/buffer-crc32/-/buffer-crc32-0.2.13.tgz", - "integrity": "sha1-DTM+PwDqxQqhRUq9MO+MKl2ackI=" - }, - "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": "sha1-+OcRMvf/5uAaXJaXpMbz5I1cyBk=" - }, - "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==" - }, - "builtins": { - "version": "1.0.3", - "resolved": "https://registry.npmjs.org/builtins/-/builtins-1.0.3.tgz", - "integrity": "sha1-y5T662HIaWRR2zZTThQi+U8K7og=", - "dev": true - }, - "byline": { - "version": "5.0.0", - "resolved": "https://registry.npmjs.org/byline/-/byline-5.0.0.tgz", - "integrity": "sha1-dBxSFkaOrcRXsDQQEYrXfejB3bE=", - "dev": true - }, - "byte-size": { - "version": "7.0.1", - "resolved": "https://registry.npmjs.org/byte-size/-/byte-size-7.0.1.tgz", - "integrity": "sha512-crQdqyCwhokxwV1UyDzLZanhkugAgft7vt0qbbdt60C6Zf3CAiGmtUCylbtYwrU6loOUw3euGrNtW1J651ot1A==", - "dev": true - }, - "bytes": { - "version": "3.1.1", - "resolved": "https://registry.npmjs.org/bytes/-/bytes-3.1.1.tgz", - "integrity": "sha512-dWe4nWO/ruEOY7HkUJ5gFt1DCFV9zPRoJr8pV0/ASQermOZjtq8jMjOprC0Kd10GLN+l7xaUPvxzJFWtxGu8Fg==" - }, - "cacache": { - "version": "15.3.0", - "resolved": "https://registry.npmjs.org/cacache/-/cacache-15.3.0.tgz", - "integrity": "sha512-VVdYzXEn+cnbXpFgWs5hTT7OScegHVmLhJIR8Ufqk3iFD6A6j5iSX1KuBTfNEv4tdJWE2PzA6IVFtcLC7fN9wQ==", - "dev": true, - "requires": { - "@npmcli/fs": "^1.0.0", - "@npmcli/move-file": "^1.0.1", - "chownr": "^2.0.0", - "fs-minipass": "^2.0.0", - "glob": "^7.1.4", - "infer-owner": "^1.0.4", - "lru-cache": "^6.0.0", - "minipass": "^3.1.1", - "minipass-collect": "^1.0.2", - "minipass-flush": "^1.0.5", - "minipass-pipeline": "^1.2.2", - "mkdirp": "^1.0.3", - "p-map": "^4.0.0", - "promise-inflight": "^1.0.1", - "rimraf": "^3.0.2", - "ssri": "^8.0.1", - "tar": "^6.0.2", - "unique-filename": "^1.1.1" - } - }, - "cache-content-type": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/cache-content-type/-/cache-content-type-1.0.1.tgz", - "integrity": "sha512-IKufZ1o4Ut42YUrZSo8+qnMTrFuKkvyoLXUywKz9GJ5BrhOFGhLdkx9sG4KAnVvbY6kEcSFjLQul+DVmBm2bgA==", - "requires": { - "mime-types": "^2.1.18", - "ylru": "^1.2.0" - } - }, - "cacheable-request": { - "version": "6.1.0", - "resolved": "https://registry.npmjs.org/cacheable-request/-/cacheable-request-6.1.0.tgz", - "integrity": "sha512-Oj3cAGPCqOZX7Rz64Uny2GYAZNliQSqfbePrgAQ1wKAihYmCUnraBtJtKcGR4xz7wF+LoJC+ssFZvv5BgF9Igg==", - "dev": true, - "requires": { - "clone-response": "^1.0.2", - "get-stream": "^5.1.0", - "http-cache-semantics": "^4.0.0", - "keyv": "^3.0.0", - "lowercase-keys": "^2.0.0", - "normalize-url": "^4.1.0", - "responselike": "^1.0.2" - }, - "dependencies": { - "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, - "requires": { - "pump": "^3.0.0" - } - }, - "lowercase-keys": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/lowercase-keys/-/lowercase-keys-2.0.0.tgz", - "integrity": "sha512-tqNXrS78oMOE73NMxK4EMLQsQowWf8jKooH9g7xPavRT706R6bkQJ6DY2Te7QukaZsulxa30wQ7bk0pm4XiHmA==", - "dev": true - }, - "normalize-url": { - "version": "4.5.1", - "resolved": "https://registry.npmjs.org/normalize-url/-/normalize-url-4.5.1.tgz", - "integrity": "sha512-9UZCFRHQdNrfTpGg8+1INIg93B6zE0aXMVFkw1WFwvO4SlZywU6aLg5Of0Ap/PgcbSw4LNxvMWXMeugwMCX0AA==", - "dev": true - } - } - }, - "caching-transform": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/caching-transform/-/caching-transform-4.0.0.tgz", - "integrity": "sha512-kpqOvwXnjjN44D89K5ccQC+RUrsy7jB/XLlRrx0D7/2HNcTPqzsb6XgYoErwko6QsV184CA2YgS1fxDiiDZMWA==", - "dev": true, - "requires": { - "hasha": "^5.0.0", - "make-dir": "^3.0.0", - "package-hash": "^4.0.0", - "write-file-atomic": "^3.0.0" - } - }, - "call-bind": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/call-bind/-/call-bind-1.0.2.tgz", - "integrity": "sha512-7O+FbCihrB5WGbFYesctwmTKae6rOiIzmz1icreWJ+0aA7LJfuqhEso2T9ncpcFtzMQtzXf2QGGueWJGTYsqrA==", - "requires": { - "function-bind": "^1.1.1", - "get-intrinsic": "^1.0.2" - } - }, - "callsites": { - "version": "3.1.0", - "resolved": "https://registry.npmjs.org/callsites/-/callsites-3.1.0.tgz", - "integrity": "sha512-P8BjAsXvZS+VIDUI11hHCQEv74YT67YUi5JJFNWIqL235sBmjX4+qx9Muvls5ivyNENctx46xQLQ3aTuE7ssaQ==", - "dev": true - }, - "camelcase": { - "version": "5.3.1", - "resolved": "https://registry.npmjs.org/camelcase/-/camelcase-5.3.1.tgz", - "integrity": "sha512-L28STB170nwWS63UjtlEOE3dldQApaJXZkOI1uMFfzf3rRuPegHaHesyee+YxQ+W6SvRDQV6UrdOdRiR153wJg==" - }, - "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, - "requires": { - "camelcase": "^5.3.1", - "map-obj": "^4.0.0", - "quick-lru": "^4.0.1" - } - }, - "caniuse-lite": { - "version": "1.0.30001295", - "resolved": "https://registry.npmjs.org/caniuse-lite/-/caniuse-lite-1.0.30001295.tgz", - "integrity": "sha512-lSP16vcyC0FEy0R4ECc9duSPoKoZy+YkpGkue9G4D81OfPnliopaZrU10+qtPdT8PbGXad/PNx43TIQrOmJZSQ==" - }, - "caseless": { - "version": "0.12.0", - "resolved": "https://registry.npmjs.org/caseless/-/caseless-0.12.0.tgz", - "integrity": "sha1-G2gcIf+EAzyCZUMJBolCDRhxUdw=", - "dev": true - }, - "center-align": { - "version": "0.1.3", - "resolved": "https://registry.npmjs.org/center-align/-/center-align-0.1.3.tgz", - "integrity": "sha1-qg0yYptu6XIgBBHL1EYckHvCt60=", - "requires": { - "align-text": "^0.1.3", - "lazy-cache": "^1.0.3" - } - }, - "chai": { - "version": "3.5.0", - "resolved": "https://registry.npmjs.org/chai/-/chai-3.5.0.tgz", - "integrity": "sha1-TQJjewZ/6Vi9v906QOxW/vc3Mkc=", - "requires": { - "assertion-error": "^1.0.1", - "deep-eql": "^0.1.3", - "type-detect": "^1.0.0" - } - }, - "chalk": { - "version": "4.1.2", - "resolved": "https://registry.npmjs.org/chalk/-/chalk-4.1.2.tgz", - "integrity": "sha512-oKnbhFyRIXpUuez8iBMmyEa4nbj4IOQyuhc/wy9kY7/WVPcwIO9VA668Pu8RkO7+0G76SLROeyw9CpQ061i4mA==", - "requires": { - "ansi-styles": "^4.1.0", - "supports-color": "^7.1.0" - } - }, - "char-props": { - "version": "0.1.5", - "resolved": "https://registry.npmjs.org/char-props/-/char-props-0.1.5.tgz", - "integrity": "sha1-W5UvniDqIc0Iyn/hNaEPb+kcEJ4=" - }, - "chardet": { - "version": "0.7.0", - "resolved": "https://registry.npmjs.org/chardet/-/chardet-0.7.0.tgz", - "integrity": "sha512-mT8iDcrh03qDGRRmoA2hmBJnxpllMR+0/0qlzjqZES6NdiWDcZkCNAk4rPFZ9Q85r27unkiNNg8ZOiwZXBHwcA==", - "dev": true - }, - "chokidar": { - "version": "3.5.2", - "resolved": "https://registry.npmjs.org/chokidar/-/chokidar-3.5.2.tgz", - "integrity": "sha512-ekGhOnNVPgT77r4K/U3GDhu+FQ2S8TnK/s2KbIGXi0SZWuwkZ2QNyfWdZW+TVfn84DpEP7rLeCt2UI6bJ8GwbQ==", - "requires": { - "anymatch": "~3.1.2", - "braces": "~3.0.2", - "fsevents": "~2.3.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" - }, - "dependencies": { - "glob-parent": { - "version": "5.1.2", - "resolved": "https://registry.npmjs.org/glob-parent/-/glob-parent-5.1.2.tgz", - "integrity": "sha512-AOIgSQCepiJYwP3ARnGx+5VnTu2HBYdzbGP45eLw1vr3zB3vZLeyed1sC9hnbcOc9/SrMyM5RPQrkGz4aS9Zow==", - "requires": { - "is-glob": "^4.0.1" - } - } - } - }, - "chownr": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/chownr/-/chownr-2.0.0.tgz", - "integrity": "sha512-bIomtDF5KGpdogkLd9VspvFzk9KfpyyGlS8YFVZl7TGPBHL5snIOnxeshwVgPteQ9b4Eydl+pVbIyE1DcvCWgQ==", - "dev": true - }, - "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==" - }, - "ci-info": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/ci-info/-/ci-info-2.0.0.tgz", - "integrity": "sha512-5tK7EtrZ0N+OLFMthtqOj4fI2Jeb88C4CAZPu25LDVUgXJ0A3Js4PMGqrn0JU1W0Mh1/Z8wZzYPxqUrXeBboCQ==", - "dev": true - }, - "cint": { - "version": "8.2.1", - "resolved": "https://registry.npmjs.org/cint/-/cint-8.2.1.tgz", - "integrity": "sha1-cDhrG0jidz0NYxZqVa/5TvRFahI=", - "dev": true - }, - "clean-stack": { - "version": "2.2.0", - "resolved": "https://registry.npmjs.org/clean-stack/-/clean-stack-2.2.0.tgz", - "integrity": "sha512-4diC9HaTE+KRAMWhDhrGOECgWZxoevMc5TlkObMqNSsVU62PYzXZ/SMTjzyGAFF1YusgxGcSWTEXBhp0CPwQ1A==", - "dev": true - }, - "cli-boxes": { - "version": "2.2.1", - "resolved": "https://registry.npmjs.org/cli-boxes/-/cli-boxes-2.2.1.tgz", - "integrity": "sha512-y4coMcylgSCdVinjiDBuR8PCC2bLjyGTwEmPb9NHR/QaNU6EUOXcTY/s6VjGMD6ENSEaeQYHCY0GNGS5jfMwPw==", - "dev": true - }, - "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, - "requires": { - "restore-cursor": "^3.1.0" - } - }, - "cli-table": { - "version": "0.3.11", - "resolved": "https://registry.npmjs.org/cli-table/-/cli-table-0.3.11.tgz", - "integrity": "sha512-IqLQi4lO0nIB4tcdTpN4LCB9FI3uqrJZK7RC515EnhZ6qBaglkIgICb1wjeAqpdoOabm1+SuQtkXIPdYC93jhQ==", - "dev": true, - "requires": { - "colors": "1.0.3" - } - }, - "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 - }, - "cliui": { - "version": "7.0.4", - "resolved": "https://registry.npmjs.org/cliui/-/cliui-7.0.4.tgz", - "integrity": "sha512-OcRE68cOsVMXp1Yvonl/fzkQOyjLSu/8bhPDfQt0e0/Eb283TKP20Fs2MqoPsr9SwA595rRCA+QMzYc9nBP+JQ==", - "requires": { - "string-width": "^4.2.0", - "strip-ansi": "^6.0.0", - "wrap-ansi": "^7.0.0" - } - }, - "clone": { - "version": "1.0.4", - "resolved": "https://registry.npmjs.org/clone/-/clone-1.0.4.tgz", - "integrity": "sha1-2jCcwmPfFZlMaIypAheco8fNfH4=", - "dev": true - }, - "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==", - "requires": { - "is-plain-object": "^2.0.4", - "kind-of": "^6.0.2", - "shallow-clone": "^3.0.0" - }, - "dependencies": { - "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==", - "requires": { - "isobject": "^3.0.1" - } - } - } - }, - "clone-response": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/clone-response/-/clone-response-1.0.2.tgz", - "integrity": "sha1-0dyXOSAxTfZ/vrlCI7TuNQI56Ws=", - "dev": true, - "requires": { - "mimic-response": "^1.0.0" - } - }, - "cmd-shim": { - "version": "4.1.0", - "resolved": "https://registry.npmjs.org/cmd-shim/-/cmd-shim-4.1.0.tgz", - "integrity": "sha512-lb9L7EM4I/ZRVuljLPEtUJOP+xiQVknZ4ZMpMgEp4JzNldPb27HU03hi6K1/6CoIuit/Zm/LQXySErFeXxDprw==", - "dev": true, - "requires": { - "mkdirp-infer-owner": "^2.0.0" - } - }, - "co": { - "version": "4.6.0", - "resolved": "https://registry.npmjs.org/co/-/co-4.6.0.tgz", - "integrity": "sha1-bqa989hTrlTMuOR7+gvz+QMfsYQ=" - }, - "co-body": { - "version": "6.1.0", - "resolved": "https://registry.npmjs.org/co-body/-/co-body-6.1.0.tgz", - "integrity": "sha512-m7pOT6CdLN7FuXUcpuz/8lfQ/L77x8SchHCF4G0RBTJO20Wzmhn5Sp4/5WsKy8OSpifBSUrmg83qEqaDHdyFuQ==", - "requires": { - "inflation": "^2.0.0", - "qs": "^6.5.2", - "raw-body": "^2.3.3", - "type-is": "^1.6.16" - } - }, - "code-point-at": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/code-point-at/-/code-point-at-1.1.0.tgz", - "integrity": "sha1-DQcLTQQ6W+ozovGkDi7bPZpMz3c=", - "dev": true - }, - "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==", - "requires": { - "color-name": "~1.1.4" - } - }, - "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==" - }, - "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==", - "dev": true - }, - "colorette": { - "version": "2.0.16", - "resolved": "https://registry.npmjs.org/colorette/-/colorette-2.0.16.tgz", - "integrity": "sha512-hUewv7oMjCp+wkBv5Rm0v87eJhq4woh5rSR+42YSQJKecCqgIqNkZ6lAlQms/BwHPJA5NKMRlpxPRv0n8HQW6g==" - }, - "colors": { - "version": "1.0.3", - "resolved": "https://registry.npmjs.org/colors/-/colors-1.0.3.tgz", - "integrity": "sha1-BDP0TYCWgP3rYO0mDxsMJi6CpAs=", - "dev": true - }, - "columnify": { - "version": "1.5.4", - "resolved": "https://registry.npmjs.org/columnify/-/columnify-1.5.4.tgz", - "integrity": "sha1-Rzfd8ce2mop8NAVweC6UfuyOeLs=", - "dev": true, - "requires": { - "strip-ansi": "^3.0.0", - "wcwidth": "^1.0.0" - }, - "dependencies": { - "ansi-regex": { - "version": "2.1.1", - "resolved": "https://registry.npmjs.org/ansi-regex/-/ansi-regex-2.1.1.tgz", - "integrity": "sha1-w7M6te42DYbg5ijwRorn7yfWVN8=", - "dev": true - }, - "strip-ansi": { - "version": "3.0.1", - "resolved": "https://registry.npmjs.org/strip-ansi/-/strip-ansi-3.0.1.tgz", - "integrity": "sha1-ajhfuIU9lS1f8F0Oiq+UJ43GPc8=", - "dev": true, - "requires": { - "ansi-regex": "^2.0.0" - } - } - } - }, - "combined-stream": { - "version": "1.0.8", - "resolved": "https://registry.npmjs.org/combined-stream/-/combined-stream-1.0.8.tgz", - "integrity": "sha512-FQN4MRfuJeHf7cBbBMJFXhKSDq+2kAArBlmRBvcvFE5BB1HZKXtSFASDhdlz9zOYwxh8lDdnvmMOe/+5cdoEdg==", - "requires": { - "delayed-stream": "~1.0.0" - } - }, - "commander": { - "version": "8.3.0", - "resolved": "https://registry.npmjs.org/commander/-/commander-8.3.0.tgz", - "integrity": "sha512-OkTL9umf+He2DZkUq8f8J9of7yL6RJKI24dVITBmNfZBmri9zYZQrKkuXiKhyfPSu8tUhnVBB1iKXevvnlR4Ww==", - "dev": true - }, - "commondir": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/commondir/-/commondir-1.0.1.tgz", - "integrity": "sha1-3dgA2gxmEnOTzKWVDqloo6rxJTs=" - }, - "compare-func": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/compare-func/-/compare-func-2.0.0.tgz", - "integrity": "sha512-zHig5N+tPWARooBnb0Zx1MFcdfpyJrfTJ3Y5L+IFvUm8rM74hHz66z0gw0x4tijh5CorKkKUCnW82R2vmpeCRA==", - "dev": true, - "requires": { - "array-ify": "^1.0.0", - "dot-prop": "^5.1.0" - }, - "dependencies": { - "dot-prop": { - "version": "5.3.0", - "resolved": "https://registry.npmjs.org/dot-prop/-/dot-prop-5.3.0.tgz", - "integrity": "sha512-QM8q3zDe58hqUqjraQOmzZ1LIH9SWQJTlEKCH4kJ2oQvLZk7RbQXvtDM2XEq3fwkV9CCvvH4LA0AV+ogFsBM2Q==", - "dev": true, - "requires": { - "is-obj": "^2.0.0" - } - } - } - }, - "complain": { - "version": "1.6.0", - "resolved": "https://registry.npmjs.org/complain/-/complain-1.6.0.tgz", - "integrity": "sha512-9oBfSEfxveaNmo2eSp/vEPkaBVxUhiJTZVgGYayzBchSAXQM6CK1PAQeV5ICShnSgfT+biYzrN7egKwwX+HkCw==", - "requires": { - "error-stack-parser": "^2.0.1" - } - }, - "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==" - }, - "concat-map": { - "version": "0.0.1", - "resolved": "https://registry.npmjs.org/concat-map/-/concat-map-0.0.1.tgz", - "integrity": "sha1-2Klr13/Wjfd5OnMDajug1UBdR3s=" - }, - "concat-stream": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/concat-stream/-/concat-stream-2.0.0.tgz", - "integrity": "sha512-MWufYdFw53ccGjCA+Ol7XJYpAlW6/prSMzuPOTRnJGcGzuhLn4Scrz7qf6o8bROZ514ltazcIFJZevcfbo0x7A==", - "dev": true, - "requires": { - "buffer-from": "^1.0.0", - "inherits": "^2.0.3", - "readable-stream": "^3.0.2", - "typedarray": "^0.0.6" - } - }, - "config": { - "version": "3.3.6", - "resolved": "https://registry.npmjs.org/config/-/config-3.3.6.tgz", - "integrity": "sha512-Hj5916C5HFawjYJat1epbyY2PlAgLpBtDUlr0MxGLgo3p5+7kylyvnRY18PqJHgnNWXcdd0eWDemT7eYWuFgwg==", - "requires": { - "json5": "^2.1.1" - } - }, - "config-chain": { - "version": "1.1.13", - "resolved": "https://registry.npmjs.org/config-chain/-/config-chain-1.1.13.tgz", - "integrity": "sha512-qj+f8APARXHrM0hraqXYb2/bOVSV4PvJQlNZ/DVj0QrmNM2q2euizkeuVckQ57J+W0mRH6Hvi+k50M4Jul2VRQ==", - "dev": true, - "requires": { - "ini": "^1.3.4", - "proto-list": "~1.2.1" - } - }, - "configstore": { - "version": "5.0.1", - "resolved": "https://registry.npmjs.org/configstore/-/configstore-5.0.1.tgz", - "integrity": "sha512-aMKprgk5YhBNyH25hj8wGt2+D52Sw1DRRIzqBwLp2Ya9mFmY8KPvvtvmna8SxVR9JMZ4kzMD68N22vlaRpkeFA==", - "dev": true, - "requires": { - "dot-prop": "^5.2.0", - "graceful-fs": "^4.1.2", - "make-dir": "^3.0.0", - "unique-string": "^2.0.0", - "write-file-atomic": "^3.0.0", - "xdg-basedir": "^4.0.0" - }, - "dependencies": { - "dot-prop": { - "version": "5.3.0", - "resolved": "https://registry.npmjs.org/dot-prop/-/dot-prop-5.3.0.tgz", - "integrity": "sha512-QM8q3zDe58hqUqjraQOmzZ1LIH9SWQJTlEKCH4kJ2oQvLZk7RbQXvtDM2XEq3fwkV9CCvvH4LA0AV+ogFsBM2Q==", - "dev": true, - "requires": { - "is-obj": "^2.0.0" - } - } - } - }, - "console-control-strings": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/console-control-strings/-/console-control-strings-1.1.0.tgz", - "integrity": "sha1-PXz0Rk22RG6mRL9LOVB/mFEAjo4=", - "dev": true - }, - "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==", - "requires": { - "safe-buffer": "5.2.1" - }, - "dependencies": { - "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==" - } - } - }, - "content-type": { - "version": "1.0.4", - "resolved": "https://registry.npmjs.org/content-type/-/content-type-1.0.4.tgz", - "integrity": "sha512-hIP3EEPs8tB9AT1L+NUqtwOAps4mk2Zob89MWXMHjHWg9milF/j4osnnQLXBCBFBk/tvIG/tUc9mOUJiPBhPXA==" - }, - "conventional-changelog-angular": { - "version": "5.0.13", - "resolved": "https://registry.npmjs.org/conventional-changelog-angular/-/conventional-changelog-angular-5.0.13.tgz", - "integrity": "sha512-i/gipMxs7s8L/QeuavPF2hLnJgH6pEZAttySB6aiQLWcX3puWDL3ACVmvBhJGxnAy52Qc15ua26BufY6KpmrVA==", - "dev": true, - "requires": { - "compare-func": "^2.0.0", - "q": "^1.5.1" - } - }, - "conventional-changelog-core": { - "version": "4.2.4", - "resolved": "https://registry.npmjs.org/conventional-changelog-core/-/conventional-changelog-core-4.2.4.tgz", - "integrity": "sha512-gDVS+zVJHE2v4SLc6B0sLsPiloR0ygU7HaDW14aNJE1v4SlqJPILPl/aJC7YdtRE4CybBf8gDwObBvKha8Xlyg==", - "dev": true, - "requires": { - "add-stream": "^1.0.0", - "conventional-changelog-writer": "^5.0.0", - "conventional-commits-parser": "^3.2.0", - "dateformat": "^3.0.0", - "get-pkg-repo": "^4.0.0", - "git-raw-commits": "^2.0.8", - "git-remote-origin-url": "^2.0.0", - "git-semver-tags": "^4.1.1", - "lodash": "^4.17.15", - "normalize-package-data": "^3.0.0", - "q": "^1.5.1", - "read-pkg": "^3.0.0", - "read-pkg-up": "^3.0.0", - "through2": "^4.0.0" - } - }, - "conventional-changelog-preset-loader": { - "version": "2.3.4", - "resolved": "https://registry.npmjs.org/conventional-changelog-preset-loader/-/conventional-changelog-preset-loader-2.3.4.tgz", - "integrity": "sha512-GEKRWkrSAZeTq5+YjUZOYxdHq+ci4dNwHvpaBC3+ENalzFWuCWa9EZXSuZBpkr72sMdKB+1fyDV4takK1Lf58g==", - "dev": true - }, - "conventional-changelog-writer": { - "version": "5.0.1", - "resolved": "https://registry.npmjs.org/conventional-changelog-writer/-/conventional-changelog-writer-5.0.1.tgz", - "integrity": "sha512-5WsuKUfxW7suLblAbFnxAcrvf6r+0b7GvNaWUwUIk0bXMnENP/PEieGKVUQrjPqwPT4o3EPAASBXiY6iHooLOQ==", - "dev": true, - "requires": { - "conventional-commits-filter": "^2.0.7", - "dateformat": "^3.0.0", - "handlebars": "^4.7.7", - "json-stringify-safe": "^5.0.1", - "lodash": "^4.17.15", - "meow": "^8.0.0", - "semver": "^6.0.0", - "split": "^1.0.0", - "through2": "^4.0.0" - }, - "dependencies": { - "semver": { - "version": "6.3.0", - "resolved": "https://registry.npmjs.org/semver/-/semver-6.3.0.tgz", - "integrity": "sha512-b39TBaTSfV6yBrapU89p5fKekE2m/NwnDocOVruQFS1/veMgdzuPcnOM34M6CwxW8jH/lxEa5rBoDeUwu5HHTw==", - "dev": true - } - } - }, - "conventional-commits-filter": { - "version": "2.0.7", - "resolved": "https://registry.npmjs.org/conventional-commits-filter/-/conventional-commits-filter-2.0.7.tgz", - "integrity": "sha512-ASS9SamOP4TbCClsRHxIHXRfcGCnIoQqkvAzCSbZzTFLfcTqJVugB0agRgsEELsqaeWgsXv513eS116wnlSSPA==", - "dev": true, - "requires": { - "lodash.ismatch": "^4.4.0", - "modify-values": "^1.0.0" - } - }, - "conventional-commits-parser": { - "version": "3.2.4", - "resolved": "https://registry.npmjs.org/conventional-commits-parser/-/conventional-commits-parser-3.2.4.tgz", - "integrity": "sha512-nK7sAtfi+QXbxHCYfhpZsfRtaitZLIA6889kFIouLvz6repszQDgxBu7wf2WbU+Dco7sAnNCJYERCwt54WPC2Q==", - "dev": true, - "requires": { - "is-text-path": "^1.0.1", - "JSONStream": "^1.0.4", - "lodash": "^4.17.15", - "meow": "^8.0.0", - "split2": "^3.0.0", - "through2": "^4.0.0" - } - }, - "conventional-recommended-bump": { - "version": "6.1.0", - "resolved": "https://registry.npmjs.org/conventional-recommended-bump/-/conventional-recommended-bump-6.1.0.tgz", - "integrity": "sha512-uiApbSiNGM/kkdL9GTOLAqC4hbptObFo4wW2QRyHsKciGAfQuLU1ShZ1BIVI/+K2BE/W1AWYQMCXAsv4dyKPaw==", - "dev": true, - "requires": { - "concat-stream": "^2.0.0", - "conventional-changelog-preset-loader": "^2.3.4", - "conventional-commits-filter": "^2.0.7", - "conventional-commits-parser": "^3.2.0", - "git-raw-commits": "^2.0.8", - "git-semver-tags": "^4.1.1", - "meow": "^8.0.0", - "q": "^1.5.1" - } - }, - "convert-source-map": { - "version": "1.8.0", - "resolved": "https://registry.npmjs.org/convert-source-map/-/convert-source-map-1.8.0.tgz", - "integrity": "sha512-+OQdjP49zViI/6i7nIJpA8rAl4sV/JdPfU9nZs3VqOwGIgizICvuN2ru6fMd+4llL0tar18UYJXfZ/TWtmhUjA==", - "requires": { - "safe-buffer": "~5.1.1" - } - }, - "cookie": { - "version": "0.4.1", - "resolved": "https://registry.npmjs.org/cookie/-/cookie-0.4.1.tgz", - "integrity": "sha512-ZwrFkGJxUR3EIoXtO+yVE69Eb7KlixbaeAWfBQB9vVsNn/o+Yw69gBWSSDK825hQNdN+wF8zELf3dFNl/kxkUA==" - }, - "cookie-signature": { - "version": "1.0.6", - "resolved": "https://registry.npmjs.org/cookie-signature/-/cookie-signature-1.0.6.tgz", - "integrity": "sha1-4wOogrNCzD7oylE6eZmXNNqzriw=" - }, - "cookiejar": { - "version": "2.1.3", - "resolved": "https://registry.npmjs.org/cookiejar/-/cookiejar-2.1.3.tgz", - "integrity": "sha512-JxbCBUdrfr6AQjOXrxoTvAMJO4HBTUIlBzslcJPAz+/KT8yk53fXun51u+RenNYvad/+Vc2DIz5o9UxlCDymFQ==" - }, - "cookies": { - "version": "0.8.0", - "resolved": "https://registry.npmjs.org/cookies/-/cookies-0.8.0.tgz", - "integrity": "sha512-8aPsApQfebXnuI+537McwYsDtjVxGm8gTIzQI3FDW6t5t/DAhERxtnbEPN/8RX+uZthoz4eCOgloXaE5cYyNow==", - "requires": { - "depd": "~2.0.0", - "keygrip": "~1.1.0" - }, - "dependencies": { - "depd": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/depd/-/depd-2.0.0.tgz", - "integrity": "sha512-g7nH6P6dyDioJogAAGprGpCtVImJhpPk/roCzdb3fIh61/s/nPsfR6onyMwkCAR/OlC3yBC0lESvUoQEAssIrw==" - } - } - }, - "copy-to": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/copy-to/-/copy-to-2.0.1.tgz", - "integrity": "sha1-JoD7uAaKSNCGVrYJgJK9r8kG9KU=" - }, - "core-js": { - "version": "2.6.12", - "resolved": "https://registry.npmjs.org/core-js/-/core-js-2.6.12.tgz", - "integrity": "sha512-Kb2wC0fvsWfQrgk8HU5lW6U/Lcs8+9aaYcy4ZFc6DDlo4nZ7n70dEgE5rtR0oG6ufKDUnrwfWL1mXR5ljDatrQ==" - }, - "core-js-compat": { - "version": "3.20.2", - "resolved": "https://registry.npmjs.org/core-js-compat/-/core-js-compat-3.20.2.tgz", - "integrity": "sha512-qZEzVQ+5Qh6cROaTPFLNS4lkvQ6mBzE3R6A6EEpssj7Zr2egMHgsy4XapdifqJDGC9CBiNv7s+ejI96rLNQFdg==", - "requires": { - "browserslist": "^4.19.1", - "semver": "7.0.0" - }, - "dependencies": { - "semver": { - "version": "7.0.0", - "resolved": "https://registry.npmjs.org/semver/-/semver-7.0.0.tgz", - "integrity": "sha512-+GB6zVA9LWh6zovYQLALHwv5rb2PHGlJi3lfiqIHxR0uuwCgefcOJc59v9fv1w8GbStwxuuqqAjI9NMAOOgq1A==" - } - } - }, - "core-util-is": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/core-util-is/-/core-util-is-1.0.2.tgz", - "integrity": "sha1-tf1UIgqivFq1eqtxQMlAdUUDwac=" - }, - "cors": { - "version": "2.8.5", - "resolved": "https://registry.npmjs.org/cors/-/cors-2.8.5.tgz", - "integrity": "sha512-KIHbLJqu73RGr/hnbrO9uBeixNGuvSQjul/jdFvS/KFSIH1hWVd1ng7zOHx+YrEfInLG7q4n6GHQ9cDtxv/P6g==", - "requires": { - "object-assign": "^4", - "vary": "^1" - } - }, - "cosmiconfig": { - "version": "7.0.1", - "resolved": "https://registry.npmjs.org/cosmiconfig/-/cosmiconfig-7.0.1.tgz", - "integrity": "sha512-a1YWNUV2HwGimB7dU2s1wUMurNKjpx60HxBB6xUM8Re+2s1g1IIfJvFR0/iCF+XHdE0GMTKTuLR32UQff4TEyQ==", - "dev": true, - "requires": { - "@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" - } - }, - "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==" - }, - "cross-spawn": { - "version": "7.0.3", - "resolved": "https://registry.npmjs.org/cross-spawn/-/cross-spawn-7.0.3.tgz", - "integrity": "sha512-iRDPJKUPVEND7dHPO8rkbOnPpyDygcDFtWjpeWNCgy8WP2rXcxXL8TskReQl6OrB2G7+UJrags1q15Fudc7G6w==", - "requires": { - "path-key": "^3.1.0", - "shebang-command": "^2.0.0", - "which": "^2.0.1" - } - }, - "crypto-random-string": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/crypto-random-string/-/crypto-random-string-2.0.0.tgz", - "integrity": "sha512-v1plID3y9r/lPhviJ1wrXpLeyUIGAZ2SHNYTEapm7/8A9nLPoyvVp3RK/EPFqn5kEznyWgYZNsRtYYIWbuG8KA==", - "dev": true - }, - "dargs": { - "version": "7.0.0", - "resolved": "https://registry.npmjs.org/dargs/-/dargs-7.0.0.tgz", - "integrity": "sha512-2iy1EkLdlBzQGvbweYRFxmFath8+K7+AKB0TlhHWkNuH+TmovaMH/Wp7V7R4u7f4SnX3OgLsU9t1NI9ioDnUpg==", - "dev": true - }, - "dashdash": { - "version": "1.14.1", - "resolved": "https://registry.npmjs.org/dashdash/-/dashdash-1.14.1.tgz", - "integrity": "sha1-hTz6D3y+L+1d4gMmuN1YEDX24vA=", - "dev": true, - "requires": { - "assert-plus": "^1.0.0" - } - }, - "dateformat": { - "version": "3.0.3", - "resolved": "https://registry.npmjs.org/dateformat/-/dateformat-3.0.3.tgz", - "integrity": "sha512-jyCETtSl3VMZMWeRo7iY1FL19ges1t55hMo5yaam4Jrsm5EPL89UQkoQRyiI+Yf4k8r2ZpdngkV8hr1lIdjb3Q==", - "dev": true - }, - "debug": { - "version": "4.3.3", - "resolved": "https://registry.npmjs.org/debug/-/debug-4.3.3.tgz", - "integrity": "sha512-/zxw5+vh1Tfv+4Qn7a5nsbcJKPaSvCDhojn6FEl9vupwK2VCSDtEiEtqr8DFtzYFOdz63LBkxec7DYuc2jon6Q==", - "requires": { - "ms": "2.1.2" - } - }, - "debuglog": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/debuglog/-/debuglog-1.0.1.tgz", - "integrity": "sha1-qiT/uaw9+aI1GDfPstJ5NgzXhJI=", - "dev": true - }, - "decamelize": { - "version": "1.2.0", - "resolved": "https://registry.npmjs.org/decamelize/-/decamelize-1.2.0.tgz", - "integrity": "sha1-9lNNFRSCabIDUue+4m9QH5oZEpA=" - }, - "decamelize-keys": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/decamelize-keys/-/decamelize-keys-1.1.0.tgz", - "integrity": "sha1-0XGoeTMlKAfrPLYdwcFEXQeN8tk=", - "dev": true, - "requires": { - "decamelize": "^1.1.0", - "map-obj": "^1.0.0" - }, - "dependencies": { - "map-obj": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/map-obj/-/map-obj-1.0.1.tgz", - "integrity": "sha1-2TPOuSBdgr3PSIb2dCvcK03qFG0=", - "dev": true - } - } - }, - "decode-uri-component": { - "version": "0.2.0", - "resolved": "https://registry.npmjs.org/decode-uri-component/-/decode-uri-component-0.2.0.tgz", - "integrity": "sha1-6zkTMzRYd1y4TNGh+uBiEGu4dUU=", - "dev": true - }, - "decompress-response": { - "version": "3.3.0", - "resolved": "https://registry.npmjs.org/decompress-response/-/decompress-response-3.3.0.tgz", - "integrity": "sha1-gKTdMjdIOEv6JICDYirt7Jgq3/M=", - "dev": true, - "requires": { - "mimic-response": "^1.0.0" - } - }, - "dedent": { - "version": "0.7.0", - "resolved": "https://registry.npmjs.org/dedent/-/dedent-0.7.0.tgz", - "integrity": "sha1-JJXduvbrh0q7Dhvp3yLS5aVEMmw=", - "dev": true - }, - "deep-eql": { - "version": "0.1.3", - "resolved": "https://registry.npmjs.org/deep-eql/-/deep-eql-0.1.3.tgz", - "integrity": "sha1-71WKyrjeJSBs1xOQbXTlaTDrafI=", - "requires": { - "type-detect": "0.1.1" - }, - "dependencies": { - "type-detect": { - "version": "0.1.1", - "resolved": "https://registry.npmjs.org/type-detect/-/type-detect-0.1.1.tgz", - "integrity": "sha1-C6XsKohWQORw6k6FBZcZANrFiCI=" - } - } - }, - "deep-equal": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/deep-equal/-/deep-equal-1.0.1.tgz", - "integrity": "sha1-9dJgKStmDghO/0zbyfCK0yR0SLU=" - }, - "deep-extend": { - "version": "0.6.0", - "resolved": "https://registry.npmjs.org/deep-extend/-/deep-extend-0.6.0.tgz", - "integrity": "sha512-LOHxIOaPYdHlJRtCQfDIVZtfw/ufM8+rVj649RIHzcm/vGwQRXFt6OPqIFWsm2XEMrNIEtWR64sY1LEKD2vAOA==", - "dev": true - }, - "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==" - }, - "default-require-extensions": { - "version": "3.0.0", - "resolved": "https://registry.npmjs.org/default-require-extensions/-/default-require-extensions-3.0.0.tgz", - "integrity": "sha512-ek6DpXq/SCpvjhpFsLFRVtIxJCRw6fUR42lYMVZuUMK7n8eMz4Uh5clckdBjEpLhn/gEBZo7hDJnJcwdKLKQjg==", - "dev": true, - "requires": { - "strip-bom": "^4.0.0" - } - }, - "defaults": { - "version": "1.0.3", - "resolved": "https://registry.npmjs.org/defaults/-/defaults-1.0.3.tgz", - "integrity": "sha1-xlYFHpgX2f8I7YgUd/P+QBnz730=", - "dev": true, - "requires": { - "clone": "^1.0.2" - } - }, - "defer-to-connect": { - "version": "1.1.3", - "resolved": "https://registry.npmjs.org/defer-to-connect/-/defer-to-connect-1.1.3.tgz", - "integrity": "sha512-0ISdNousHvZT2EiFlZeZAHBUvSxmKswVCEf8hW7KWgG4a8MVEu/3Vb6uWYozkjylyCxe0JBIiRB1jV45S70WVQ==", - "dev": true - }, - "define-properties": { - "version": "1.1.3", - "resolved": "https://registry.npmjs.org/define-properties/-/define-properties-1.1.3.tgz", - "integrity": "sha512-3MqfYKj2lLzdMSf8ZIZE/V+Zuy+BgD6f164e8K2w7dgnpKArBDerGYpM46IYYcjnkdPNMjPk9A6VFB8+3SKlXQ==", - "requires": { - "object-keys": "^1.0.12" - } - }, - "delayed-stream": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/delayed-stream/-/delayed-stream-1.0.0.tgz", - "integrity": "sha1-3zrhmayt+31ECqrgsp4icrJOxhk=" - }, - "delegates": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/delegates/-/delegates-1.0.0.tgz", - "integrity": "sha1-hMbhWbgZBP3KWaDvRM2HDTElD5o=" - }, - "denque": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/denque/-/denque-2.0.1.tgz", - "integrity": "sha512-tfiWc6BQLXNLpNiR5iGd0Ocu3P3VpxfzFiqubLgMfhfOw9WyvgJBd46CClNn9k3qfbjvT//0cf7AlYRX/OslMQ==" - }, - "depd": { - "version": "1.1.2", - "resolved": "https://registry.npmjs.org/depd/-/depd-1.1.2.tgz", - "integrity": "sha1-m81S4UwJd2PnSbJ0xDRu0uVgtak=" - }, - "deprecation": { - "version": "2.3.1", - "resolved": "https://registry.npmjs.org/deprecation/-/deprecation-2.3.1.tgz", - "integrity": "sha512-xmHIy4F3scKVwMsQ4WnVaS8bHOx0DmVwRywosKhaILI0ywMDWPtBSku2HNxRvF7jtwDRsoEwYQSfbxj8b7RlJQ==", - "dev": true - }, - "deresolve": { - "version": "1.1.2", - "resolved": "https://registry.npmjs.org/deresolve/-/deresolve-1.1.2.tgz", - "integrity": "sha1-nPI3nI0tYx3EuZVylLkOSnLLbOA=", - "requires": { - "lasso-package-root": "^1.0.0", - "raptor-polyfill": "^1.0.2", - "resolve-from": "^1.0.1" - }, - "dependencies": { - "resolve-from": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/resolve-from/-/resolve-from-1.0.1.tgz", - "integrity": "sha1-Jsv+k10a7uq7Kbw/5a6wHpPUQiY=" - } - } - }, - "destroy": { - "version": "1.0.4", - "resolved": "https://registry.npmjs.org/destroy/-/destroy-1.0.4.tgz", - "integrity": "sha1-l4hXRCxEdJ5CBmE+N5RiBYJqvYA=" - }, - "detect-indent": { - "version": "6.1.0", - "resolved": "https://registry.npmjs.org/detect-indent/-/detect-indent-6.1.0.tgz", - "integrity": "sha512-reYkTUJAZb9gUuZ2RvVCNhVHdg62RHnJ7WJl8ftMi4diZ6NWlciOzQN88pUhSELEwflJht4oQDv0F0BMlwaYtA==", - "dev": true - }, - "dezalgo": { - "version": "1.0.3", - "resolved": "https://registry.npmjs.org/dezalgo/-/dezalgo-1.0.3.tgz", - "integrity": "sha1-f3Qt4Gb8dIvI24IFad3c5Jvw1FY=", - "dev": true, - "requires": { - "asap": "^2.0.0", - "wrappy": "1" - } - }, - "diff": { - "version": "5.0.0", - "resolved": "https://registry.npmjs.org/diff/-/diff-5.0.0.tgz", - "integrity": "sha512-/VTCrvm5Z0JGty/BWHljh+BAiw3IK+2j87NGMu8Nwc/f48WoDAC395uomO9ZD117ZOBaHmkX1oyLvkVM/aIT3w==" - }, - "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, - "requires": { - "path-type": "^4.0.0" - } - }, - "dissolve": { - "version": "0.3.3", - "resolved": "https://registry.npmjs.org/dissolve/-/dissolve-0.3.3.tgz", - "integrity": "sha1-uX7x/ymJx4nOz7AxB+F0EfqL5uU=", - "requires": { - "bl": "^0.7.0", - "readable-stream": "^1.0.26" - }, - "dependencies": { - "isarray": { - "version": "0.0.1", - "resolved": "https://registry.npmjs.org/isarray/-/isarray-0.0.1.tgz", - "integrity": "sha1-ihis/Kmo9Bd+Cav8YDiTmwXR7t8=" - }, - "readable-stream": { - "version": "1.1.14", - "resolved": "https://registry.npmjs.org/readable-stream/-/readable-stream-1.1.14.tgz", - "integrity": "sha1-fPTFTvZI44EwhMY23SB54WbAgdk=", - "requires": { - "core-util-is": "~1.0.0", - "inherits": "~2.0.1", - "isarray": "0.0.1", - "string_decoder": "~0.10.x" - } - }, - "string_decoder": { - "version": "0.10.31", - "resolved": "https://registry.npmjs.org/string_decoder/-/string_decoder-0.10.31.tgz", - "integrity": "sha1-YuIDvEF2bGwoyfyEMB2rHFMQ+pQ=" - } - } - }, - "doctrine": { - "version": "3.0.0", - "resolved": "https://registry.npmjs.org/doctrine/-/doctrine-3.0.0.tgz", - "integrity": "sha512-yS+Q5i3hBf7GBkd4KG8a7eBNNWNGLTaEwwYWUijIYM7zrlYDM0BFXHjjPWlWZ1Rg7UaddZeIDmi9jF3HmqiQ2w==", - "dev": true, - "requires": { - "esutils": "^2.0.2" - } - }, - "dot-prop": { - "version": "6.0.1", - "resolved": "https://registry.npmjs.org/dot-prop/-/dot-prop-6.0.1.tgz", - "integrity": "sha512-tE7ztYzXHIeyvc7N+hR3oi7FIbf/NIjVP9hmAt3yMXzrQ072/fpjGLx2GxNxGxUl5V73MEqYzioOMoVhGMJ5cA==", - "dev": true, - "requires": { - "is-obj": "^2.0.0" - } - }, - "duplexer": { - "version": "0.1.2", - "resolved": "https://registry.npmjs.org/duplexer/-/duplexer-0.1.2.tgz", - "integrity": "sha512-jtD6YG370ZCIi/9GTaJKQxWTZD045+4R4hTk/x1UyoqadyJ9x9CgSi1RlVDQF8U2sxLLSnFkCaMihqljHIWgMg==", - "dev": true - }, - "duplexer3": { - "version": "0.1.4", - "resolved": "https://registry.npmjs.org/duplexer3/-/duplexer3-0.1.4.tgz", - "integrity": "sha1-7gHdHKwO08vH/b6jfcCo8c4ALOI=", - "dev": true - }, - "ecc-jsbn": { - "version": "0.1.2", - "resolved": "https://registry.npmjs.org/ecc-jsbn/-/ecc-jsbn-0.1.2.tgz", - "integrity": "sha1-OoOpBOVDUyh4dMVkt1SThoSamMk=", - "dev": true, - "requires": { - "jsbn": "~0.1.0", - "safer-buffer": "^2.1.0" - } - }, - "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==", - "requires": { - "safe-buffer": "^5.0.1" - } - }, - "ee-first": { - "version": "1.1.1", - "resolved": "https://registry.npmjs.org/ee-first/-/ee-first-1.1.1.tgz", - "integrity": "sha1-WQxhFWsK4vTwJVcyoViyZrxWsh0=" - }, - "electron-to-chromium": { - "version": "1.4.32", - "resolved": "https://registry.npmjs.org/electron-to-chromium/-/electron-to-chromium-1.4.32.tgz", - "integrity": "sha512-7QRVfMlccTFs7cZV3lB0k9Wcm6R6F+w1yBPX+xBAlAP/1oJIstxTev3A4r8REnUUAFph/cIB8y/EBU7PDbJTQw==" - }, - "elliptic": { - "version": "6.5.4", - "resolved": "https://registry.npmjs.org/elliptic/-/elliptic-6.5.4.tgz", - "integrity": "sha512-iLhC6ULemrljPZb+QutR5TQGB+pdW6KGD5RSegS+8sorOZT+rdQFbsQFJgvN3eRqNALqJer4oQ16YvJHlU8hzQ==", - "optional": true, - "requires": { - "bn.js": "^4.11.9", - "brorand": "^1.1.0", - "hash.js": "^1.0.0", - "hmac-drbg": "^1.0.1", - "inherits": "^2.0.4", - "minimalistic-assert": "^1.0.1", - "minimalistic-crypto-utils": "^1.0.1" - } - }, - "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==" - }, - "emojis-list": { - "version": "3.0.0", - "resolved": "https://registry.npmjs.org/emojis-list/-/emojis-list-3.0.0.tgz", - "integrity": "sha512-/kyM18EfinwXZbno9FyUGeFh87KC8HRQBQGildHZbEuRyWFOmv1U10o9BBp8XVZDVNNuQKyIGIu5ZYAAXJ0V2Q==" - }, - "encodeurl": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/encodeurl/-/encodeurl-1.0.2.tgz", - "integrity": "sha1-rT/0yG7C0CkyL1oCw6mmBslbP1k=" - }, - "encoding": { - "version": "0.1.13", - "resolved": "https://registry.npmjs.org/encoding/-/encoding-0.1.13.tgz", - "integrity": "sha512-ETBauow1T35Y/WZMkio9jiM0Z5xjHHmJ4XmjZOq1l/dXz3lr2sRn87nJy20RupqSh1F2m3HHPSp8ShIPQJrJ3A==", - "dev": true, - "optional": true, - "requires": { - "iconv-lite": "^0.6.2" - }, - "dependencies": { - "iconv-lite": { - "version": "0.6.3", - "resolved": "https://registry.npmjs.org/iconv-lite/-/iconv-lite-0.6.3.tgz", - "integrity": "sha512-4fCk79wshMdzMp2rH06qWrJE4iolqLhCUH+OiuIgU++RB0+94NlDL81atO7GX55uUKueo0txHNtvEyI6D7WdMw==", - "dev": true, - "optional": true, - "requires": { - "safer-buffer": ">= 2.1.2 < 3.0.0" - } - } - } - }, - "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, - "requires": { - "once": "^1.4.0" - } - }, - "engine.io": { - "version": "6.1.0", - "resolved": "https://registry.npmjs.org/engine.io/-/engine.io-6.1.0.tgz", - "integrity": "sha512-ErhZOVu2xweCjEfYcTdkCnEYUiZgkAcBBAhW4jbIvNG8SLU3orAqoJCiytZjYF7eTpVmmCrLDjLIEaPlUAs1uw==", - "requires": { - "@types/cookie": "^0.4.1", - "@types/cors": "^2.8.12", - "@types/node": ">=10.0.0", - "accepts": "~1.3.4", - "base64id": "2.0.0", - "cookie": "~0.4.1", - "cors": "~2.8.5", - "debug": "~4.3.1", - "engine.io-parser": "~5.0.0", - "ws": "~8.2.3" - }, - "dependencies": { - "ws": { - "version": "8.2.3", - "resolved": "https://registry.npmjs.org/ws/-/ws-8.2.3.tgz", - "integrity": "sha512-wBuoj1BDpC6ZQ1B7DWQBYVLphPWkm8i9Y0/3YdHjHKHiohOJ1ws+3OccDWtH+PoC9DZD5WOTrJvNbWvjS6JWaA==", - "requires": {} - } - } - }, - "engine.io-client": { - "version": "6.1.1", - "resolved": "https://registry.npmjs.org/engine.io-client/-/engine.io-client-6.1.1.tgz", - "integrity": "sha512-V05mmDo4gjimYW+FGujoGmmmxRaDsrVr7AXA3ZIfa04MWM1jOfZfUwou0oNqhNwy/votUDvGDt4JA4QF4e0b4g==", - "requires": { - "@socket.io/component-emitter": "~3.0.0", - "debug": "~4.3.1", - "engine.io-parser": "~5.0.0", - "has-cors": "1.1.0", - "parseqs": "0.0.6", - "parseuri": "0.0.6", - "ws": "~8.2.3", - "xmlhttprequest-ssl": "~2.0.0", - "yeast": "0.1.2" - }, - "dependencies": { - "ws": { - "version": "8.2.3", - "resolved": "https://registry.npmjs.org/ws/-/ws-8.2.3.tgz", - "integrity": "sha512-wBuoj1BDpC6ZQ1B7DWQBYVLphPWkm8i9Y0/3YdHjHKHiohOJ1ws+3OccDWtH+PoC9DZD5WOTrJvNbWvjS6JWaA==", - "requires": {} - } - } - }, - "engine.io-parser": { - "version": "5.0.2", - "resolved": "https://registry.npmjs.org/engine.io-parser/-/engine.io-parser-5.0.2.tgz", - "integrity": "sha512-wuiO7qO/OEkPJSFueuATIXtrxF7/6GTbAO9QLv7nnbjwZ5tYhLm9zxvLwxstRs0dcT0KUlWTjtIOs1T86jt12g==", - "requires": { - "base64-arraybuffer": "~1.0.1" - } - }, - "enhanced-resolve": { - "version": "5.8.3", - "resolved": "https://registry.npmjs.org/enhanced-resolve/-/enhanced-resolve-5.8.3.tgz", - "integrity": "sha512-EGAbGvH7j7Xt2nc0E7D99La1OiEs8LnyimkRgwExpUMScN6O+3x9tIWs7PLQZVNx4YD+00skHXPXi1yQHpAmZA==", - "requires": { - "graceful-fs": "^4.2.4", - "tapable": "^2.2.0" - } - }, - "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, - "requires": { - "ansi-colors": "^4.1.1" - } - }, - "env-paths": { - "version": "2.2.1", - "resolved": "https://registry.npmjs.org/env-paths/-/env-paths-2.2.1.tgz", - "integrity": "sha512-+h1lkLKhZMTYjog1VEpJNG7NZJWcuc2DDk/qsqSTRRCOXiLjeQ1d1/udrUGhqMxUgAlwKNZ0cf2uqan5GLuS2A==", - "dev": true - }, - "envinfo": { - "version": "7.8.1", - "resolved": "https://registry.npmjs.org/envinfo/-/envinfo-7.8.1.tgz", - "integrity": "sha512-/o+BXHmB7ocbHEAs6F2EnG0ogybVVUdkRunTT2glZU9XAaGmhqskrvKwqXuDfNjEO0LZKWdejEEpnq8aM0tOaw==" - }, - "err-code": { - "version": "2.0.3", - "resolved": "https://registry.npmjs.org/err-code/-/err-code-2.0.3.tgz", - "integrity": "sha512-2bmlRpNKBxT/CRmPOlyISQpNj+qSeYvcym/uT0Jx2bMOlKLtSy1ZmLuVxSEKKyor/N5yhvp/ZiG1oE3DEYMSFA==", - "dev": true - }, - "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==", - "requires": { - "is-arrayish": "^0.2.1" - } - }, - "error-stack-parser": { - "version": "2.0.6", - "resolved": "https://registry.npmjs.org/error-stack-parser/-/error-stack-parser-2.0.6.tgz", - "integrity": "sha512-d51brTeqC+BHlwF0BhPtcYgF5nlzf9ZZ0ZIUQNZpc9ZB9qw5IJ2diTrBY9jlCJkTLITYPjmiX6OWCwH+fuyNgQ==", - "requires": { - "stackframe": "^1.1.1" - } - }, - "es-abstract": { - "version": "1.19.1", - "resolved": "https://registry.npmjs.org/es-abstract/-/es-abstract-1.19.1.tgz", - "integrity": "sha512-2vJ6tjA/UfqLm2MPs7jxVybLoB8i1t1Jd9R3kISld20sIxPcTbLuggQOUxeWeAvIUkduv/CfMjuh4WmiXr2v9w==", - "dev": true, - "requires": { - "call-bind": "^1.0.2", - "es-to-primitive": "^1.2.1", - "function-bind": "^1.1.1", - "get-intrinsic": "^1.1.1", - "get-symbol-description": "^1.0.0", - "has": "^1.0.3", - "has-symbols": "^1.0.2", - "internal-slot": "^1.0.3", - "is-callable": "^1.2.4", - "is-negative-zero": "^2.0.1", - "is-regex": "^1.1.4", - "is-shared-array-buffer": "^1.0.1", - "is-string": "^1.0.7", - "is-weakref": "^1.0.1", - "object-inspect": "^1.11.0", - "object-keys": "^1.1.1", - "object.assign": "^4.1.2", - "string.prototype.trimend": "^1.0.4", - "string.prototype.trimstart": "^1.0.4", - "unbox-primitive": "^1.0.1" - } - }, - "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==" - }, - "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, - "requires": { - "is-callable": "^1.1.4", - "is-date-object": "^1.0.1", - "is-symbol": "^1.0.2" - } - }, - "es6-error": { - "version": "4.1.1", - "resolved": "https://registry.npmjs.org/es6-error/-/es6-error-4.1.1.tgz", - "integrity": "sha512-Um/+FxMr9CISWh0bi5Zv0iOD+4cFh5qLeks1qhAopKVAJw3drgKbKySikp7wGhDL0HPeaja0P5ULZrxLkniUVg==", - "dev": true - }, - "es6-promise": { - "version": "4.2.8", - "resolved": "https://registry.npmjs.org/es6-promise/-/es6-promise-4.2.8.tgz", - "integrity": "sha512-HJDGx5daxeIvxdBxvG2cb9g4tEvwIk3i8+nhX0yGrYmZUzbkdg8QbDevheDB8gd0//uPj4c1EQua8Q+MViT0/w==" - }, - "es6-promisify": { - "version": "5.0.0", - "resolved": "https://registry.npmjs.org/es6-promisify/-/es6-promisify-5.0.0.tgz", - "integrity": "sha1-UQnWLz5W6pZ8S2NQWu8IKRyKUgM=", - "requires": { - "es6-promise": "^4.0.3" - } - }, - "escalade": { - "version": "3.1.1", - "resolved": "https://registry.npmjs.org/escalade/-/escalade-3.1.1.tgz", - "integrity": "sha512-k0er2gUkLf8O0zKJiAhmkTnJlTvINGv7ygDNPbeIsX/TJjGJZHuh9B2UxbsaEkmlEo9MfhrSzmhIlhRlI2GXnw==" - }, - "escape-goat": { - "version": "2.1.1", - "resolved": "https://registry.npmjs.org/escape-goat/-/escape-goat-2.1.1.tgz", - "integrity": "sha512-8/uIhbG12Csjy2JEW7D9pHbreaVaS/OpN3ycnyvElTdwM5n6GY6W6e2IPemfvGZeUMqZ9A/3GqIZMgKnBhAw/Q==", - "dev": true - }, - "escape-html": { - "version": "1.0.3", - "resolved": "https://registry.npmjs.org/escape-html/-/escape-html-1.0.3.tgz", - "integrity": "sha1-Aljq5NPQwJdN4cFpGI7wBR0dGYg=" - }, - "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==" - }, - "escodegen": { - "version": "1.14.3", - "resolved": "https://registry.npmjs.org/escodegen/-/escodegen-1.14.3.tgz", - "integrity": "sha512-qFcX0XJkdg+PB3xjZZG/wKSuT1PnQWx57+TVSjIMmILd2yC/6ByYElPwJnslDsuWuSAp4AwJGumarAAmJch5Kw==", - "requires": { - "esprima": "^4.0.1", - "estraverse": "^4.2.0", - "esutils": "^2.0.2", - "optionator": "^0.8.1", - "source-map": "~0.6.1" - }, - "dependencies": { - "levn": { - "version": "0.3.0", - "resolved": "https://registry.npmjs.org/levn/-/levn-0.3.0.tgz", - "integrity": "sha1-OwmSTt+fCDwEkP3UwLxEIeBHZO4=", - "requires": { - "prelude-ls": "~1.1.2", - "type-check": "~0.3.2" - } - }, - "optionator": { - "version": "0.8.3", - "resolved": "https://registry.npmjs.org/optionator/-/optionator-0.8.3.tgz", - "integrity": "sha512-+IW9pACdk3XWmmTXG8m3upGUJst5XRGzxMRjXzAuJ1XnIFNvfhjjIuYkDvysnPQ7qzqVzLt78BCruntqRhWQbA==", - "requires": { - "deep-is": "~0.1.3", - "fast-levenshtein": "~2.0.6", - "levn": "~0.3.0", - "prelude-ls": "~1.1.2", - "type-check": "~0.3.2", - "word-wrap": "~1.2.3" - } - }, - "prelude-ls": { - "version": "1.1.2", - "resolved": "https://registry.npmjs.org/prelude-ls/-/prelude-ls-1.1.2.tgz", - "integrity": "sha1-IZMqVJ9eUv/ZqCf1cOBL5iqX2lQ=" - }, - "type-check": { - "version": "0.3.2", - "resolved": "https://registry.npmjs.org/type-check/-/type-check-0.3.2.tgz", - "integrity": "sha1-WITKtRLPHTVeP7eE8wgEsrUg23I=", - "requires": { - "prelude-ls": "~1.1.2" - } - } - } - }, - "eslint": { - "version": "8.6.0", - "resolved": "https://registry.npmjs.org/eslint/-/eslint-8.6.0.tgz", - "integrity": "sha512-UvxdOJ7mXFlw7iuHZA4jmzPaUqIw54mZrv+XPYKNbKdLR0et4rf60lIZUU9kiNtnzzMzGWxMV+tQ7uG7JG8DPw==", - "dev": true, - "requires": { - "@eslint/eslintrc": "^1.0.5", - "@humanwhocodes/config-array": "^0.9.2", - "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": "^7.1.0", - "eslint-utils": "^3.0.0", - "eslint-visitor-keys": "^3.1.0", - "espree": "^9.3.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" - }, - "dependencies": { - "ajv": { - "version": "6.12.6", - "resolved": "https://registry.npmjs.org/ajv/-/ajv-6.12.6.tgz", - "integrity": "sha512-j3fVLgvTo527anyYyJOGTYJbG+vnnQYvE0m5mmkc1TK+nxAppkCLMIL0aZ4dblVCNoGShhm+kzE4ZUykBoMg4g==", - "dev": true, - "requires": { - "fast-deep-equal": "^3.1.1", - "fast-json-stable-stringify": "^2.0.0", - "json-schema-traverse": "^0.4.1", - "uri-js": "^4.2.2" - } - }, - "eslint-scope": { - "version": "7.1.0", - "resolved": "https://registry.npmjs.org/eslint-scope/-/eslint-scope-7.1.0.tgz", - "integrity": "sha512-aWwkhnS0qAXqNOgKOK0dJ2nvzEbhEvpy8OlJ9kZ0FeZnA6zpjv1/Vei+puGFFX7zkPCkHHXb7IDX3A+7yPrRWg==", - "dev": true, - "requires": { - "esrecurse": "^4.3.0", - "estraverse": "^5.2.0" - } - }, - "estraverse": { - "version": "5.3.0", - "resolved": "https://registry.npmjs.org/estraverse/-/estraverse-5.3.0.tgz", - "integrity": "sha512-MMdARuVEQziNTeJD8DgMqmhwR11BRQ/cBP+pLtYdSTnf3MIO8fFeiINEbX36ZdNlfU/7A9f3gUw49B3oQsvwBA==", - "dev": true - }, - "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 - }, - "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 - } - } - }, - "eslint-import-resolver-node": { - "version": "0.3.6", - "resolved": "https://registry.npmjs.org/eslint-import-resolver-node/-/eslint-import-resolver-node-0.3.6.tgz", - "integrity": "sha512-0En0w03NRVMn9Uiyn8YRPDKvWjxCWkslUEhGNTdGx15RvPJYQ+lbOlqrlNI2vEAs4pDYK4f/HN2TbDmk5TP0iw==", - "dev": true, - "requires": { - "debug": "^3.2.7", - "resolve": "^1.20.0" - }, - "dependencies": { - "debug": { - "version": "3.2.7", - "resolved": "https://registry.npmjs.org/debug/-/debug-3.2.7.tgz", - "integrity": "sha512-CFjzYYAi4ThfiQvizrFQevTTXHtnCqWfe7x1AhgEscTz6ZbLbfoLRLPugTQyBth6f8ZERVUSyWHFD/7Wu4t1XQ==", - "dev": true, - "requires": { - "ms": "^2.1.1" - } - } - } - }, - "eslint-module-utils": { - "version": "2.7.2", - "resolved": "https://registry.npmjs.org/eslint-module-utils/-/eslint-module-utils-2.7.2.tgz", - "integrity": "sha512-zquepFnWCY2ISMFwD/DqzaM++H+7PDzOpUvotJWm/y1BAFt5R4oeULgdrTejKqLkz7MA/tgstsUMNYc7wNdTrg==", - "dev": true, - "requires": { - "debug": "^3.2.7", - "find-up": "^2.1.0" - }, - "dependencies": { - "debug": { - "version": "3.2.7", - "resolved": "https://registry.npmjs.org/debug/-/debug-3.2.7.tgz", - "integrity": "sha512-CFjzYYAi4ThfiQvizrFQevTTXHtnCqWfe7x1AhgEscTz6ZbLbfoLRLPugTQyBth6f8ZERVUSyWHFD/7Wu4t1XQ==", - "dev": true, - "requires": { - "ms": "^2.1.1" - } - } - } - }, - "eslint-plugin-import": { - "version": "2.25.4", - "resolved": "https://registry.npmjs.org/eslint-plugin-import/-/eslint-plugin-import-2.25.4.tgz", - "integrity": "sha512-/KJBASVFxpu0xg1kIBn9AUa8hQVnszpwgE7Ld0lKAlx7Ie87yzEzCgSkekt+le/YVhiaosO4Y14GDAOc41nfxA==", - "dev": true, - "requires": { - "array-includes": "^3.1.4", - "array.prototype.flat": "^1.2.5", - "debug": "^2.6.9", - "doctrine": "^2.1.0", - "eslint-import-resolver-node": "^0.3.6", - "eslint-module-utils": "^2.7.2", - "has": "^1.0.3", - "is-core-module": "^2.8.0", - "is-glob": "^4.0.3", - "minimatch": "^3.0.4", - "object.values": "^1.1.5", - "resolve": "^1.20.0", - "tsconfig-paths": "^3.12.0" - }, - "dependencies": { - "debug": { - "version": "2.6.9", - "resolved": "https://registry.npmjs.org/debug/-/debug-2.6.9.tgz", - "integrity": "sha512-bC7ElrdJaJnPbAP+1EotYvqZsb3ecl5wi6Bfi6BJTUcNowp6cvspg0jXznRTKDjm/E7AdgFBVeAPVMNcKGsHMA==", - "dev": true, - "requires": { - "ms": "2.0.0" - } - }, - "doctrine": { - "version": "2.1.0", - "resolved": "https://registry.npmjs.org/doctrine/-/doctrine-2.1.0.tgz", - "integrity": "sha512-35mSku4ZXK0vfCuHEDAwt55dg2jNajHZ1odvF+8SSr82EsZY4QmXfuWso8oEd8zRhVObSN18aM0CjSdoBX7zIw==", - "dev": true, - "requires": { - "esutils": "^2.0.2" - } - }, - "ms": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/ms/-/ms-2.0.0.tgz", - "integrity": "sha1-VgiurfwAvmwpAd9fmGF4jeDVl8g=", - "dev": true - } - } - }, - "eslint-plugin-prefer-arrow": { - "version": "1.2.3", - "resolved": "https://registry.npmjs.org/eslint-plugin-prefer-arrow/-/eslint-plugin-prefer-arrow-1.2.3.tgz", - "integrity": "sha512-J9I5PKCOJretVuiZRGvPQxCbllxGAV/viI20JO3LYblAodofBxyMnZAJ+WGeClHgANnSJberTNoFWWjrWKBuXQ==", - "dev": true, - "requires": {} - }, - "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==", - "requires": { - "esrecurse": "^4.3.0", - "estraverse": "^4.1.1" - } - }, - "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, - "requires": { - "eslint-visitor-keys": "^2.0.0" - }, - "dependencies": { - "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 - } - } - }, - "eslint-visitor-keys": { - "version": "3.1.0", - "resolved": "https://registry.npmjs.org/eslint-visitor-keys/-/eslint-visitor-keys-3.1.0.tgz", - "integrity": "sha512-yWJFpu4DtjsWKkt5GeNBBuZMlNcYVs6vRCLoCVEJrTjaSB6LC98gFipNK/erM2Heg/E8mIK+hXG/pJMLK+eRZA==", - "dev": true - }, - "espree": { - "version": "9.3.0", - "resolved": "https://registry.npmjs.org/espree/-/espree-9.3.0.tgz", - "integrity": "sha512-d/5nCsb0JcqsSEeQzFZ8DH1RmxPcglRWh24EFTlUEmCKoehXGdpsx0RkHDubqUI8LSAIKMQp4r9SzQ3n+sm4HQ==", - "dev": true, - "requires": { - "acorn": "^8.7.0", - "acorn-jsx": "^5.3.1", - "eslint-visitor-keys": "^3.1.0" - } - }, - "esprima": { - "version": "4.0.1", - "resolved": "https://registry.npmjs.org/esprima/-/esprima-4.0.1.tgz", - "integrity": "sha512-eGuFFw7Upda+g4p+QHvnW0RyTX/SVeJBDM/gCtMARO0cLuT2HcEKnTPvhjV6aGeqrCB/sbNop0Kszm0jsaWU4A==" - }, - "esquery": { - "version": "1.4.0", - "resolved": "https://registry.npmjs.org/esquery/-/esquery-1.4.0.tgz", - "integrity": "sha512-cCDispWt5vHHtwMY2YrAQ4ibFkAL8RbH5YGBnZBc90MolvvfkkQcJro/aZiAQUlQ3qgrYS6D6v8Gc5G5CQsc9w==", - "dev": true, - "requires": { - "estraverse": "^5.1.0" - }, - "dependencies": { - "estraverse": { - "version": "5.3.0", - "resolved": "https://registry.npmjs.org/estraverse/-/estraverse-5.3.0.tgz", - "integrity": "sha512-MMdARuVEQziNTeJD8DgMqmhwR11BRQ/cBP+pLtYdSTnf3MIO8fFeiINEbX36ZdNlfU/7A9f3gUw49B3oQsvwBA==", - "dev": true - } - } - }, - "esrecurse": { - "version": "4.3.0", - "resolved": "https://registry.npmjs.org/esrecurse/-/esrecurse-4.3.0.tgz", - "integrity": "sha512-KmfKL3b6G+RXvP8N1vr3Tq1kL/oCFgn2NYXEtqP8/L3pKapUA4G8cFVaoF3SU323CD4XypR/ffioHmkti6/Tag==", - "requires": { - "estraverse": "^5.2.0" - }, - "dependencies": { - "estraverse": { - "version": "5.3.0", - "resolved": "https://registry.npmjs.org/estraverse/-/estraverse-5.3.0.tgz", - "integrity": "sha512-MMdARuVEQziNTeJD8DgMqmhwR11BRQ/cBP+pLtYdSTnf3MIO8fFeiINEbX36ZdNlfU/7A9f3gUw49B3oQsvwBA==" - } - } - }, - "estraverse": { - "version": "4.3.0", - "resolved": "https://registry.npmjs.org/estraverse/-/estraverse-4.3.0.tgz", - "integrity": "sha512-39nnKffWz8xN1BU/2c79n9nB9HDzo0niYUqx6xyqUnyoAnQyyWpOTdZEeiCch8BBu515t4wp9ZmgVfVhn9EBpw==" - }, - "esutils": { - "version": "2.0.3", - "resolved": "https://registry.npmjs.org/esutils/-/esutils-2.0.3.tgz", - "integrity": "sha512-kVscqXk4OCp68SZ0dkgEKVi6/8ij300KBWTJq32P/dYeWTSwK41WyTxalN1eRmA5Z9UU/LX9D7FWSmV9SAYx6g==" - }, - "etag": { - "version": "1.8.1", - "resolved": "https://registry.npmjs.org/etag/-/etag-1.8.1.tgz", - "integrity": "sha1-Qa4u62XvpiJorr/qg6x9eSmbCIc=" - }, - "eventemitter3": { - "version": "4.0.7", - "resolved": "https://registry.npmjs.org/eventemitter3/-/eventemitter3-4.0.7.tgz", - "integrity": "sha512-8guHBZCwKnFhYdHr2ysuRWErTwhoN2X8XELRlrRwpmfeY2jjuUN4taQMsULKUVo1K4DvZl+0pgfyoysHxvmvEw==", - "dev": true - }, - "events": { - "version": "3.3.0", - "resolved": "https://registry.npmjs.org/events/-/events-3.3.0.tgz", - "integrity": "sha512-mQw+2fkQbALzQ7V0MY0IqdnXNOeTtP4r0lN9z7AAawCXgqea7bDii20AYrIBrFd/Hx0M2Ocz6S111CaFkUcb0Q==" - }, - "events-light": { - "version": "1.0.5", - "resolved": "https://registry.npmjs.org/events-light/-/events-light-1.0.5.tgz", - "integrity": "sha1-lk5jRQugr0prAiqpVbF//vZXte4=", - "requires": { - "chai": "^3.5.0" - } - }, - "execa": { - "version": "5.1.1", - "resolved": "https://registry.npmjs.org/execa/-/execa-5.1.1.tgz", - "integrity": "sha512-8uSpZZocAZRBAPIEINJj3Lo9HyGitllczc27Eh5YYojjMFMn8yHMDMaUHE2Jqfq05D/wucwI4JGURyXt1vchyg==", - "requires": { - "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" - } - }, - "expand-brackets": { - "version": "0.1.5", - "resolved": "https://registry.npmjs.org/expand-brackets/-/expand-brackets-0.1.5.tgz", - "integrity": "sha1-3wcoTjQqgHzXM6xa9yQR5YHRF3s=", - "requires": { - "is-posix-bracket": "^0.1.0" - } - }, - "expand-range": { - "version": "1.8.2", - "resolved": "https://registry.npmjs.org/expand-range/-/expand-range-1.8.2.tgz", - "integrity": "sha1-opnv/TNf4nIeuujiV+x5ZE/IUzc=", - "requires": { - "fill-range": "^2.1.0" - }, - "dependencies": { - "fill-range": { - "version": "2.2.4", - "resolved": "https://registry.npmjs.org/fill-range/-/fill-range-2.2.4.tgz", - "integrity": "sha512-cnrcCbj01+j2gTG921VZPnHbjmdAf8oQV/iGeV2kZxGSyfYjjTyY79ErsK1WJWMpw6DaApEX72binqJE+/d+5Q==", - "requires": { - "is-number": "^2.1.0", - "isobject": "^2.0.0", - "randomatic": "^3.0.0", - "repeat-element": "^1.1.2", - "repeat-string": "^1.5.2" - } - }, - "is-number": { - "version": "2.1.0", - "resolved": "https://registry.npmjs.org/is-number/-/is-number-2.1.0.tgz", - "integrity": "sha1-Afy7s5NGOlSPL0ZszhbezknbkI8=", - "requires": { - "kind-of": "^3.0.2" - } - }, - "isobject": { - "version": "2.1.0", - "resolved": "https://registry.npmjs.org/isobject/-/isobject-2.1.0.tgz", - "integrity": "sha1-8GVWEJaj8dou9GJy+BXIQNh+DIk=", - "requires": { - "isarray": "1.0.0" - } - }, - "kind-of": { - "version": "3.2.2", - "resolved": "https://registry.npmjs.org/kind-of/-/kind-of-3.2.2.tgz", - "integrity": "sha1-MeohpzS6ubuw8yRm2JOupR5KPGQ=", - "requires": { - "is-buffer": "^1.1.5" - } - } - } - }, - "express": { - "version": "4.17.2", - "resolved": "https://registry.npmjs.org/express/-/express-4.17.2.tgz", - "integrity": "sha512-oxlxJxcQlYwqPWKVJJtvQiwHgosH/LrLSPA+H4UxpyvSS6jC5aH+5MoHFM+KABgTOt0APue4w66Ha8jCUo9QGg==", - "requires": { - "accepts": "~1.3.7", - "array-flatten": "1.1.1", - "body-parser": "1.19.1", - "content-disposition": "0.5.4", - "content-type": "~1.0.4", - "cookie": "0.4.1", - "cookie-signature": "1.0.6", - "debug": "2.6.9", - "depd": "~1.1.2", - "encodeurl": "~1.0.2", - "escape-html": "~1.0.3", - "etag": "~1.8.1", - "finalhandler": "~1.1.2", - "fresh": "0.5.2", - "merge-descriptors": "1.0.1", - "methods": "~1.1.2", - "on-finished": "~2.3.0", - "parseurl": "~1.3.3", - "path-to-regexp": "0.1.7", - "proxy-addr": "~2.0.7", - "qs": "6.9.6", - "range-parser": "~1.2.1", - "safe-buffer": "5.2.1", - "send": "0.17.2", - "serve-static": "1.14.2", - "setprototypeof": "1.2.0", - "statuses": "~1.5.0", - "type-is": "~1.6.18", - "utils-merge": "1.0.1", - "vary": "~1.1.2" - }, - "dependencies": { - "debug": { - "version": "2.6.9", - "resolved": "https://registry.npmjs.org/debug/-/debug-2.6.9.tgz", - "integrity": "sha512-bC7ElrdJaJnPbAP+1EotYvqZsb3ecl5wi6Bfi6BJTUcNowp6cvspg0jXznRTKDjm/E7AdgFBVeAPVMNcKGsHMA==", - "requires": { - "ms": "2.0.0" - } - }, - "ms": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/ms/-/ms-2.0.0.tgz", - "integrity": "sha1-VgiurfwAvmwpAd9fmGF4jeDVl8g=" - }, - "qs": { - "version": "6.9.6", - "resolved": "https://registry.npmjs.org/qs/-/qs-6.9.6.tgz", - "integrity": "sha512-TIRk4aqYLNoJUbd+g2lEdz5kLWIuTMRagAXxl78Q0RiVjAOugHmeKNGdd3cwo/ktpf9aL9epCfFqWDEKysUlLQ==" - }, - "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==" - } - } - }, - "express-session": { - "version": "1.17.2", - "resolved": "https://registry.npmjs.org/express-session/-/express-session-1.17.2.tgz", - "integrity": "sha512-mPcYcLA0lvh7D4Oqr5aNJFMtBMKPLl++OKKxkHzZ0U0oDq1rpKBnkR5f5vCHR26VeArlTOEF9td4x5IjICksRQ==", - "requires": { - "cookie": "0.4.1", - "cookie-signature": "1.0.6", - "debug": "2.6.9", - "depd": "~2.0.0", - "on-headers": "~1.0.2", - "parseurl": "~1.3.3", - "safe-buffer": "5.2.1", - "uid-safe": "~2.1.5" - }, - "dependencies": { - "debug": { - "version": "2.6.9", - "resolved": "https://registry.npmjs.org/debug/-/debug-2.6.9.tgz", - "integrity": "sha512-bC7ElrdJaJnPbAP+1EotYvqZsb3ecl5wi6Bfi6BJTUcNowp6cvspg0jXznRTKDjm/E7AdgFBVeAPVMNcKGsHMA==", - "requires": { - "ms": "2.0.0" - } - }, - "depd": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/depd/-/depd-2.0.0.tgz", - "integrity": "sha512-g7nH6P6dyDioJogAAGprGpCtVImJhpPk/roCzdb3fIh61/s/nPsfR6onyMwkCAR/OlC3yBC0lESvUoQEAssIrw==" - }, - "ms": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/ms/-/ms-2.0.0.tgz", - "integrity": "sha1-VgiurfwAvmwpAd9fmGF4jeDVl8g=" - }, - "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==" - } - } - }, - "extend": { - "version": "3.0.2", - "resolved": "https://registry.npmjs.org/extend/-/extend-3.0.2.tgz", - "integrity": "sha512-fjquC59cD7CyW6urNXK0FBufkZcoiGG80wTuPujX590cB5Ttln20E2UB4S/WARVqhXffZl2LNgS+gQdPIIim/g==" - }, - "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, - "requires": { - "chardet": "^0.7.0", - "iconv-lite": "^0.4.24", - "tmp": "^0.0.33" - } - }, - "extglob": { - "version": "0.3.2", - "resolved": "https://registry.npmjs.org/extglob/-/extglob-0.3.2.tgz", - "integrity": "sha1-Lhj/PS9JqydlzskCPwEdqo2DSaE=", - "requires": { - "is-extglob": "^1.0.0" - }, - "dependencies": { - "is-extglob": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/is-extglob/-/is-extglob-1.0.0.tgz", - "integrity": "sha1-rEaBd8SUNAWgkvyPKXYMb/xiBsA=" - } - } - }, - "extract-zip": { - "version": "1.7.0", - "resolved": "https://registry.npmjs.org/extract-zip/-/extract-zip-1.7.0.tgz", - "integrity": "sha512-xoh5G1W/PB0/27lXgMQyIhP5DSY/LhoCsOyZgb+6iMmRtCwVBo55uKaMoEYrDCKQhWvqEip5ZPKAc6eFNyf/MA==", - "requires": { - "concat-stream": "^1.6.2", - "debug": "^2.6.9", - "mkdirp": "^0.5.4", - "yauzl": "^2.10.0" - }, - "dependencies": { - "concat-stream": { - "version": "1.6.2", - "resolved": "https://registry.npmjs.org/concat-stream/-/concat-stream-1.6.2.tgz", - "integrity": "sha512-27HBghJxjiZtIk3Ycvn/4kbJk/1uZuJFfuPEns6LaEvpvG1f0hTea8lilrouyo9mVc2GWdcEZ8OLoGmSADlrCw==", - "requires": { - "buffer-from": "^1.0.0", - "inherits": "^2.0.3", - "readable-stream": "^2.2.2", - "typedarray": "^0.0.6" - } - }, - "debug": { - "version": "2.6.9", - "resolved": "https://registry.npmjs.org/debug/-/debug-2.6.9.tgz", - "integrity": "sha512-bC7ElrdJaJnPbAP+1EotYvqZsb3ecl5wi6Bfi6BJTUcNowp6cvspg0jXznRTKDjm/E7AdgFBVeAPVMNcKGsHMA==", - "requires": { - "ms": "2.0.0" - } - }, - "mkdirp": { - "version": "0.5.5", - "resolved": "https://registry.npmjs.org/mkdirp/-/mkdirp-0.5.5.tgz", - "integrity": "sha512-NKmAlESf6jMGym1++R0Ra7wvhV+wFW63FaSOFPwRahvea0gMUcGUhVeAg/0BC0wiv9ih5NYPB1Wn1UEI1/L+xQ==", - "requires": { - "minimist": "^1.2.5" - } - }, - "ms": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/ms/-/ms-2.0.0.tgz", - "integrity": "sha1-VgiurfwAvmwpAd9fmGF4jeDVl8g=" - }, - "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==", - "requires": { - "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" - } - }, - "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==", - "requires": { - "safe-buffer": "~5.1.0" - } - } - } - }, - "extsprintf": { - "version": "1.3.0", - "resolved": "https://registry.npmjs.org/extsprintf/-/extsprintf-1.3.0.tgz", - "integrity": "sha1-lpGEQOMEGnpBT4xS48V06zw+HgU=", - "dev": true - }, - "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==" - }, - "fast-glob": { - "version": "3.2.7", - "resolved": "https://registry.npmjs.org/fast-glob/-/fast-glob-3.2.7.tgz", - "integrity": "sha512-rYGMRwip6lUMvYD3BTScMwT1HtAs2d71SMv66Vrxs0IekGZEjhM0pcMfjQPnknBt2zeCwQMEupiN02ZP4DiT1Q==", - "dev": true, - "requires": { - "@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" - }, - "dependencies": { - "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, - "requires": { - "is-glob": "^4.0.1" - } - } - } - }, - "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==" - }, - "fast-levenshtein": { - "version": "2.0.6", - "resolved": "https://registry.npmjs.org/fast-levenshtein/-/fast-levenshtein-2.0.6.tgz", - "integrity": "sha1-PYpcZog6FqMMqGQ+hR8Zuqd5eRc=" - }, - "fast-memoize": { - "version": "2.5.2", - "resolved": "https://registry.npmjs.org/fast-memoize/-/fast-memoize-2.5.2.tgz", - "integrity": "sha512-Ue0LwpDYErFbmNnZSF0UH6eImUwDmogUO1jyE+JbN2gsQz/jICm1Ve7t9QT0rNSsfJt+Hs4/S3GnsDVjL4HVrw==", - "dev": true - }, - "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==" - }, - "fastest-levenshtein": { - "version": "1.0.12", - "resolved": "https://registry.npmjs.org/fastest-levenshtein/-/fastest-levenshtein-1.0.12.tgz", - "integrity": "sha512-On2N+BpYJ15xIC974QNVuYGMOlEVt4s0EOI3wwMqOmK1fdDY+FN/zltPV8vosq4ad4c/gJ1KHScUn/6AWIgiow==" - }, - "fastq": { - "version": "1.13.0", - "resolved": "https://registry.npmjs.org/fastq/-/fastq-1.13.0.tgz", - "integrity": "sha512-YpkpUnK8od0o1hmeSc7UUs/eB/vIPWJYjKck2QKIzAf71Vm1AAQ3EbuZB3g2JIy+pg+ERD0vqI79KyZiB2e2Nw==", - "dev": true, - "requires": { - "reusify": "^1.0.4" - } - }, - "fd-slicer": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/fd-slicer/-/fd-slicer-1.1.0.tgz", - "integrity": "sha1-JcfInLH5B3+IkbvmHY85Dq4lbx4=", - "requires": { - "pend": "~1.2.0" - } - }, - "figgy-pudding": { - "version": "3.5.2", - "resolved": "https://registry.npmjs.org/figgy-pudding/-/figgy-pudding-3.5.2.tgz", - "integrity": "sha512-0btnI/H8f2pavGMN8w40mlSKOfTK2SVJmBfBeVIj3kNw0swwgzyRq0d5TJVOwodFmtvpPeWPN/MCcfuWF0Ezbw==", - "dev": true - }, - "figures": { - "version": "3.2.0", - "resolved": "https://registry.npmjs.org/figures/-/figures-3.2.0.tgz", - "integrity": "sha512-yaduQFRKLXYOGgEn6AZau90j3ggSOyiqXU0F9JZfeXYhNa+Jk4X+s45A2zg5jns87GAFa34BBm2kXw4XpNcbdg==", - "dev": true, - "requires": { - "escape-string-regexp": "^1.0.5" - }, - "dependencies": { - "escape-string-regexp": { - "version": "1.0.5", - "resolved": "https://registry.npmjs.org/escape-string-regexp/-/escape-string-regexp-1.0.5.tgz", - "integrity": "sha1-G2HAViGQqN/2rjuyzwIAyhMLhtQ=", - "dev": true - } - } - }, - "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, - "requires": { - "flat-cache": "^3.0.4" - } - }, - "filename-regex": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/filename-regex/-/filename-regex-2.0.1.tgz", - "integrity": "sha1-wcS5vuPglyXdsQa3XB4wH+LxiyY=" - }, - "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==", - "requires": { - "to-regex-range": "^5.0.1" - } - }, - "filter-obj": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/filter-obj/-/filter-obj-1.1.0.tgz", - "integrity": "sha1-mzERErxsYSehbgFsbF1/GeCAXFs=", - "dev": true - }, - "finalhandler": { - "version": "1.1.2", - "resolved": "https://registry.npmjs.org/finalhandler/-/finalhandler-1.1.2.tgz", - "integrity": "sha512-aAWcW57uxVNrQZqFXjITpW3sIUQmHGG3qSb9mUah9MgMC4NeWhNOlNjXEYq3HjRAvL6arUviZGGJsBg6z0zsWA==", - "requires": { - "debug": "2.6.9", - "encodeurl": "~1.0.2", - "escape-html": "~1.0.3", - "on-finished": "~2.3.0", - "parseurl": "~1.3.3", - "statuses": "~1.5.0", - "unpipe": "~1.0.0" - }, - "dependencies": { - "debug": { - "version": "2.6.9", - "resolved": "https://registry.npmjs.org/debug/-/debug-2.6.9.tgz", - "integrity": "sha512-bC7ElrdJaJnPbAP+1EotYvqZsb3ecl5wi6Bfi6BJTUcNowp6cvspg0jXznRTKDjm/E7AdgFBVeAPVMNcKGsHMA==", - "requires": { - "ms": "2.0.0" - } - }, - "ms": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/ms/-/ms-2.0.0.tgz", - "integrity": "sha1-VgiurfwAvmwpAd9fmGF4jeDVl8g=" - } - } - }, - "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==", - "requires": { - "commondir": "^1.0.1", - "make-dir": "^3.0.2", - "pkg-dir": "^4.1.0" - } - }, - "find-up": { - "version": "2.1.0", - "resolved": "https://registry.npmjs.org/find-up/-/find-up-2.1.0.tgz", - "integrity": "sha1-RdG35QbHF93UgndaK3eSCjwMV6c=", - "requires": { - "locate-path": "^2.0.0" - } - }, - "flat": { - "version": "5.0.2", - "resolved": "https://registry.npmjs.org/flat/-/flat-5.0.2.tgz", - "integrity": "sha512-b6suED+5/3rTpUBdG1gupIl8MPFCAMA0QXwmljLhvCUKcUvdE4gWky9zpuGCcXHOsz4J9wPGNWq6OKpmIzz3hQ==" - }, - "flat-cache": { - "version": "3.0.4", - "resolved": "https://registry.npmjs.org/flat-cache/-/flat-cache-3.0.4.tgz", - "integrity": "sha512-dm9s5Pw7Jc0GvMYbshN6zchCA9RgQlzzEZX3vylR9IqFfS8XciblUXOKfW6SiuJ0e13eDYZoZV5wdrev7P3Nwg==", - "dev": true, - "requires": { - "flatted": "^3.1.0", - "rimraf": "^3.0.2" - } - }, - "flatted": { - "version": "3.2.4", - "resolved": "https://registry.npmjs.org/flatted/-/flatted-3.2.4.tgz", - "integrity": "sha512-8/sOawo8tJ4QOBX8YlQBMxL8+RLZfxMQOif9o0KUKTNTjMYElWPE0r/m5VNFxTRd0NSw8qSy8dajrwX4RYI1Hw==", - "dev": true - }, - "follow-redirects": { - "version": "1.14.6", - "resolved": "https://registry.npmjs.org/follow-redirects/-/follow-redirects-1.14.6.tgz", - "integrity": "sha512-fhUl5EwSJbbl8AR+uYL2KQDxLkdSjZGR36xy46AO7cOMTrCMON6Sa28FmAnC2tRTDbd/Uuzz3aJBv7EBN7JH8A==" - }, - "for-in": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/for-in/-/for-in-1.0.2.tgz", - "integrity": "sha1-gQaNKVqBQuwKxybG4iAMMPttXoA=" - }, - "for-own": { - "version": "0.1.5", - "resolved": "https://registry.npmjs.org/for-own/-/for-own-0.1.5.tgz", - "integrity": "sha1-UmXGgaTylNq78XyVCbZ2OqhFEM4=", - "requires": { - "for-in": "^1.0.1" - } - }, - "foreground-child": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/foreground-child/-/foreground-child-2.0.0.tgz", - "integrity": "sha512-dCIq9FpEcyQyXKCkyzmlPTFNgrCzPudOe+mhvJU5zAtlBnGVy2yKxtfsxK2tQBThwq225jcvBjpw1Gr40uzZCA==", - "dev": true, - "requires": { - "cross-spawn": "^7.0.0", - "signal-exit": "^3.0.2" - } - }, - "forever-agent": { - "version": "0.6.1", - "resolved": "https://registry.npmjs.org/forever-agent/-/forever-agent-0.6.1.tgz", - "integrity": "sha1-+8cfDEGt6zf5bFd60e1C2P2sypE=", - "dev": true - }, - "form-data": { - "version": "2.3.3", - "resolved": "https://registry.npmjs.org/form-data/-/form-data-2.3.3.tgz", - "integrity": "sha512-1lLKB2Mu3aGP1Q/2eCOx0fNbRMe7XdwktwOruhfqqd0rIJWwN4Dh+E3hrPSlDCXnSR7UtZ1N38rVXm+6+MEhJQ==", - "requires": { - "asynckit": "^0.4.0", - "combined-stream": "^1.0.6", - "mime-types": "^2.1.12" - } - }, - "formidable": { - "version": "1.2.6", - "resolved": "https://registry.npmjs.org/formidable/-/formidable-1.2.6.tgz", - "integrity": "sha512-KcpbcpuLNOwrEjnbpMC0gS+X8ciDoZE1kkqzat4a8vrprf+s9pKNQ/QIwWfbfs4ltgmFl3MD177SNTkve3BwGQ==" - }, - "forwarded": { - "version": "0.2.0", - "resolved": "https://registry.npmjs.org/forwarded/-/forwarded-0.2.0.tgz", - "integrity": "sha512-buRG0fpBtRHSTCOASe6hD258tEubFoRLb4ZNA6NxMVHNw2gOcwHo9wyablzMzOA5z9xA9L1KNjk/Nt6MT9aYow==" - }, - "fp-and-or": { - "version": "0.1.3", - "resolved": "https://registry.npmjs.org/fp-and-or/-/fp-and-or-0.1.3.tgz", - "integrity": "sha512-wJaE62fLaB3jCYvY2ZHjZvmKK2iiLiiehX38rz5QZxtdN8fVPJDeZUiVvJrHStdTc+23LHlyZuSEKgFc0pxi2g==", - "dev": true - }, - "fresh": { - "version": "0.5.2", - "resolved": "https://registry.npmjs.org/fresh/-/fresh-0.5.2.tgz", - "integrity": "sha1-PYyt2Q2XZWn6g1qx+OSyOhBWBac=" - }, - "fromentries": { - "version": "1.3.2", - "resolved": "https://registry.npmjs.org/fromentries/-/fromentries-1.3.2.tgz", - "integrity": "sha512-cHEpEQHUg0f8XdtZCc2ZAhrHzKzT0MrFUTcvx+hfxYu7rGMDc5SKoXFh+n4YigxsHXRzc6OrCshdR1bWH6HHyg==", - "dev": true - }, - "fs-extra": { - "version": "9.1.0", - "resolved": "https://registry.npmjs.org/fs-extra/-/fs-extra-9.1.0.tgz", - "integrity": "sha512-hcg3ZmepS30/7BSFqRvoo3DOMQu7IjqxO5nCDt+zM9XWjb33Wg7ziNT+Qvqbuc3+gWpzO02JubVyk2G4Zvo1OQ==", - "dev": true, - "requires": { - "at-least-node": "^1.0.0", - "graceful-fs": "^4.2.0", - "jsonfile": "^6.0.1", - "universalify": "^2.0.0" - } - }, - "fs-minipass": { - "version": "2.1.0", - "resolved": "https://registry.npmjs.org/fs-minipass/-/fs-minipass-2.1.0.tgz", - "integrity": "sha512-V/JgOLFCS+R6Vcq0slCuaeWEdNC3ouDlJMNIsacH2VtALiu9mV4LPrHc5cDl8k5aw6J8jwgWWpiTo5RYhmIzvg==", - "dev": true, - "requires": { - "minipass": "^3.0.0" - } - }, - "fs-walk": { - "version": "0.0.1", - "resolved": "https://registry.npmjs.org/fs-walk/-/fs-walk-0.0.1.tgz", - "integrity": "sha1-9/yRw64e6tB8mYvF0N1B8tvr0zU=", - "requires": { - "async": "*" - } - }, - "fs.realpath": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/fs.realpath/-/fs.realpath-1.0.0.tgz", - "integrity": "sha1-FQStJSMVjKpA20onh8sBQRmU6k8=" - }, - "fsevents": { - "version": "2.3.2", - "resolved": "https://registry.npmjs.org/fsevents/-/fsevents-2.3.2.tgz", - "integrity": "sha512-xiqMQR4xAeHTuB9uWm+fFRcIOgKBMiOBP+eXiyT7jsgVCq1bkVygt00oASowB7EdtpOHaaPgKt812P9ab+DDKA==", - "optional": true - }, - "function-bind": { - "version": "1.1.1", - "resolved": "https://registry.npmjs.org/function-bind/-/function-bind-1.1.1.tgz", - "integrity": "sha512-yIovAzMX49sF8Yl58fSCWJ5svSLuaibPxXQJFLmBObTuCr0Mf1KiPopGM9NiFjiYBCbfaa2Fh6breQ6ANVTI0A==" - }, - "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": "sha1-GwqzvVU7Kg1jmdKcDj6gslIHgyc=", - "dev": true - }, - "gauge": { - "version": "2.7.4", - "resolved": "https://registry.npmjs.org/gauge/-/gauge-2.7.4.tgz", - "integrity": "sha1-LANAXHU4w51+s3sxcCLjJfsBi/c=", - "dev": true, - "requires": { - "aproba": "^1.0.3", - "console-control-strings": "^1.0.0", - "has-unicode": "^2.0.0", - "object-assign": "^4.1.0", - "signal-exit": "^3.0.0", - "string-width": "^1.0.1", - "strip-ansi": "^3.0.1", - "wide-align": "^1.1.0" - }, - "dependencies": { - "ansi-regex": { - "version": "2.1.1", - "resolved": "https://registry.npmjs.org/ansi-regex/-/ansi-regex-2.1.1.tgz", - "integrity": "sha1-w7M6te42DYbg5ijwRorn7yfWVN8=", - "dev": true - }, - "aproba": { - "version": "1.2.0", - "resolved": "https://registry.npmjs.org/aproba/-/aproba-1.2.0.tgz", - "integrity": "sha512-Y9J6ZjXtoYh8RnXVCMOU/ttDmk1aBjunq9vO0ta5x85WDQiQfUF9sIPBITdbiiIVcBo03Hi3jMxigBtsddlXRw==", - "dev": true - }, - "is-fullwidth-code-point": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/is-fullwidth-code-point/-/is-fullwidth-code-point-1.0.0.tgz", - "integrity": "sha1-754xOG8DGn8NZDr4L95QxFfvAMs=", - "dev": true, - "requires": { - "number-is-nan": "^1.0.0" - } - }, - "string-width": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/string-width/-/string-width-1.0.2.tgz", - "integrity": "sha1-EYvfW4zcUaKn5w0hHgfisLmxB9M=", - "dev": true, - "requires": { - "code-point-at": "^1.0.0", - "is-fullwidth-code-point": "^1.0.0", - "strip-ansi": "^3.0.0" - } - }, - "strip-ansi": { - "version": "3.0.1", - "resolved": "https://registry.npmjs.org/strip-ansi/-/strip-ansi-3.0.1.tgz", - "integrity": "sha1-ajhfuIU9lS1f8F0Oiq+UJ43GPc8=", - "dev": true, - "requires": { - "ansi-regex": "^2.0.0" - } - } - } - }, - "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==" - }, - "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==" - }, - "get-intrinsic": { - "version": "1.1.1", - "resolved": "https://registry.npmjs.org/get-intrinsic/-/get-intrinsic-1.1.1.tgz", - "integrity": "sha512-kWZrnVM42QCiEA2Ig1bG8zjoIMOgxWwYCEeNdwY6Tv/cOSeGpcoX4pXHfKUxNKVoArnrEr2e9srnAxxGIraS9Q==", - "requires": { - "function-bind": "^1.1.1", - "has": "^1.0.3", - "has-symbols": "^1.0.1" - } - }, - "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 - }, - "get-pkg-repo": { - "version": "4.2.1", - "resolved": "https://registry.npmjs.org/get-pkg-repo/-/get-pkg-repo-4.2.1.tgz", - "integrity": "sha512-2+QbHjFRfGB74v/pYWjd5OhU3TDIC2Gv/YKUTk/tCvAz0pkn/Mz6P3uByuBimLOcPvN2jYdScl3xGFSrx0jEcA==", - "dev": true, - "requires": { - "@hutson/parse-repository-url": "^3.0.0", - "hosted-git-info": "^4.0.0", - "through2": "^2.0.0", - "yargs": "^16.2.0" - }, - "dependencies": { - "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, - "requires": { - "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" - } - }, - "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, - "requires": { - "safe-buffer": "~5.1.0" - } - }, - "through2": { - "version": "2.0.5", - "resolved": "https://registry.npmjs.org/through2/-/through2-2.0.5.tgz", - "integrity": "sha512-/mrRod8xqpA+IHSLyGCQ2s8SPHiCDEeQJSep1jqLYeEUClOFG2Qsh+4FU6G9VeqpZnGW/Su8LQGc4YKni5rYSQ==", - "dev": true, - "requires": { - "readable-stream": "~2.3.6", - "xtend": "~4.0.1" - } - } - } - }, - "get-port": { - "version": "5.1.1", - "resolved": "https://registry.npmjs.org/get-port/-/get-port-5.1.1.tgz", - "integrity": "sha512-g/Q1aTSDOxFpchXC4i8ZWvxA1lnPqx/JHqcpIw0/LX9T8x/GBbi6YnlN5nhaKIFkT8oFsscUKgDJYxfwfS6QsQ==", - "dev": true - }, - "get-stdin": { - "version": "8.0.0", - "resolved": "https://registry.npmjs.org/get-stdin/-/get-stdin-8.0.0.tgz", - "integrity": "sha512-sY22aA6xchAzprjyqmSEQv4UbAAzRN0L2dQB0NlN5acTTK9Don6nhoc3eAbUnpZiCANAMfd/+40kVdKfFygohg==", - "dev": true - }, - "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==" - }, - "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, - "requires": { - "call-bind": "^1.0.2", - "get-intrinsic": "^1.1.1" - } - }, - "getpass": { - "version": "0.1.7", - "resolved": "https://registry.npmjs.org/getpass/-/getpass-0.1.7.tgz", - "integrity": "sha1-Xv+OPmhNVprkyysSgmBOi6YhSfo=", - "dev": true, - "requires": { - "assert-plus": "^1.0.0" - } - }, - "git-raw-commits": { - "version": "2.0.11", - "resolved": "https://registry.npmjs.org/git-raw-commits/-/git-raw-commits-2.0.11.tgz", - "integrity": "sha512-VnctFhw+xfj8Va1xtfEqCUD2XDrbAPSJx+hSrE5K7fGdjZruW7XV+QOrN7LF/RJyvspRiD2I0asWsxFp0ya26A==", - "dev": true, - "requires": { - "dargs": "^7.0.0", - "lodash": "^4.17.15", - "meow": "^8.0.0", - "split2": "^3.0.0", - "through2": "^4.0.0" - } - }, - "git-remote-origin-url": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/git-remote-origin-url/-/git-remote-origin-url-2.0.0.tgz", - "integrity": "sha1-UoJlna4hBxRaERJhEq0yFuxfpl8=", - "dev": true, - "requires": { - "gitconfiglocal": "^1.0.0", - "pify": "^2.3.0" - }, - "dependencies": { - "pify": { - "version": "2.3.0", - "resolved": "https://registry.npmjs.org/pify/-/pify-2.3.0.tgz", - "integrity": "sha1-7RQaasBDqEnqWISY59yosVMw6Qw=", - "dev": true - } - } - }, - "git-semver-tags": { - "version": "4.1.1", - "resolved": "https://registry.npmjs.org/git-semver-tags/-/git-semver-tags-4.1.1.tgz", - "integrity": "sha512-OWyMt5zBe7xFs8vglMmhM9lRQzCWL3WjHtxNNfJTMngGym7pC1kh8sP6jevfydJ6LP3ZvGxfb6ABYgPUM0mtsA==", - "dev": true, - "requires": { - "meow": "^8.0.0", - "semver": "^6.0.0" - }, - "dependencies": { - "semver": { - "version": "6.3.0", - "resolved": "https://registry.npmjs.org/semver/-/semver-6.3.0.tgz", - "integrity": "sha512-b39TBaTSfV6yBrapU89p5fKekE2m/NwnDocOVruQFS1/veMgdzuPcnOM34M6CwxW8jH/lxEa5rBoDeUwu5HHTw==", - "dev": true - } - } - }, - "git-up": { - "version": "4.0.5", - "resolved": "https://registry.npmjs.org/git-up/-/git-up-4.0.5.tgz", - "integrity": "sha512-YUvVDg/vX3d0syBsk/CKUTib0srcQME0JyHkL5BaYdwLsiCslPWmDSi8PUMo9pXYjrryMcmsCoCgsTpSCJEQaA==", - "dev": true, - "requires": { - "is-ssh": "^1.3.0", - "parse-url": "^6.0.0" - } - }, - "git-url-parse": { - "version": "11.6.0", - "resolved": "https://registry.npmjs.org/git-url-parse/-/git-url-parse-11.6.0.tgz", - "integrity": "sha512-WWUxvJs5HsyHL6L08wOusa/IXYtMuCAhrMmnTjQPpBU0TTHyDhnOATNH3xNQz7YOQUsqIIPTGr4xiVti1Hsk5g==", - "dev": true, - "requires": { - "git-up": "^4.0.0" - } - }, - "gitconfiglocal": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/gitconfiglocal/-/gitconfiglocal-1.0.0.tgz", - "integrity": "sha1-QdBF84UaXqiPA/JMocYXgRRGS5s=", - "dev": true, - "requires": { - "ini": "^1.3.2" - } - }, - "glob": { - "version": "7.2.0", - "resolved": "https://registry.npmjs.org/glob/-/glob-7.2.0.tgz", - "integrity": "sha512-lmLf6gtyrPq8tTjSmrO94wBeQbFR3HbLHbuyD69wuyQkImp2hWqMGB47OX65FBkPffO641IP9jWa1z4ivqG26Q==", - "requires": { - "fs.realpath": "^1.0.0", - "inflight": "^1.0.4", - "inherits": "2", - "minimatch": "^3.0.4", - "once": "^1.3.0", - "path-is-absolute": "^1.0.0" - } - }, - "glob-base": { - "version": "0.3.0", - "resolved": "https://registry.npmjs.org/glob-base/-/glob-base-0.3.0.tgz", - "integrity": "sha1-27Fk9iIbHAscz4Kuoyi0l98Oo8Q=", - "requires": { - "glob-parent": "^2.0.0", - "is-glob": "^2.0.0" - }, - "dependencies": { - "glob-parent": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/glob-parent/-/glob-parent-2.0.0.tgz", - "integrity": "sha1-gTg9ctsFT8zPUzbaqQLxgvbtuyg=", - "requires": { - "is-glob": "^2.0.0" - } - }, - "is-extglob": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/is-extglob/-/is-extglob-1.0.0.tgz", - "integrity": "sha1-rEaBd8SUNAWgkvyPKXYMb/xiBsA=" - }, - "is-glob": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/is-glob/-/is-glob-2.0.1.tgz", - "integrity": "sha1-0Jb5JqPe1WAPP9/ZEZjLCIjC2GM=", - "requires": { - "is-extglob": "^1.0.0" - } - } - } - }, - "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, - "requires": { - "is-glob": "^4.0.3" - } - }, - "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==" - }, - "global-dirs": { - "version": "3.0.0", - "resolved": "https://registry.npmjs.org/global-dirs/-/global-dirs-3.0.0.tgz", - "integrity": "sha512-v8ho2DS5RiCjftj1nD9NmnfaOzTdud7RRnVd9kFNOjqZbISlx5DQ+OrTkywgd0dIt7oFCvKetZSHoHcP3sDdiA==", - "dev": true, - "requires": { - "ini": "2.0.0" - }, - "dependencies": { - "ini": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/ini/-/ini-2.0.0.tgz", - "integrity": "sha512-7PnF4oN3CvZF23ADhA5wRaYEQpJ8qygSkbtTXWBeXWXmEVRXK+1ITciHWwHhsjv1TmW0MgacIv6hEi5pX5NQdA==", - "dev": true - } - } - }, - "globals": { - "version": "13.12.0", - "resolved": "https://registry.npmjs.org/globals/-/globals-13.12.0.tgz", - "integrity": "sha512-uS8X6lSKN2JumVoXrbUz+uG4BYG+eiawqm3qFcT7ammfbUHeCBoJMlHcec/S3krSk73/AE/f0szYFmgAA3kYZg==", - "dev": true, - "requires": { - "type-fest": "^0.20.2" - } - }, - "globby": { - "version": "11.0.4", - "resolved": "https://registry.npmjs.org/globby/-/globby-11.0.4.tgz", - "integrity": "sha512-9O4MVG9ioZJ08ffbcyVYyLOJLk5JQ688pJ4eMGLpdWLHq/Wr1D9BlriLQyL0E+jbkuePVZXYFj47QM/v093wHg==", - "dev": true, - "requires": { - "array-union": "^2.1.0", - "dir-glob": "^3.0.1", - "fast-glob": "^3.1.1", - "ignore": "^5.1.4", - "merge2": "^1.3.0", - "slash": "^3.0.0" - } - }, - "got": { - "version": "9.6.0", - "resolved": "https://registry.npmjs.org/got/-/got-9.6.0.tgz", - "integrity": "sha512-R7eWptXuGYxwijs0eV+v3o6+XH1IqVK8dJOEecQfTmkncw9AV4dcw/Dhxi8MdlqPthxxpZyizMzyg8RTmEsG+Q==", - "dev": true, - "requires": { - "@sindresorhus/is": "^0.14.0", - "@szmarczak/http-timer": "^1.1.2", - "cacheable-request": "^6.0.0", - "decompress-response": "^3.3.0", - "duplexer3": "^0.1.4", - "get-stream": "^4.1.0", - "lowercase-keys": "^1.0.1", - "mimic-response": "^1.0.1", - "p-cancelable": "^1.0.0", - "to-readable-stream": "^1.0.0", - "url-parse-lax": "^3.0.0" - }, - "dependencies": { - "get-stream": { - "version": "4.1.0", - "resolved": "https://registry.npmjs.org/get-stream/-/get-stream-4.1.0.tgz", - "integrity": "sha512-GMat4EJ5161kIy2HevLlr4luNjBgvmj413KaQA7jt4V8B4RDsfpHk7WQ9GVqfYyyx8OS/L66Kox+rJRNklLK7w==", - "dev": true, - "requires": { - "pump": "^3.0.0" - } - } - } - }, - "graceful-fs": { - "version": "4.2.8", - "resolved": "https://registry.npmjs.org/graceful-fs/-/graceful-fs-4.2.8.tgz", - "integrity": "sha512-qkIilPUYcNhJpd33n0GBXTB1MMPp14TxEsEs0pTrsSVucApsYzW5V+Q8Qxhik6KU3evy+qkAAowTByymK0avdg==" - }, - "graceful-readlink": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/graceful-readlink/-/graceful-readlink-1.0.1.tgz", - "integrity": "sha1-TK+tdrxi8C+gObL5Tpo906ORpyU=" - }, - "grant": { - "version": "5.4.19", - "resolved": "https://registry.npmjs.org/grant/-/grant-5.4.19.tgz", - "integrity": "sha512-VCYpHZP2ss7OYdKFIsSK2/WD7Vrf5klzj+CA/6p8PC1mPHqTLEDhMFejnmjICBZytl858eNUWFs8yCUZ28eevg==", - "requires": { - "cookie": "^0.4.1", - "cookie-signature": "^1.1.0", - "jwk-to-pem": "^2.0.5", - "jws": "^4.0.0", - "qs": "^6.10.2", - "request-compose": "^2.1.4", - "request-oauth": "^1.0.1" - }, - "dependencies": { - "cookie-signature": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/cookie-signature/-/cookie-signature-1.1.0.tgz", - "integrity": "sha512-Alvs19Vgq07eunykd3Xy2jF0/qSNv2u7KDbAek9H5liV1UMijbqFs5cycZvv5dVsvseT/U4H8/7/w8Koh35C4A==", - "optional": true - } - } - }, - "growl": { - "version": "1.10.5", - "resolved": "https://registry.npmjs.org/growl/-/growl-1.10.5.tgz", - "integrity": "sha512-qBr4OuELkhPenW6goKVXiv47US3clb3/IbuWF9KNKEijAy9oeHxU9IgzjvJhHkUzhaj7rOUD7+YGWqUjLp5oSA==" - }, - "handlebars": { - "version": "4.7.7", - "resolved": "https://registry.npmjs.org/handlebars/-/handlebars-4.7.7.tgz", - "integrity": "sha512-aAcXm5OAfE/8IXkcZvCepKU3VzW1/39Fb5ZuqMtgI/hT8X2YgoMvBY5dLhq/cpOvw7Lk1nK/UF71aLG/ZnVYRA==", - "dev": true, - "requires": { - "minimist": "^1.2.5", - "neo-async": "^2.6.0", - "source-map": "^0.6.1", - "uglify-js": "^3.1.4", - "wordwrap": "^1.0.0" - } - }, - "har-schema": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/har-schema/-/har-schema-2.0.0.tgz", - "integrity": "sha1-qUwiJOvKwEeCoNkDVSHyRzW37JI=", - "dev": true - }, - "har-validator": { - "version": "5.1.5", - "resolved": "https://registry.npmjs.org/har-validator/-/har-validator-5.1.5.tgz", - "integrity": "sha512-nmT2T0lljbxdQZfspsno9hgrG3Uir6Ks5afism62poxqBM6sDnMEuPmzTq8XN0OEwqKLLdh1jQI3qyE66Nzb3w==", - "dev": true, - "requires": { - "ajv": "^6.12.3", - "har-schema": "^2.0.0" - }, - "dependencies": { - "ajv": { - "version": "6.12.6", - "resolved": "https://registry.npmjs.org/ajv/-/ajv-6.12.6.tgz", - "integrity": "sha512-j3fVLgvTo527anyYyJOGTYJbG+vnnQYvE0m5mmkc1TK+nxAppkCLMIL0aZ4dblVCNoGShhm+kzE4ZUykBoMg4g==", - "dev": true, - "requires": { - "fast-deep-equal": "^3.1.1", - "fast-json-stable-stringify": "^2.0.0", - "json-schema-traverse": "^0.4.1", - "uri-js": "^4.2.2" - } - }, - "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 - } - } - }, - "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 - }, - "has": { - "version": "1.0.3", - "resolved": "https://registry.npmjs.org/has/-/has-1.0.3.tgz", - "integrity": "sha512-f2dvO0VU6Oej7RkWJGrehjbzMAjFp5/VKPp5tTpWIV4JHHZK1/BxbFRtf/siA2SWTe09caDmVtYYzWEIbBS4zw==", - "requires": { - "function-bind": "^1.1.1" - } - }, - "has-ansi": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/has-ansi/-/has-ansi-2.0.0.tgz", - "integrity": "sha1-NPUEnOHs3ysGSa8+8k5F7TVBbZE=", - "requires": { - "ansi-regex": "^2.0.0" - }, - "dependencies": { - "ansi-regex": { - "version": "2.1.1", - "resolved": "https://registry.npmjs.org/ansi-regex/-/ansi-regex-2.1.1.tgz", - "integrity": "sha1-w7M6te42DYbg5ijwRorn7yfWVN8=" - } - } - }, - "has-bigints": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/has-bigints/-/has-bigints-1.0.1.tgz", - "integrity": "sha512-LSBS2LjbNBTf6287JEbEzvJgftkF5qFkmCo9hDRpAzKhUOlJ+hx8dd4USs00SgsUNwc4617J9ki5YtEClM2ffA==", - "dev": true - }, - "has-cors": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/has-cors/-/has-cors-1.1.0.tgz", - "integrity": "sha1-XkdHk/fqmEPRu5nCPu9J/xJv/zk=" - }, - "has-flag": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/has-flag/-/has-flag-4.0.0.tgz", - "integrity": "sha512-EykJT/Q1KjTWctppgIAgfSO0tKVuZUjhgMr17kqTumMl6Afv3EISleU7qZUzoXDFTAHTDC4NOoG/ZxU3EvlMPQ==" - }, - "has-symbols": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/has-symbols/-/has-symbols-1.0.2.tgz", - "integrity": "sha512-chXa79rL/UC2KlX17jo3vRGz0azaWEx5tGqZg5pO3NUyEJVB17dMruQlzCCOfUvElghKcm5194+BCRvi2Rv/Gw==" - }, - "has-tostringtag": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/has-tostringtag/-/has-tostringtag-1.0.0.tgz", - "integrity": "sha512-kFjcSNhnlGV1kyoGk7OXKSawH5JOb/LzUc5w9B02hOTO0dfFRjbHQKvg1d6cf3HbeUmtU9VbbV3qzZ2Teh97WQ==", - "requires": { - "has-symbols": "^1.0.2" - } - }, - "has-unicode": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/has-unicode/-/has-unicode-2.0.1.tgz", - "integrity": "sha1-4Ob+aijPUROIVeCG0Wkedx3iqLk=", - "dev": true - }, - "has-yarn": { - "version": "2.1.0", - "resolved": "https://registry.npmjs.org/has-yarn/-/has-yarn-2.1.0.tgz", - "integrity": "sha512-UqBRqi4ju7T+TqGNdqAO0PaSVGsDGJUBQvk9eUWNGRY1CFGDzYhLWoM7JQEemnlvVcv/YEmc2wNW8BC24EnUsw==", - "dev": true - }, - "hash.js": { - "version": "1.1.7", - "resolved": "https://registry.npmjs.org/hash.js/-/hash.js-1.1.7.tgz", - "integrity": "sha512-taOaskGt4z4SOANNseOviYDvjEJinIkRgmp7LbKP2YTTmVxWBl87s/uzK9r+44BclBSp2X7K1hqeNfz9JbBeXA==", - "optional": true, - "requires": { - "inherits": "^2.0.3", - "minimalistic-assert": "^1.0.1" - } - }, - "hasha": { - "version": "5.2.2", - "resolved": "https://registry.npmjs.org/hasha/-/hasha-5.2.2.tgz", - "integrity": "sha512-Hrp5vIK/xr5SkeN2onO32H0MgNZ0f17HRNH39WfL0SYUNOTZ5Lz1TJ8Pajo/87dYGEFlLMm7mIc/k/s6Bvz9HQ==", - "dev": true, - "requires": { - "is-stream": "^2.0.0", - "type-fest": "^0.8.0" - }, - "dependencies": { - "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 - } - } - }, - "he": { - "version": "1.2.0", - "resolved": "https://registry.npmjs.org/he/-/he-1.2.0.tgz", - "integrity": "sha512-F/1DnUGPopORZi0ni+CvrCgHQ5FyEAHRLSApuYWMmrbSwoN2Mn/7k+Gl38gJnR7yyDZk6WLXwiGod1JOWNDKGw==" - }, - "hmac-drbg": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/hmac-drbg/-/hmac-drbg-1.0.1.tgz", - "integrity": "sha1-0nRXAQJabHdabFRXk+1QL8DGSaE=", - "optional": true, - "requires": { - "hash.js": "^1.0.3", - "minimalistic-assert": "^1.0.0", - "minimalistic-crypto-utils": "^1.0.1" - } - }, - "home-or-tmp": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/home-or-tmp/-/home-or-tmp-2.0.0.tgz", - "integrity": "sha1-42w/LSyufXRqhX440Y1fMqeILbg=", - "requires": { - "os-homedir": "^1.0.0", - "os-tmpdir": "^1.0.1" - } - }, - "hosted-git-info": { - "version": "4.0.2", - "resolved": "https://registry.npmjs.org/hosted-git-info/-/hosted-git-info-4.0.2.tgz", - "integrity": "sha512-c9OGXbZ3guC/xOlCg1Ci/VgWlwsqDv1yMQL1CWqXDL0hDjXuNcq0zuR4xqPSuasI3kqFDhqSyTjREz5gzq0fXg==", - "dev": true, - "requires": { - "lru-cache": "^6.0.0" - } - }, - "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 - }, - "htmljs-parser": { - "version": "2.11.1", - "resolved": "https://registry.npmjs.org/htmljs-parser/-/htmljs-parser-2.11.1.tgz", - "integrity": "sha512-9TM67eoRSSYFYi+R0yP8ysFOzhQiXClQ41r8V+HCWXuQHKG5qEtY/H8wAhOIsBEVroIeMHU/DatFKOkMXmDnwg==", - "requires": { - "char-props": "^0.1.5", - "complain": "^1.0.0" - } - }, - "http-assert": { - "version": "1.5.0", - "resolved": "https://registry.npmjs.org/http-assert/-/http-assert-1.5.0.tgz", - "integrity": "sha512-uPpH7OKX4H25hBmU6G1jWNaqJGpTXxey+YOUizJUAgu0AjLUeC8D73hTrhvDS5D+GJN1DN1+hhc/eF/wpxtp0w==", - "requires": { - "deep-equal": "~1.0.1", - "http-errors": "~1.8.0" - } - }, - "http-cache-semantics": { - "version": "4.1.0", - "resolved": "https://registry.npmjs.org/http-cache-semantics/-/http-cache-semantics-4.1.0.tgz", - "integrity": "sha512-carPklcUh7ROWRK7Cv27RPtdhYhUsela/ue5/jKzjegVvXDqM2ILE9Q2BGn9JZJh1g87cp56su/FgQSzcWS8cQ==", - "dev": true - }, - "http-errors": { - "version": "1.8.1", - "resolved": "https://registry.npmjs.org/http-errors/-/http-errors-1.8.1.tgz", - "integrity": "sha512-Kpk9Sm7NmI+RHhnj6OIWDI1d6fIoFAtFt9RLaTMRlg/8w49juAStsrBgp0Dp4OdxdVbRIeKhtCUvoi/RuAhO4g==", - "requires": { - "depd": "~1.1.2", - "inherits": "2.0.4", - "setprototypeof": "1.2.0", - "statuses": ">= 1.5.0 < 2", - "toidentifier": "1.0.1" - } - }, - "http-proxy-agent": { - "version": "4.0.1", - "resolved": "https://registry.npmjs.org/http-proxy-agent/-/http-proxy-agent-4.0.1.tgz", - "integrity": "sha512-k0zdNgqWTGA6aeIRVpvfVob4fL52dTfaehylg0Y4UvSySvOq/Y+BOyPrgpUrA7HylqvU8vIZGsRuXmspskV0Tg==", - "dev": true, - "requires": { - "@tootallnate/once": "1", - "agent-base": "6", - "debug": "4" - } - }, - "http-signature": { - "version": "1.2.0", - "resolved": "https://registry.npmjs.org/http-signature/-/http-signature-1.2.0.tgz", - "integrity": "sha1-muzZJRFHcvPZW2WmCruPfBj7rOE=", - "dev": true, - "requires": { - "assert-plus": "^1.0.0", - "jsprim": "^1.2.2", - "sshpk": "^1.7.0" - } - }, - "https-proxy-agent": { - "version": "5.0.0", - "resolved": "https://registry.npmjs.org/https-proxy-agent/-/https-proxy-agent-5.0.0.tgz", - "integrity": "sha512-EkYm5BcKUGiduxzSt3Eppko+PiNWNEpa4ySk9vTC6wDsQJW9rHSa+UhGNJoRYp7bz6Ht1eaRIa6QaJqO5rCFbA==", - "dev": true, - "requires": { - "agent-base": "6", - "debug": "4" - } - }, - "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==" - }, - "humanize-ms": { - "version": "1.2.1", - "resolved": "https://registry.npmjs.org/humanize-ms/-/humanize-ms-1.2.1.tgz", - "integrity": "sha1-xG4xWaKT9riW2ikxbYtv6Lt5u+0=", - "dev": true, - "requires": { - "ms": "^2.0.0" - } - }, - "iconv-lite": { - "version": "0.4.24", - "resolved": "https://registry.npmjs.org/iconv-lite/-/iconv-lite-0.4.24.tgz", - "integrity": "sha512-v3MXnZAcvnywkTUEZomIActle7RXXeedOR31wwl7VlyoXO4Qi9arvSenNQWne1TcRwhCL1HwLI21bEqdpj8/rA==", - "requires": { - "safer-buffer": ">= 2.1.2 < 3" - } - }, - "ieee754": { - "version": "1.2.1", - "resolved": "https://registry.npmjs.org/ieee754/-/ieee754-1.2.1.tgz", - "integrity": "sha512-dcyqhDvX1C46lXZcVqCpK+FtMRQVdIMN6/Df5js2zouUsqG7I6sFxitIC+7KYK29KdXOLHdu9zL4sFnoVQnqaA==" - }, - "ignore": { - "version": "5.2.0", - "resolved": "https://registry.npmjs.org/ignore/-/ignore-5.2.0.tgz", - "integrity": "sha512-CmxgYGiEPCLhfLnpPp1MoRmifwEIOgjcHXxOBjv7mY96c+eWScsOP9c112ZyLdWHi0FxHjI+4uVhKYp/gcdRmQ==" - }, - "ignore-walk": { - "version": "3.0.4", - "resolved": "https://registry.npmjs.org/ignore-walk/-/ignore-walk-3.0.4.tgz", - "integrity": "sha512-PY6Ii8o1jMRA1z4F2hRkH/xN59ox43DavKvD3oDpfurRlOJyAHpifIwpbdv1n4jt4ov0jSpw3kQ4GhJnpBL6WQ==", - "dev": true, - "requires": { - "minimatch": "^3.0.4" - } - }, - "image-size": { - "version": "0.3.5", - "resolved": "https://registry.npmjs.org/image-size/-/image-size-0.3.5.tgz", - "integrity": "sha1-gyQOqy+1sAsEqrjHSwRx6cunrYw=" - }, - "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, - "requires": { - "parent-module": "^1.0.0", - "resolve-from": "^4.0.0" - } - }, - "import-lazy": { - "version": "2.1.0", - "resolved": "https://registry.npmjs.org/import-lazy/-/import-lazy-2.1.0.tgz", - "integrity": "sha1-BWmOPUXIjo1+nZLLBYTnfwlvPkM=", - "dev": true - }, - "import-local": { - "version": "3.0.3", - "resolved": "https://registry.npmjs.org/import-local/-/import-local-3.0.3.tgz", - "integrity": "sha512-bE9iaUY3CXH8Cwfan/abDKAxe1KGT9kyGsBPqf6DMK/z0a2OzAsrukeYNgIH6cH5Xr452jb1TUL8rSfCLjZ9uA==", - "requires": { - "pkg-dir": "^4.2.0", - "resolve-cwd": "^3.0.0" - } - }, - "imurmurhash": { - "version": "0.1.4", - "resolved": "https://registry.npmjs.org/imurmurhash/-/imurmurhash-0.1.4.tgz", - "integrity": "sha1-khi5srkoojixPcT7a21XbyMUU+o=", - "dev": true - }, - "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 - }, - "infer-owner": { - "version": "1.0.4", - "resolved": "https://registry.npmjs.org/infer-owner/-/infer-owner-1.0.4.tgz", - "integrity": "sha512-IClj+Xz94+d7irH5qRyfJonOdfTzuDaifE6ZPWfx0N0+/ATZCbuTPq2prFl526urkQd90WyUKIh1DfBQ2hMz9A==", - "dev": true - }, - "inflation": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/inflation/-/inflation-2.0.0.tgz", - "integrity": "sha1-i0F+R8KPklpFEz2RTKH9OJEH8w8=" - }, - "inflight": { - "version": "1.0.6", - "resolved": "https://registry.npmjs.org/inflight/-/inflight-1.0.6.tgz", - "integrity": "sha1-Sb1jMdfQLQwJvJEKEHW6gWW1bfk=", - "requires": { - "once": "^1.3.0", - "wrappy": "1" - } - }, - "inherits": { - "version": "2.0.4", - "resolved": "https://registry.npmjs.org/inherits/-/inherits-2.0.4.tgz", - "integrity": "sha512-k/vGaX4/Yla3WzyMCvTQOXYeIHvqOKtnqBduzTHpzpQZzAskKMhZ2K+EnBiSM9zGSoIFeMpXKxa4dYeZIQqewQ==" - }, - "ini": { - "version": "1.3.8", - "resolved": "https://registry.npmjs.org/ini/-/ini-1.3.8.tgz", - "integrity": "sha512-JV/yugV2uzW5iMRSiZAyDtQd+nxtUnjeLt0acNdw98kKLrvuRVyB80tsREOE7yvGVgalhZ6RNXCmEHkUKBKxew==", - "dev": true - }, - "init-package-json": { - "version": "2.0.5", - "resolved": "https://registry.npmjs.org/init-package-json/-/init-package-json-2.0.5.tgz", - "integrity": "sha512-u1uGAtEFu3VA6HNl/yUWw57jmKEMx8SKOxHhxjGnOFUiIlFnohKDFg4ZrPpv9wWqk44nDxGJAtqjdQFm+9XXQA==", - "dev": true, - "requires": { - "npm-package-arg": "^8.1.5", - "promzard": "^0.3.0", - "read": "~1.0.1", - "read-package-json": "^4.1.1", - "semver": "^7.3.5", - "validate-npm-package-license": "^3.0.4", - "validate-npm-package-name": "^3.0.0" - }, - "dependencies": { - "read-package-json": { - "version": "4.1.1", - "resolved": "https://registry.npmjs.org/read-package-json/-/read-package-json-4.1.1.tgz", - "integrity": "sha512-P82sbZJ3ldDrWCOSKxJT0r/CXMWR0OR3KRh55SgKo3p91GSIEEC32v3lSHAvO/UcH3/IoL7uqhOFBduAnwdldw==", - "dev": true, - "requires": { - "glob": "^7.1.1", - "json-parse-even-better-errors": "^2.3.0", - "normalize-package-data": "^3.0.0", - "npm-normalize-package-bin": "^1.0.0" - } - } - } - }, - "inquirer": { - "version": "7.3.3", - "resolved": "https://registry.npmjs.org/inquirer/-/inquirer-7.3.3.tgz", - "integrity": "sha512-JG3eIAj5V9CwcGvuOmoo6LB9kbAYT8HXffUl6memuszlwDC/qvFAJw49XJ5NROSFNPxp3iQg1GqkFhaY/CR0IA==", - "dev": true, - "requires": { - "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" - }, - "dependencies": { - "rxjs": { - "version": "6.6.7", - "resolved": "https://registry.npmjs.org/rxjs/-/rxjs-6.6.7.tgz", - "integrity": "sha512-hTdwr+7yYNIT5n4AMYp85KA6yw2Va0FLa3Rguvbpa4W3I5xynaBZo41cM3XM+4Q6fRMj3sBYIR1VAmZMXYJvRQ==", - "dev": true, - "requires": { - "tslib": "^1.9.0" - } - } - } - }, - "internal-slot": { - "version": "1.0.3", - "resolved": "https://registry.npmjs.org/internal-slot/-/internal-slot-1.0.3.tgz", - "integrity": "sha512-O0DB1JC/sPyZl7cIo78n5dR7eUSwwpYPiXRhTzNxZVAMUuB8vlnRFyLxdrVToks6XPLVnFfbzaVd5WLjhgg+vA==", - "dev": true, - "requires": { - "get-intrinsic": "^1.1.0", - "has": "^1.0.3", - "side-channel": "^1.0.4" - } - }, - "interpret": { - "version": "1.4.0", - "resolved": "https://registry.npmjs.org/interpret/-/interpret-1.4.0.tgz", - "integrity": "sha512-agE4QfB2Lkp9uICn7BAqoscw4SZP9kTE2hxiFI3jBPmXJfdqiahTbUuKGsMoN2GtqL9AxhYioAcVvgsb1HvRbA==" - }, - "invariant": { - "version": "2.2.4", - "resolved": "https://registry.npmjs.org/invariant/-/invariant-2.2.4.tgz", - "integrity": "sha512-phJfQVBuaJM5raOpJjSfkiD6BpbCE4Ns//LaXl6wGYtUBY83nWS6Rf9tXm2e8VaK60JEjYldbPif/A2B1C2gNA==", - "requires": { - "loose-envify": "^1.0.0" - } - }, - "ip": { - "version": "1.1.5", - "resolved": "https://registry.npmjs.org/ip/-/ip-1.1.5.tgz", - "integrity": "sha1-vd7XARQpCCjAoDnnLvJfWq7ENUo=", - "dev": true - }, - "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==" - }, - "is-absolute": { - "version": "0.2.6", - "resolved": "https://registry.npmjs.org/is-absolute/-/is-absolute-0.2.6.tgz", - "integrity": "sha1-IN5p89uULvLYe5wto28XIjWxtes=", - "requires": { - "is-relative": "^0.2.1", - "is-windows": "^0.2.0" - }, - "dependencies": { - "is-windows": { - "version": "0.2.0", - "resolved": "https://registry.npmjs.org/is-windows/-/is-windows-0.2.0.tgz", - "integrity": "sha1-3hqm1j6indJIc3tp8f+LgALSEIw=" - } - } - }, - "is-arrayish": { - "version": "0.2.1", - "resolved": "https://registry.npmjs.org/is-arrayish/-/is-arrayish-0.2.1.tgz", - "integrity": "sha1-d8mYQFJ6qOyxqLppe4BkWnqSap0=" - }, - "is-bigint": { - "version": "1.0.4", - "resolved": "https://registry.npmjs.org/is-bigint/-/is-bigint-1.0.4.tgz", - "integrity": "sha512-zB9CruMamjym81i2JZ3UMn54PKGsQzsJeo6xvN3HJJ4CAsQNB6iRutp2To77OfCNuoxspsIhzaPoO1zyCEhFOg==", - "dev": true, - "requires": { - "has-bigints": "^1.0.1" - } - }, - "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==", - "requires": { - "binary-extensions": "^2.0.0" - } - }, - "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, - "requires": { - "call-bind": "^1.0.2", - "has-tostringtag": "^1.0.0" - } - }, - "is-buffer": { - "version": "1.1.6", - "resolved": "https://registry.npmjs.org/is-buffer/-/is-buffer-1.1.6.tgz", - "integrity": "sha512-NcdALwpXkTm5Zvvbk7owOUSvVvBKDgKP5/ewfXEznmQFfs4ZRmanOeKBTjRVjka3QFoN6XJ+9F3USqfHqTaU5w==" - }, - "is-callable": { - "version": "1.2.4", - "resolved": "https://registry.npmjs.org/is-callable/-/is-callable-1.2.4.tgz", - "integrity": "sha512-nsuwtxZfMX67Oryl9LCQ+upnC0Z0BgpwntpS89m1H/TLF0zNfzfLMV/9Wa/6MZsj0acpEjAO0KF1xT6ZdLl95w==", - "dev": true - }, - "is-ci": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/is-ci/-/is-ci-2.0.0.tgz", - "integrity": "sha512-YfJT7rkpQB0updsdHLGWrvhBJfcfzNNawYDNIyQXJz0IViGf75O8EBPKSdvw2rF+LGCsX4FZ8tcr3b19LcZq4w==", - "dev": true, - "requires": { - "ci-info": "^2.0.0" - } - }, - "is-core-module": { - "version": "2.8.0", - "resolved": "https://registry.npmjs.org/is-core-module/-/is-core-module-2.8.0.tgz", - "integrity": "sha512-vd15qHsaqrRL7dtH6QNuy0ndJmRDrS9HAM1CAiSifNUFv4x1a0CCVsj18hJ1mShxIG6T2i1sO78MkP56r0nYRw==", - "requires": { - "has": "^1.0.3" - } - }, - "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, - "requires": { - "has-tostringtag": "^1.0.0" - } - }, - "is-dotfile": { - "version": "1.0.3", - "resolved": "https://registry.npmjs.org/is-dotfile/-/is-dotfile-1.0.3.tgz", - "integrity": "sha1-pqLzL/0t+wT1yiXs0Pa4PPeYoeE=" - }, - "is-equal-shallow": { - "version": "0.1.3", - "resolved": "https://registry.npmjs.org/is-equal-shallow/-/is-equal-shallow-0.1.3.tgz", - "integrity": "sha1-IjgJj8Ih3gvPpdnqxMRdY4qhxTQ=", - "requires": { - "is-primitive": "^2.0.0" - } - }, - "is-extendable": { - "version": "0.1.1", - "resolved": "https://registry.npmjs.org/is-extendable/-/is-extendable-0.1.1.tgz", - "integrity": "sha1-YrEQ4omkcUGOPsNqYX1HLjAd/Ik=" - }, - "is-extglob": { - "version": "2.1.1", - "resolved": "https://registry.npmjs.org/is-extglob/-/is-extglob-2.1.1.tgz", - "integrity": "sha1-qIwCU1eR8C7TfHahueqXc8gz+MI=" - }, - "is-finite": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/is-finite/-/is-finite-1.1.0.tgz", - "integrity": "sha512-cdyMtqX/BOqqNBBiKlIVkytNHm49MtMlYyn1zxzvJKWmFMlGzm+ry5BBfYyeY9YmNKbRSo/o7OX9w9ale0wg3w==" - }, - "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==" - }, - "is-generator-function": { - "version": "1.0.10", - "resolved": "https://registry.npmjs.org/is-generator-function/-/is-generator-function-1.0.10.tgz", - "integrity": "sha512-jsEjy9l3yiXEQ+PsXdmBwEPcOxaXWLspKdplFUVI9vq1iZgIekeC0L167qeu86czQaxed3q/Uzuw0swL0irL8A==", - "requires": { - "has-tostringtag": "^1.0.0" - } - }, - "is-glob": { - "version": "4.0.3", - "resolved": "https://registry.npmjs.org/is-glob/-/is-glob-4.0.3.tgz", - "integrity": "sha512-xelSayHH36ZgE7ZWhli7pW34hNbNl8Ojv5KVmkJD4hBdD3th8Tfk9vYasLM+mXWOZhFkgZfxhLSnrwRr4elSSg==", - "requires": { - "is-extglob": "^2.1.1" - } - }, - "is-installed-globally": { - "version": "0.4.0", - "resolved": "https://registry.npmjs.org/is-installed-globally/-/is-installed-globally-0.4.0.tgz", - "integrity": "sha512-iwGqO3J21aaSkC7jWnHP/difazwS7SFeIqxv6wEtLU8Y5KlzFTjyqcSIT0d8s4+dDhKytsk9PJZ2BkS5eZwQRQ==", - "dev": true, - "requires": { - "global-dirs": "^3.0.0", - "is-path-inside": "^3.0.2" - } - }, - "is-lambda": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/is-lambda/-/is-lambda-1.0.1.tgz", - "integrity": "sha1-PZh3iZ5qU+/AFgUEzeFfgubwYdU=", - "dev": true - }, - "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 - }, - "is-npm": { - "version": "5.0.0", - "resolved": "https://registry.npmjs.org/is-npm/-/is-npm-5.0.0.tgz", - "integrity": "sha512-WW/rQLOazUq+ST/bCAVBp/2oMERWLsR7OrKyt052dNDk4DHcDE0/7QSXITlmi+VBcV13DfIbysG3tZJm5RfdBA==", - "dev": true - }, - "is-number": { - "version": "7.0.0", - "resolved": "https://registry.npmjs.org/is-number/-/is-number-7.0.0.tgz", - "integrity": "sha512-41Cifkg6e8TylSpdtTpeLVMqvSBEVzTttHvERD741+pnZ8ANv0004MRL43QKPDlK9cGvNp6NZWZUBlbGXYxxng==" - }, - "is-number-object": { - "version": "1.0.6", - "resolved": "https://registry.npmjs.org/is-number-object/-/is-number-object-1.0.6.tgz", - "integrity": "sha512-bEVOqiRcvo3zO1+G2lVMy+gkkEm9Yh7cDMRusKKu5ZJKPUYSJwICTKZrNKHA2EbSP0Tu0+6B/emsYNHZyn6K8g==", - "dev": true, - "requires": { - "has-tostringtag": "^1.0.0" - } - }, - "is-obj": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/is-obj/-/is-obj-2.0.0.tgz", - "integrity": "sha512-drqDG3cbczxxEJRoOXcOjtdp1J/lyp1mNn0xaznRs8+muBhgQcrnbspox5X5fOw0HnMnbfDzvnEMEtqDEJEo8w==", - "dev": true - }, - "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 - }, - "is-plain-obj": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/is-plain-obj/-/is-plain-obj-1.1.0.tgz", - "integrity": "sha1-caUMhCnfync8kqOQpKA7OfzVHT4=", - "dev": true - }, - "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 - }, - "is-posix-bracket": { - "version": "0.1.1", - "resolved": "https://registry.npmjs.org/is-posix-bracket/-/is-posix-bracket-0.1.1.tgz", - "integrity": "sha1-MzTceXdDaOkvAW5vvAqI9c1ua8Q=" - }, - "is-primitive": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/is-primitive/-/is-primitive-2.0.0.tgz", - "integrity": "sha1-IHurkWOEmcB7Kt8kCkGochADRXU=" - }, - "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, - "requires": { - "call-bind": "^1.0.2", - "has-tostringtag": "^1.0.0" - } - }, - "is-relative": { - "version": "0.2.1", - "resolved": "https://registry.npmjs.org/is-relative/-/is-relative-0.2.1.tgz", - "integrity": "sha1-0n9MfVFtF1+2ENuEu+7yPDvJeqU=", - "requires": { - "is-unc-path": "^0.1.1" - } - }, - "is-shared-array-buffer": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/is-shared-array-buffer/-/is-shared-array-buffer-1.0.1.tgz", - "integrity": "sha512-IU0NmyknYZN0rChcKhRO1X8LYz5Isj/Fsqh8NJOSf+N/hCOTwy29F32Ik7a+QszE63IdvmwdTPDd6cZ5pg4cwA==", - "dev": true - }, - "is-ssh": { - "version": "1.3.3", - "resolved": "https://registry.npmjs.org/is-ssh/-/is-ssh-1.3.3.tgz", - "integrity": "sha512-NKzJmQzJfEEma3w5cJNcUMxoXfDjz0Zj0eyCalHn2E6VOwlzjZo0yuO2fcBSf8zhFuVCL/82/r5gRcoi6aEPVQ==", - "dev": true, - "requires": { - "protocols": "^1.1.0" - } - }, - "is-stream": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/is-stream/-/is-stream-2.0.1.tgz", - "integrity": "sha512-hFoiJiTl63nn+kstHGBtewWSKnQLpyb155KHheA1l39uvtO9nWIop1p3udqPcUd/xbF1VLMO4n7OI6p7RbngDg==" - }, - "is-string": { - "version": "1.0.7", - "resolved": "https://registry.npmjs.org/is-string/-/is-string-1.0.7.tgz", - "integrity": "sha512-tE2UXzivje6ofPW7l23cjDOMa09gb7xlAqG6jG5ej6uPV32TlWP3NKPigtaGeHNu9fohccRYvIiZMfOOnOYUtg==", - "dev": true, - "requires": { - "has-tostringtag": "^1.0.0" - } - }, - "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, - "requires": { - "has-symbols": "^1.0.2" - } - }, - "is-text-path": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/is-text-path/-/is-text-path-1.0.1.tgz", - "integrity": "sha1-Thqg+1G/vLPpJogAE5cgLBd1tm4=", - "dev": true, - "requires": { - "text-extensions": "^1.0.0" - } - }, - "is-typedarray": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/is-typedarray/-/is-typedarray-1.0.0.tgz", - "integrity": "sha1-5HnICFjfDBsR3dppQPlgEfzaSpo=", - "dev": true - }, - "is-unc-path": { - "version": "0.1.2", - "resolved": "https://registry.npmjs.org/is-unc-path/-/is-unc-path-0.1.2.tgz", - "integrity": "sha1-arBTpyVzwQJQ/0FqOBTDUXivObk=", - "requires": { - "unc-path-regex": "^0.1.0" - } - }, - "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==" - }, - "is-utf8": { - "version": "0.2.1", - "resolved": "https://registry.npmjs.org/is-utf8/-/is-utf8-0.2.1.tgz", - "integrity": "sha1-Sw2hRCEE0bM2NA6AeX6GXPOffXI=" - }, - "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, - "requires": { - "call-bind": "^1.0.2" - } - }, - "is-windows": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/is-windows/-/is-windows-1.0.2.tgz", - "integrity": "sha512-eXK1UInq2bPmjyX6e3VHIzMLobc4J94i4AWn+Hpq3OU5KkrRC96OAcR3PRJ/pGu6m8TRnBHP9dkXQVsT/COVIA==", - "dev": true - }, - "is-yarn-global": { - "version": "0.3.0", - "resolved": "https://registry.npmjs.org/is-yarn-global/-/is-yarn-global-0.3.0.tgz", - "integrity": "sha512-VjSeb/lHmkoyd8ryPVIKvOCn4D1koMqY+vqyjjUfc3xyKtP4dYOxM44sZrnqQSzSds3xyOrUTLTC9LVCVgLngw==", - "dev": true - }, - "isarray": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/isarray/-/isarray-1.0.0.tgz", - "integrity": "sha1-u5NdSFgsuhaMBoNJV6VKPgcSTxE=" - }, - "isexe": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/isexe/-/isexe-2.0.0.tgz", - "integrity": "sha1-6PvzdNxVb/iUehDcsFctYz8s+hA=" - }, - "isobject": { - "version": "3.0.1", - "resolved": "https://registry.npmjs.org/isobject/-/isobject-3.0.1.tgz", - "integrity": "sha1-TkMekrEalzFjaqH5yNHMvP2reN8=" - }, - "isstream": { - "version": "0.1.2", - "resolved": "https://registry.npmjs.org/isstream/-/isstream-0.1.2.tgz", - "integrity": "sha1-R+Y/evVa+m+S4VAOaQ64uFKcCZo=", - "dev": true - }, - "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 - }, - "istanbul-lib-hook": { - "version": "3.0.0", - "resolved": "https://registry.npmjs.org/istanbul-lib-hook/-/istanbul-lib-hook-3.0.0.tgz", - "integrity": "sha512-Pt/uge1Q9s+5VAZ+pCo16TYMWPBIl+oaNIjgLQxcX0itS6ueeaA+pEfThZpH8WxhFgCiEb8sAJY6MdUKgiIWaQ==", - "dev": true, - "requires": { - "append-transform": "^2.0.0" - } - }, - "istanbul-lib-instrument": { - "version": "4.0.3", - "resolved": "https://registry.npmjs.org/istanbul-lib-instrument/-/istanbul-lib-instrument-4.0.3.tgz", - "integrity": "sha512-BXgQl9kf4WTCPCCpmFGoJkz/+uhvm7h7PFKUYxh7qarQd3ER33vHG//qaE8eN25l07YqZPpHXU9I09l/RD5aGQ==", - "dev": true, - "requires": { - "@babel/core": "^7.7.5", - "@istanbuljs/schema": "^0.1.2", - "istanbul-lib-coverage": "^3.0.0", - "semver": "^6.3.0" - }, - "dependencies": { - "semver": { - "version": "6.3.0", - "resolved": "https://registry.npmjs.org/semver/-/semver-6.3.0.tgz", - "integrity": "sha512-b39TBaTSfV6yBrapU89p5fKekE2m/NwnDocOVruQFS1/veMgdzuPcnOM34M6CwxW8jH/lxEa5rBoDeUwu5HHTw==", - "dev": true - } - } - }, - "istanbul-lib-processinfo": { - "version": "2.0.2", - "resolved": "https://registry.npmjs.org/istanbul-lib-processinfo/-/istanbul-lib-processinfo-2.0.2.tgz", - "integrity": "sha512-kOwpa7z9hme+IBPZMzQ5vdQj8srYgAtaRqeI48NGmAQ+/5yKiHLV0QbYqQpxsdEF0+w14SoB8YbnHKcXE2KnYw==", - "dev": true, - "requires": { - "archy": "^1.0.0", - "cross-spawn": "^7.0.0", - "istanbul-lib-coverage": "^3.0.0-alpha.1", - "make-dir": "^3.0.0", - "p-map": "^3.0.0", - "rimraf": "^3.0.0", - "uuid": "^3.3.3" - }, - "dependencies": { - "p-map": { - "version": "3.0.0", - "resolved": "https://registry.npmjs.org/p-map/-/p-map-3.0.0.tgz", - "integrity": "sha512-d3qXVTF/s+W+CdJ5A29wywV2n8CQQYahlgz2bFiA+4eVNJbHJodPZ+/gXwPGh0bOqA+j8S+6+ckmvLGPk1QpxQ==", - "dev": true, - "requires": { - "aggregate-error": "^3.0.0" - } - }, - "uuid": { - "version": "3.4.0", - "resolved": "https://registry.npmjs.org/uuid/-/uuid-3.4.0.tgz", - "integrity": "sha512-HjSDRw6gZE5JMggctHBcjVak08+KEVhSIiDzFnT9S9aegmp85S/bReBVTb4QTFaRNptJ9kuYaNhnbNEOkbKb/A==", - "dev": true - } - } - }, - "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, - "requires": { - "istanbul-lib-coverage": "^3.0.0", - "make-dir": "^3.0.0", - "supports-color": "^7.1.0" - } - }, - "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, - "requires": { - "debug": "^4.1.1", - "istanbul-lib-coverage": "^3.0.0", - "source-map": "^0.6.1" - } - }, - "istanbul-reports": { - "version": "3.1.3", - "resolved": "https://registry.npmjs.org/istanbul-reports/-/istanbul-reports-3.1.3.tgz", - "integrity": "sha512-x9LtDVtfm/t1GFiLl3NffC7hz+I1ragvgX1P/Lg1NlIagifZDKUkuuaAxH/qpwj2IuEfD8G2Bs/UKp+sZ/pKkg==", - "dev": true, - "requires": { - "html-escaper": "^2.0.0", - "istanbul-lib-report": "^3.0.0" - } - }, - "jest-worker": { - "version": "27.4.5", - "resolved": "https://registry.npmjs.org/jest-worker/-/jest-worker-27.4.5.tgz", - "integrity": "sha512-f2s8kEdy15cv9r7q4KkzGXvlY0JTcmCbMHZBfSQDwW77REr45IDWwd0lksDFeVHH2jJ5pqb90T77XscrjeGzzg==", - "requires": { - "@types/node": "*", - "merge-stream": "^2.0.0", - "supports-color": "^8.0.0" - }, - "dependencies": { - "supports-color": { - "version": "8.1.1", - "resolved": "https://registry.npmjs.org/supports-color/-/supports-color-8.1.1.tgz", - "integrity": "sha512-MpUEN2OodtUzxvKQl72cUF7RQ5EiHsGvSsVG0ia9c5RbWGL2CI4C7EpPS8UTBIplnlzZiNuV56w+FuNxy3ty2Q==", - "requires": { - "has-flag": "^4.0.0" - } - } - } - }, - "jju": { - "version": "1.4.0", - "resolved": "https://registry.npmjs.org/jju/-/jju-1.4.0.tgz", - "integrity": "sha1-o6vicYryQaKykE+EpiWXDzia4yo=", - "dev": true - }, - "js-tokens": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/js-tokens/-/js-tokens-4.0.0.tgz", - "integrity": "sha512-RdJUflcE3cUzKiMqQgsCu06FPu9UdIJO0beYbPhHN4k6apgJtifcoCtT9bcxOpYBtpD2kCM6Sbzg4CausW/PKQ==" - }, - "js-yaml": { - "version": "4.1.0", - "resolved": "https://registry.npmjs.org/js-yaml/-/js-yaml-4.1.0.tgz", - "integrity": "sha512-wpxZs9NoxZaJESJGIZTyDEaYpl0FKSA+FB9aJiyemKhMwkxQg63h4T1KJgUGHpTqPDNRcmmYLugrRjJlBtWvRA==", - "requires": { - "argparse": "^2.0.1" - } - }, - "jsbn": { - "version": "0.1.1", - "resolved": "https://registry.npmjs.org/jsbn/-/jsbn-0.1.1.tgz", - "integrity": "sha1-peZUwuWi3rXyAdls77yoDA7y9RM=", - "dev": true - }, - "jsesc": { - "version": "2.5.2", - "resolved": "https://registry.npmjs.org/jsesc/-/jsesc-2.5.2.tgz", - "integrity": "sha512-OYu7XEzjkCQ3C5Ps3QIZsQfNpqoJyZZA99wd9aWd05NCtC5pWOkShK2mkL6HXQR6/Cy2lbNdPlZBpuQHXE63gA==" - }, - "json-buffer": { - "version": "3.0.0", - "resolved": "https://registry.npmjs.org/json-buffer/-/json-buffer-3.0.0.tgz", - "integrity": "sha1-Wx85evx11ne96Lz8Dkfh+aPZqJg=", - "dev": true - }, - "json-parse-better-errors": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/json-parse-better-errors/-/json-parse-better-errors-1.0.2.tgz", - "integrity": "sha512-mrqyZKfX5EhL7hvqcV6WG1yYjnjeuYDzDhhcAAUrq8Po85NBQBJP+ZDUT75qZQ98IkUoBqdkExkukOU7Ts2wrw==" - }, - "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 - }, - "json-parse-helpfulerror": { - "version": "1.0.3", - "resolved": "https://registry.npmjs.org/json-parse-helpfulerror/-/json-parse-helpfulerror-1.0.3.tgz", - "integrity": "sha1-E/FM4C7tTpgSl7ZOueO5MuLdE9w=", - "dev": true, - "requires": { - "jju": "^1.1.0" - } - }, - "json-schema": { - "version": "0.4.0", - "resolved": "https://registry.npmjs.org/json-schema/-/json-schema-0.4.0.tgz", - "integrity": "sha512-es94M3nTIfsEPisRafak+HDLfHXnKBhV3vU5eqPcS3flIWqcxJWgXHXiey3YrpaNsanY5ei1VoYEbOzijuq9BA==" - }, - "json-schema-to-ts": { - "version": "1.6.4", - "resolved": "https://registry.npmjs.org/json-schema-to-ts/-/json-schema-to-ts-1.6.4.tgz", - "integrity": "sha512-pR4yQ9DHz6itqswtHCm26mw45FSNfQ9rEQjosaZErhn5J3J2sIViQiz8rDaezjKAhFGpmsoczYVBgGHzFw/stA==", - "requires": { - "@types/json-schema": "^7.0.6", - "ts-toolbelt": "^6.15.5" - } - }, - "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==" - }, - "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": "sha1-nbe1lJatPzz+8wp1FC0tkwrXJlE=", - "dev": true - }, - "json-stringify-safe": { - "version": "5.0.1", - "resolved": "https://registry.npmjs.org/json-stringify-safe/-/json-stringify-safe-5.0.1.tgz", - "integrity": "sha1-Epai1Y/UXxmg9s4B1lcB4sc1tus=", - "dev": true - }, - "json3": { - "version": "3.3.2", - "resolved": "https://registry.npmjs.org/json3/-/json3-3.3.2.tgz", - "integrity": "sha1-PAQ0dD35Pi9cQq7nsZvLSDV19OE=" - }, - "json5": { - "version": "2.2.0", - "resolved": "https://registry.npmjs.org/json5/-/json5-2.2.0.tgz", - "integrity": "sha512-f+8cldu7X/y7RAJurMEJmdoKXGB/X550w2Nr3tTbezL6RwEE/iMcm+tZnXeoZtKuOq6ft8+CqzEkrIgx1fPoQA==", - "requires": { - "minimist": "^1.2.5" - } - }, - "jsonfile": { - "version": "6.1.0", - "resolved": "https://registry.npmjs.org/jsonfile/-/jsonfile-6.1.0.tgz", - "integrity": "sha512-5dgndWOriYSm5cnYaJNhalLNDKOqFwyDB/rr1E9ZsGciGvKPs8R2xYGCacuf3z6K1YKDz182fd+fY3cn3pMqXQ==", - "dev": true, - "requires": { - "graceful-fs": "^4.1.6", - "universalify": "^2.0.0" - } - }, - "jsonlines": { - "version": "0.1.1", - "resolved": "https://registry.npmjs.org/jsonlines/-/jsonlines-0.1.1.tgz", - "integrity": "sha1-T80kbcXQ44aRkHxEqwAveC0dlMw=", - "dev": true - }, - "jsonparse": { - "version": "1.3.1", - "resolved": "https://registry.npmjs.org/jsonparse/-/jsonparse-1.3.1.tgz", - "integrity": "sha1-P02uSpH6wxX3EGL4UhzCOfE2YoA=", - "dev": true - }, - "JSONStream": { - "version": "1.3.5", - "resolved": "https://registry.npmjs.org/JSONStream/-/JSONStream-1.3.5.tgz", - "integrity": "sha512-E+iruNOY8VV9s4JEbe1aNEm6MiszPRr/UfcHMz0TQh1BXSxHK+ASV1R6W4HpjBhSeS+54PIsAMCBmwD06LLsqQ==", - "dev": true, - "requires": { - "jsonparse": "^1.2.0", - "through": ">=2.2.7 <3" - } - }, - "jsonwebtoken": { - "version": "8.5.1", - "resolved": "https://registry.npmjs.org/jsonwebtoken/-/jsonwebtoken-8.5.1.tgz", - "integrity": "sha512-XjwVfRS6jTMsqYs0EsuJ4LGxXV14zQybNd4L2r0UvbVnSF9Af8x7p5MzbJ90Ioz/9TI41/hTCvznF/loiSzn8w==", - "requires": { - "jws": "^3.2.2", - "lodash.includes": "^4.3.0", - "lodash.isboolean": "^3.0.3", - "lodash.isinteger": "^4.0.4", - "lodash.isnumber": "^3.0.3", - "lodash.isplainobject": "^4.0.6", - "lodash.isstring": "^4.0.1", - "lodash.once": "^4.0.0", - "ms": "^2.1.1", - "semver": "^5.6.0" - }, - "dependencies": { - "jwa": { - "version": "1.4.1", - "resolved": "https://registry.npmjs.org/jwa/-/jwa-1.4.1.tgz", - "integrity": "sha512-qiLX/xhEEFKUAJ6FiBMbes3w9ATzyk5W7Hvzpa/SLYdxNtng+gcurvrI7TbACjIXlsJyr05/S1oUhZrc63evQA==", - "requires": { - "buffer-equal-constant-time": "1.0.1", - "ecdsa-sig-formatter": "1.0.11", - "safe-buffer": "^5.0.1" - } - }, - "jws": { - "version": "3.2.2", - "resolved": "https://registry.npmjs.org/jws/-/jws-3.2.2.tgz", - "integrity": "sha512-YHlZCB6lMTllWDtSPHz/ZXTsi8S00usEV6v1tjq8tOUZzw7DpSDWVXjXDre6ed1w/pd495ODpHZYSdkRTsa0HA==", - "requires": { - "jwa": "^1.4.1", - "safe-buffer": "^5.0.1" - } - }, - "semver": { - "version": "5.7.1", - "resolved": "https://registry.npmjs.org/semver/-/semver-5.7.1.tgz", - "integrity": "sha512-sauaDf/PZdVgrLTNYHRtpXa1iRiKcaebiKQ1BJdpQlWH2lCvexQdX55snPFyK7QzpudqbCI0qXFfOasHdyNDGQ==" - } - } - }, - "jsprim": { - "version": "1.4.2", - "resolved": "https://registry.npmjs.org/jsprim/-/jsprim-1.4.2.tgz", - "integrity": "sha512-P2bSOMAc/ciLz6DzgjVlGJP9+BrJWu5UDGK70C2iweC5QBIeFf0ZXRvGjEj2uYgrY2MkAAhsSWHDWlFtEroZWw==", - "dev": true, - "requires": { - "assert-plus": "1.0.0", - "extsprintf": "1.3.0", - "json-schema": "0.4.0", - "verror": "1.10.0" - } - }, - "jwa": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/jwa/-/jwa-2.0.0.tgz", - "integrity": "sha512-jrZ2Qx916EA+fq9cEAeCROWPTfCwi1IVHqT2tapuqLEVVDKFDENFw1oL+MwrTvH6msKxsd1YTDVw6uKEcsrLEA==", - "optional": true, - "requires": { - "buffer-equal-constant-time": "1.0.1", - "ecdsa-sig-formatter": "1.0.11", - "safe-buffer": "^5.0.1" - } - }, - "jwk-to-pem": { - "version": "2.0.5", - "resolved": "https://registry.npmjs.org/jwk-to-pem/-/jwk-to-pem-2.0.5.tgz", - "integrity": "sha512-L90jwellhO8jRKYwbssU9ifaMVqajzj3fpRjDKcsDzrslU9syRbFqfkXtT4B89HYAap+xsxNcxgBSB09ig+a7A==", - "optional": true, - "requires": { - "asn1.js": "^5.3.0", - "elliptic": "^6.5.4", - "safe-buffer": "^5.0.1" - } - }, - "jws": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/jws/-/jws-4.0.0.tgz", - "integrity": "sha512-KDncfTmOZoOMTFG4mBlG0qUIOlc03fmzH+ru6RgYVZhPkyiy/92Owlt/8UEN+a4TXR1FQetfIpJE8ApdvdVxTg==", - "optional": true, - "requires": { - "jwa": "^2.0.0", - "safe-buffer": "^5.0.1" - } - }, - "keygrip": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/keygrip/-/keygrip-1.1.0.tgz", - "integrity": "sha512-iYSchDJ+liQ8iwbSI2QqsQOvqv58eJCEanyJPJi+Khyu8smkcKSFUCbPwzFcL7YVtZ6eONjqRX/38caJ7QjRAQ==", - "requires": { - "tsscmp": "1.0.6" - } - }, - "keyv": { - "version": "3.1.0", - "resolved": "https://registry.npmjs.org/keyv/-/keyv-3.1.0.tgz", - "integrity": "sha512-9ykJ/46SN/9KPM/sichzQ7OvXyGDYKGTaDlKMGCAlg2UK8KRy4jb0d8sFc+0Tt0YYnThq8X2RZgCg74RPxgcVA==", - "dev": true, - "requires": { - "json-buffer": "3.0.0" - } - }, - "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==" - }, - "kleur": { - "version": "3.0.3", - "resolved": "https://registry.npmjs.org/kleur/-/kleur-3.0.3.tgz", - "integrity": "sha512-eTIzlVOSUR+JxdDFepEYcBMtZ9Qqdef+rnzWdRZuMbOywu5tO2w2N7rqjoANZ5k9vywhL6Br1VRjUIgTQx4E8w==", - "dev": true - }, - "koa": { - "version": "2.13.4", - "resolved": "https://registry.npmjs.org/koa/-/koa-2.13.4.tgz", - "integrity": "sha512-43zkIKubNbnrULWlHdN5h1g3SEKXOEzoAlRsHOTFpnlDu8JlAOZSMJBLULusuXRequboiwJcj5vtYXKB3k7+2g==", - "requires": { - "accepts": "^1.3.5", - "cache-content-type": "^1.0.0", - "content-disposition": "~0.5.2", - "content-type": "^1.0.4", - "cookies": "~0.8.0", - "debug": "^4.3.2", - "delegates": "^1.0.0", - "depd": "^2.0.0", - "destroy": "^1.0.4", - "encodeurl": "^1.0.2", - "escape-html": "^1.0.3", - "fresh": "~0.5.2", - "http-assert": "^1.3.0", - "http-errors": "^1.6.3", - "is-generator-function": "^1.0.7", - "koa-compose": "^4.1.0", - "koa-convert": "^2.0.0", - "on-finished": "^2.3.0", - "only": "~0.0.2", - "parseurl": "^1.3.2", - "statuses": "^1.5.0", - "type-is": "^1.6.16", - "vary": "^1.1.2" - }, - "dependencies": { - "depd": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/depd/-/depd-2.0.0.tgz", - "integrity": "sha512-g7nH6P6dyDioJogAAGprGpCtVImJhpPk/roCzdb3fIh61/s/nPsfR6onyMwkCAR/OlC3yBC0lESvUoQEAssIrw==" - } - } - }, - "koa-bodyparser": { - "version": "4.3.0", - "resolved": "https://registry.npmjs.org/koa-bodyparser/-/koa-bodyparser-4.3.0.tgz", - "integrity": "sha512-uyV8G29KAGwZc4q/0WUAjH+Tsmuv9ImfBUF2oZVyZtaeo0husInagyn/JH85xMSxM0hEk/mbCII5ubLDuqW/Rw==", - "requires": { - "co-body": "^6.0.0", - "copy-to": "^2.0.1" - } - }, - "koa-compose": { - "version": "4.1.0", - "resolved": "https://registry.npmjs.org/koa-compose/-/koa-compose-4.1.0.tgz", - "integrity": "sha512-8ODW8TrDuMYvXRwra/Kh7/rJo9BtOfPc6qO8eAfC80CnCvSjSl0bkRM24X6/XBBEyj0v1nRUQ1LyOy3dbqOWXw==" - }, - "koa-convert": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/koa-convert/-/koa-convert-2.0.0.tgz", - "integrity": "sha512-asOvN6bFlSnxewce2e/DK3p4tltyfC4VM7ZwuTuepI7dEQVcvpyFuBcEARu1+Hxg8DIwytce2n7jrZtRlPrARA==", - "requires": { - "co": "^4.6.0", - "koa-compose": "^4.1.0" - } - }, - "koa-qs": { - "version": "3.0.0", - "resolved": "https://registry.npmjs.org/koa-qs/-/koa-qs-3.0.0.tgz", - "integrity": "sha512-05IB5KirwMs3heWW26iTz46HuMAtrlrRMus/aNH1BRDocLyF/099EtCB0MIfQpRuT0TISvaTsWwSy2gctIWiGA==", - "requires": { - "merge-descriptors": "^1.0.1", - "qs": "^6.9.4" - } - }, - "lasso": { - "version": "2.11.24", - "resolved": "https://registry.npmjs.org/lasso/-/lasso-2.11.24.tgz", - "integrity": "sha512-q3FixSAt5I4OeUUadKEWfR7fPivFWhPBwqSAYtda8PwVKivAZ1DFyNFgP3l/1dc4ZfGuZt8R8rcU0YrL11wVag==", - "requires": { - "app-module-path": "^1.1.0", - "app-root-dir": "^1.0.2", - "async": "^0.9.2", - "browser-refresh-client": "^1.1.4", - "glob": "^7.1.1", - "lasso-caching-fs": "^1.0.2", - "lasso-image": "^1.0.12", - "lasso-minify-css": "^1.1.4", - "lasso-minify-js": "^1.4.0", - "lasso-package-root": "^1.0.1", - "lasso-require": "^3.4.4", - "lasso-resolve-css-urls": "^2.0.2", - "lasso-resolve-from": "^1.2.0", - "marko": "^4.2.8", - "mime": "^1.2.11", - "mkdirp": "^0.5.1", - "property-handlers": "^1.1.1", - "raptor-async": "^1.1.3", - "raptor-cache": "^1.2.3", - "raptor-detect": "^1.0.1", - "raptor-logging": "^1.1.2", - "raptor-objects": "^1.0.2", - "raptor-polyfill": "^1.0.2", - "raptor-promises": "^1.0.3", - "raptor-regexp": "^1.0.1", - "raptor-strings": "^1.0.2", - "raptor-util": "^3.2.0", - "resolve-from": "^1.0.1", - "send": "^0.13.2", - "strip-json-comments": "^2.0.1", - "through": "^2.3.8" - }, - "dependencies": { - "async": { - "version": "0.9.2", - "resolved": "https://registry.npmjs.org/async/-/async-0.9.2.tgz", - "integrity": "sha1-rqdNXmHB+JlhO/ZL2mbUx48v0X0=" - }, - "debug": { - "version": "2.2.0", - "resolved": "https://registry.npmjs.org/debug/-/debug-2.2.0.tgz", - "integrity": "sha1-+HBX6ZWxofauaklgZkE3vFbwOdo=", - "requires": { - "ms": "0.7.1" - } - }, - "etag": { - "version": "1.7.0", - "resolved": "https://registry.npmjs.org/etag/-/etag-1.7.0.tgz", - "integrity": "sha1-A9MLX2fdbmMtKUXTDWZScxo01dg=" - }, - "fresh": { - "version": "0.3.0", - "resolved": "https://registry.npmjs.org/fresh/-/fresh-0.3.0.tgz", - "integrity": "sha1-ZR+DjiJCTnVm3hYdg1jKoZn4PU8=" - }, - "http-errors": { - "version": "1.3.1", - "resolved": "https://registry.npmjs.org/http-errors/-/http-errors-1.3.1.tgz", - "integrity": "sha1-GX4izevUGYWF6GlO9nhhl7ke2UI=", - "requires": { - "inherits": "~2.0.1", - "statuses": "1" - } - }, - "mime": { - "version": "1.3.4", - "resolved": "https://registry.npmjs.org/mime/-/mime-1.3.4.tgz", - "integrity": "sha1-EV+eO2s9rylZmDyzjxSaLUDrXVM=" - }, - "mkdirp": { - "version": "0.5.5", - "resolved": "https://registry.npmjs.org/mkdirp/-/mkdirp-0.5.5.tgz", - "integrity": "sha512-NKmAlESf6jMGym1++R0Ra7wvhV+wFW63FaSOFPwRahvea0gMUcGUhVeAg/0BC0wiv9ih5NYPB1Wn1UEI1/L+xQ==", - "requires": { - "minimist": "^1.2.5" - } - }, - "ms": { - "version": "0.7.1", - "resolved": "https://registry.npmjs.org/ms/-/ms-0.7.1.tgz", - "integrity": "sha1-nNE8A62/8ltl7/3nzoZO6VIBcJg=" - }, - "range-parser": { - "version": "1.0.3", - "resolved": "https://registry.npmjs.org/range-parser/-/range-parser-1.0.3.tgz", - "integrity": "sha1-aHKCNTXGkuLCoBA4Jq/YLC4P8XU=" - }, - "resolve-from": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/resolve-from/-/resolve-from-1.0.1.tgz", - "integrity": "sha1-Jsv+k10a7uq7Kbw/5a6wHpPUQiY=" - }, - "send": { - "version": "0.13.2", - "resolved": "https://registry.npmjs.org/send/-/send-0.13.2.tgz", - "integrity": "sha1-dl52B8gFVFK7pvCwUllTUJhgNt4=", - "requires": { - "debug": "~2.2.0", - "depd": "~1.1.0", - "destroy": "~1.0.4", - "escape-html": "~1.0.3", - "etag": "~1.7.0", - "fresh": "0.3.0", - "http-errors": "~1.3.1", - "mime": "1.3.4", - "ms": "0.7.1", - "on-finished": "~2.3.0", - "range-parser": "~1.0.3", - "statuses": "~1.2.1" - } - }, - "statuses": { - "version": "1.2.1", - "resolved": "https://registry.npmjs.org/statuses/-/statuses-1.2.1.tgz", - "integrity": "sha1-3e1FzBglbVHtQK7BQkidXGECbSg=" - }, - "strip-json-comments": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/strip-json-comments/-/strip-json-comments-2.0.1.tgz", - "integrity": "sha1-PFMZQukIwml8DsNEhYwobHygpgo=" - } - } - }, - "lasso-babel-transform": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/lasso-babel-transform/-/lasso-babel-transform-1.0.2.tgz", - "integrity": "sha512-8AUeZ22LC5onZ6lanBRrdJKYq2D8EVtUoEm3UfMV/lNHD/8NUQEITZ+uRgTMxmSmAV0y68j06hsEUe4lf0tVVQ==", - "requires": { - "babel-core": "^6.0.14", - "lasso-caching-fs": "^1.0.1", - "lasso-package-root": "^1.0.0", - "strip-json-comments": "^2.0.1" - }, - "dependencies": { - "strip-json-comments": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/strip-json-comments/-/strip-json-comments-2.0.1.tgz", - "integrity": "sha1-PFMZQukIwml8DsNEhYwobHygpgo=" - } - } - }, - "lasso-caching-fs": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/lasso-caching-fs/-/lasso-caching-fs-1.0.2.tgz", - "integrity": "sha1-m+TrHwaqwSYDRMrq70LC8AhusQ0=", - "requires": { - "raptor-async": "^1.1.2" - } - }, - "lasso-image": { - "version": "1.0.13", - "resolved": "https://registry.npmjs.org/lasso-image/-/lasso-image-1.0.13.tgz", - "integrity": "sha1-ZZOAhS/AnTj5ZL8cEQTv/bzpYOE=", - "requires": { - "image-size": "^0.3.3", - "raptor-async": "^1.0.1" - } - }, - "lasso-loader": { - "version": "3.0.2", - "resolved": "https://registry.npmjs.org/lasso-loader/-/lasso-loader-3.0.2.tgz", - "integrity": "sha1-29tV1fcu6zpbrnSn4xtrtf8t0JM=", - "requires": { - "events": "^1.0.2", - "raptor-util": "^1.0.0" - }, - "dependencies": { - "events": { - "version": "1.1.1", - "resolved": "https://registry.npmjs.org/events/-/events-1.1.1.tgz", - "integrity": "sha1-nr23Y1rQmccNzEwqH1AEKI6L2SQ=" - }, - "raptor-util": { - "version": "1.1.2", - "resolved": "https://registry.npmjs.org/raptor-util/-/raptor-util-1.1.2.tgz", - "integrity": "sha1-8u6AdqmuPq4uZWcuRqIgB0+i3/M=" - } - } - }, - "lasso-minify-css": { - "version": "1.1.4", - "resolved": "https://registry.npmjs.org/lasso-minify-css/-/lasso-minify-css-1.1.4.tgz", - "integrity": "sha1-mqlNuBeL8GshR0zDDKY0l10TwB8=", - "requires": { - "sqwish": "~0.2.1" - } - }, - "lasso-minify-js": { - "version": "1.4.0", - "resolved": "https://registry.npmjs.org/lasso-minify-js/-/lasso-minify-js-1.4.0.tgz", - "integrity": "sha1-8ij0J7tkebSzdxQeN8Tp34Fznks=", - "requires": { - "uglify-js": "^2.7.3" - }, - "dependencies": { - "camelcase": { - "version": "1.2.1", - "resolved": "https://registry.npmjs.org/camelcase/-/camelcase-1.2.1.tgz", - "integrity": "sha1-m7UwTS4LVmmLLHWLCKPqqdqlijk=" - }, - "cliui": { - "version": "2.1.0", - "resolved": "https://registry.npmjs.org/cliui/-/cliui-2.1.0.tgz", - "integrity": "sha1-S0dXYP+AJkx2LDoXGQMukcf+oNE=", - "requires": { - "center-align": "^0.1.1", - "right-align": "^0.1.1", - "wordwrap": "0.0.2" - } - }, - "source-map": { - "version": "0.5.7", - "resolved": "https://registry.npmjs.org/source-map/-/source-map-0.5.7.tgz", - "integrity": "sha1-igOdLRAh0i0eoUyA2OpGi6LvP8w=" - }, - "uglify-js": { - "version": "2.8.29", - "resolved": "https://registry.npmjs.org/uglify-js/-/uglify-js-2.8.29.tgz", - "integrity": "sha1-KcVzMUgFe7Th913zW3qcty5qWd0=", - "requires": { - "source-map": "~0.5.1", - "uglify-to-browserify": "~1.0.0", - "yargs": "~3.10.0" - } - }, - "wordwrap": { - "version": "0.0.2", - "resolved": "https://registry.npmjs.org/wordwrap/-/wordwrap-0.0.2.tgz", - "integrity": "sha1-t5Zpu0LstAn4PVg8rVLKF+qhZD8=" - }, - "yargs": { - "version": "3.10.0", - "resolved": "https://registry.npmjs.org/yargs/-/yargs-3.10.0.tgz", - "integrity": "sha1-9+572FfdfB0tOMDnTvvWgdFDH9E=", - "requires": { - "camelcase": "^1.0.2", - "cliui": "^2.1.0", - "decamelize": "^1.0.0", - "window-size": "0.1.0" - } - } - } - }, - "lasso-modules-client": { - "version": "2.0.7", - "resolved": "https://registry.npmjs.org/lasso-modules-client/-/lasso-modules-client-2.0.7.tgz", - "integrity": "sha512-yYqHNy5OnZGAtKiFIx+K9F6szWxZhRibA3PVi+P2eCfQb9uKCrZnDjea+s4s9M8UXWEm/Af2mrHdx1PMKTSMJQ==", - "requires": { - "lasso-package-root": "^1.0.0", - "raptor-polyfill": "^1.0.2" - } - }, - "lasso-package-root": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/lasso-package-root/-/lasso-package-root-1.0.1.tgz", - "integrity": "sha1-mX0OcfQdA8Xw+gmlvCmNeW+LLCM=", - "requires": { - "lasso-caching-fs": "^1.0.0" - } - }, - "lasso-require": { - "version": "3.5.0", - "resolved": "https://registry.npmjs.org/lasso-require/-/lasso-require-3.5.0.tgz", - "integrity": "sha512-qXBGpZMER5Gtuw3BCBPvfvEK3Vu9MR+ekPRGvKfpuLa+OYSHL6vvcmrQIZJqrCSwCutlge+JNKwCxp6gtbQatQ==", - "requires": { - "assert": "^1.4.1", - "babel-core": "^6.26.3", - "babel-preset-env": "^1.7.0", - "buffer": "^5.2.1", - "clone": "^2.1.2", - "escodegen": "^1.11.0", - "esprima": "^4.0.1", - "estraverse": "^4.2.0", - "events": "^3.0.0", - "ignore": "^5.0.2", - "lasso-caching-fs": "^1.0.2", - "lasso-loader": "^3.0.2", - "lasso-modules-client": "^2.0.5", - "lasso-package-root": "^1.0.1", - "lasso-resolve-from": "^1.2.0", - "mkdirp": "^0.5.1", - "path-browserify": "1.0.0", - "process": "^0.11.10", - "raptor-async": "^1.1.3", - "raptor-logging": "^1.1.3", - "raptor-polyfill": "^1.1.0", - "raptor-promises": "^1.0.3", - "raptor-util": "^1.1.2", - "resolve-from": "^4.0.0", - "stream-browserify": "^2.0.1", - "string_decoder": "^1.1.1", - "through": "^2.3.8", - "url": "^0.11.0", - "util": "^0.11.0" - }, - "dependencies": { - "clone": { - "version": "2.1.2", - "resolved": "https://registry.npmjs.org/clone/-/clone-2.1.2.tgz", - "integrity": "sha1-G39Ln1kfHo+DZwQBYANFoCiHQ18=" - }, - "mkdirp": { - "version": "0.5.5", - "resolved": "https://registry.npmjs.org/mkdirp/-/mkdirp-0.5.5.tgz", - "integrity": "sha512-NKmAlESf6jMGym1++R0Ra7wvhV+wFW63FaSOFPwRahvea0gMUcGUhVeAg/0BC0wiv9ih5NYPB1Wn1UEI1/L+xQ==", - "requires": { - "minimist": "^1.2.5" - } - }, - "raptor-util": { - "version": "1.1.2", - "resolved": "https://registry.npmjs.org/raptor-util/-/raptor-util-1.1.2.tgz", - "integrity": "sha1-8u6AdqmuPq4uZWcuRqIgB0+i3/M=" - } - } - }, - "lasso-resolve-css-urls": { - "version": "2.0.2", - "resolved": "https://registry.npmjs.org/lasso-resolve-css-urls/-/lasso-resolve-css-urls-2.0.2.tgz", - "integrity": "sha1-VeWOTvLCu9nk7I+jliBv1KAVdME=", - "requires": { - "lasso-resolve-from": "^1.0.1", - "raptor-css-parser": "^1.0.2" - } - }, - "lasso-resolve-from": { - "version": "1.2.0", - "resolved": "https://registry.npmjs.org/lasso-resolve-from/-/lasso-resolve-from-1.2.0.tgz", - "integrity": "sha1-v7I0Rnr7abUwn1aLpFnMgyBiHG4=", - "requires": { - "is-absolute": "^0.2.3", - "lasso-caching-fs": "^1.0.1", - "raptor-util": "^1.0.10", - "resolve-from": "^2.0.0" - }, - "dependencies": { - "raptor-util": { - "version": "1.1.2", - "resolved": "https://registry.npmjs.org/raptor-util/-/raptor-util-1.1.2.tgz", - "integrity": "sha1-8u6AdqmuPq4uZWcuRqIgB0+i3/M=" - }, - "resolve-from": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/resolve-from/-/resolve-from-2.0.0.tgz", - "integrity": "sha1-lICrIOlP+h2egKgEx+oUdhGWa1c=" - } - } - }, - "latest-version": { - "version": "5.1.0", - "resolved": "https://registry.npmjs.org/latest-version/-/latest-version-5.1.0.tgz", - "integrity": "sha512-weT+r0kTkRQdCdYCNtkMwWXQTMEswKrFBkm4ckQOMVhhqhIMI1UT2hMj+1iigIhgSZm5gTmrRXBNoGUgaTY1xA==", - "dev": true, - "requires": { - "package-json": "^6.3.0" - } - }, - "lazy-cache": { - "version": "1.0.4", - "resolved": "https://registry.npmjs.org/lazy-cache/-/lazy-cache-1.0.4.tgz", - "integrity": "sha1-odePw6UEdMuAhF07O24dpJpEbo4=" - }, - "lerna": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/lerna/-/lerna-4.0.0.tgz", - "integrity": "sha512-DD/i1znurfOmNJb0OBw66NmNqiM8kF6uIrzrJ0wGE3VNdzeOhz9ziWLYiRaZDGGwgbcjOo6eIfcx9O5Qynz+kg==", - "dev": true, - "requires": { - "@lerna/add": "4.0.0", - "@lerna/bootstrap": "4.0.0", - "@lerna/changed": "4.0.0", - "@lerna/clean": "4.0.0", - "@lerna/cli": "4.0.0", - "@lerna/create": "4.0.0", - "@lerna/diff": "4.0.0", - "@lerna/exec": "4.0.0", - "@lerna/import": "4.0.0", - "@lerna/info": "4.0.0", - "@lerna/init": "4.0.0", - "@lerna/link": "4.0.0", - "@lerna/list": "4.0.0", - "@lerna/publish": "4.0.0", - "@lerna/run": "4.0.0", - "@lerna/version": "4.0.0", - "import-local": "^3.0.2", - "npmlog": "^4.1.2" - } - }, - "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, - "requires": { - "prelude-ls": "^1.2.1", - "type-check": "~0.4.0" - } - }, - "libnpmaccess": { - "version": "4.0.3", - "resolved": "https://registry.npmjs.org/libnpmaccess/-/libnpmaccess-4.0.3.tgz", - "integrity": "sha512-sPeTSNImksm8O2b6/pf3ikv4N567ERYEpeKRPSmqlNt1dTZbvgpJIzg5vAhXHpw2ISBsELFRelk0jEahj1c6nQ==", - "dev": true, - "requires": { - "aproba": "^2.0.0", - "minipass": "^3.1.1", - "npm-package-arg": "^8.1.2", - "npm-registry-fetch": "^11.0.0" - }, - "dependencies": { - "make-fetch-happen": { - "version": "9.1.0", - "resolved": "https://registry.npmjs.org/make-fetch-happen/-/make-fetch-happen-9.1.0.tgz", - "integrity": "sha512-+zopwDy7DNknmwPQplem5lAZX/eCOzSvSNNcSKm5eVwTkOBzoktEfXsa9L23J/GIRhxRsaxzkPEhrJEpE2F4Gg==", - "dev": true, - "requires": { - "agentkeepalive": "^4.1.3", - "cacache": "^15.2.0", - "http-cache-semantics": "^4.1.0", - "http-proxy-agent": "^4.0.1", - "https-proxy-agent": "^5.0.0", - "is-lambda": "^1.0.1", - "lru-cache": "^6.0.0", - "minipass": "^3.1.3", - "minipass-collect": "^1.0.2", - "minipass-fetch": "^1.3.2", - "minipass-flush": "^1.0.5", - "minipass-pipeline": "^1.2.4", - "negotiator": "^0.6.2", - "promise-retry": "^2.0.1", - "socks-proxy-agent": "^6.0.0", - "ssri": "^8.0.0" - } - }, - "npm-registry-fetch": { - "version": "11.0.0", - "resolved": "https://registry.npmjs.org/npm-registry-fetch/-/npm-registry-fetch-11.0.0.tgz", - "integrity": "sha512-jmlgSxoDNuhAtxUIG6pVwwtz840i994dL14FoNVZisrmZW5kWd63IUTNv1m/hyRSGSqWjCUp/YZlS1BJyNp9XA==", - "dev": true, - "requires": { - "make-fetch-happen": "^9.0.1", - "minipass": "^3.1.3", - "minipass-fetch": "^1.3.0", - "minipass-json-stream": "^1.0.1", - "minizlib": "^2.0.0", - "npm-package-arg": "^8.0.0" - } - }, - "socks-proxy-agent": { - "version": "6.1.1", - "resolved": "https://registry.npmjs.org/socks-proxy-agent/-/socks-proxy-agent-6.1.1.tgz", - "integrity": "sha512-t8J0kG3csjA4g6FTbsMOWws+7R7vuRC8aQ/wy3/1OWmsgwA68zs/+cExQ0koSitUDXqhufF/YJr9wtNMZHw5Ew==", - "dev": true, - "requires": { - "agent-base": "^6.0.2", - "debug": "^4.3.1", - "socks": "^2.6.1" - } - } - } - }, - "libnpmconfig": { - "version": "1.2.1", - "resolved": "https://registry.npmjs.org/libnpmconfig/-/libnpmconfig-1.2.1.tgz", - "integrity": "sha512-9esX8rTQAHqarx6qeZqmGQKBNZR5OIbl/Ayr0qQDy3oXja2iFVQQI81R6GZ2a02bSNZ9p3YOGX1O6HHCb1X7kA==", - "dev": true, - "requires": { - "figgy-pudding": "^3.5.1", - "find-up": "^3.0.0", - "ini": "^1.3.5" - }, - "dependencies": { - "find-up": { - "version": "3.0.0", - "resolved": "https://registry.npmjs.org/find-up/-/find-up-3.0.0.tgz", - "integrity": "sha512-1yD6RmLI1XBfxugvORwlck6f75tYL+iR0jqwsOrOxMZyGYqUuDhJ0l4AXdO1iX/FTs9cBAMEk1gWSEx1kSbylg==", - "dev": true, - "requires": { - "locate-path": "^3.0.0" - } - }, - "locate-path": { - "version": "3.0.0", - "resolved": "https://registry.npmjs.org/locate-path/-/locate-path-3.0.0.tgz", - "integrity": "sha512-7AO748wWnIhNqAuaty2ZWHkQHRSNfPVIsPIfwEOWO22AmaoVrWavlOcMR5nzTLNYvp36X220/maaRsrec1G65A==", - "dev": true, - "requires": { - "p-locate": "^3.0.0", - "path-exists": "^3.0.0" - } - }, - "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, - "requires": { - "p-try": "^2.0.0" - } - }, - "p-locate": { - "version": "3.0.0", - "resolved": "https://registry.npmjs.org/p-locate/-/p-locate-3.0.0.tgz", - "integrity": "sha512-x+12w/To+4GFfgJhBEpiDcLozRJGegY+Ei7/z0tSLkMmxGZNybVMSfWj9aJn8Z5Fc7dBUNJOOVgPv2H7IwulSQ==", - "dev": true, - "requires": { - "p-limit": "^2.0.0" - } - }, - "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 - }, - "path-exists": { - "version": "3.0.0", - "resolved": "https://registry.npmjs.org/path-exists/-/path-exists-3.0.0.tgz", - "integrity": "sha1-zg6+ql94yxiSXqfYENe1mwEP1RU=", - "dev": true - } - } - }, - "libnpmpublish": { - "version": "4.0.2", - "resolved": "https://registry.npmjs.org/libnpmpublish/-/libnpmpublish-4.0.2.tgz", - "integrity": "sha512-+AD7A2zbVeGRCFI2aO//oUmapCwy7GHqPXFJh3qpToSRNU+tXKJ2YFUgjt04LPPAf2dlEH95s6EhIHM1J7bmOw==", - "dev": true, - "requires": { - "normalize-package-data": "^3.0.2", - "npm-package-arg": "^8.1.2", - "npm-registry-fetch": "^11.0.0", - "semver": "^7.1.3", - "ssri": "^8.0.1" - }, - "dependencies": { - "make-fetch-happen": { - "version": "9.1.0", - "resolved": "https://registry.npmjs.org/make-fetch-happen/-/make-fetch-happen-9.1.0.tgz", - "integrity": "sha512-+zopwDy7DNknmwPQplem5lAZX/eCOzSvSNNcSKm5eVwTkOBzoktEfXsa9L23J/GIRhxRsaxzkPEhrJEpE2F4Gg==", - "dev": true, - "requires": { - "agentkeepalive": "^4.1.3", - "cacache": "^15.2.0", - "http-cache-semantics": "^4.1.0", - "http-proxy-agent": "^4.0.1", - "https-proxy-agent": "^5.0.0", - "is-lambda": "^1.0.1", - "lru-cache": "^6.0.0", - "minipass": "^3.1.3", - "minipass-collect": "^1.0.2", - "minipass-fetch": "^1.3.2", - "minipass-flush": "^1.0.5", - "minipass-pipeline": "^1.2.4", - "negotiator": "^0.6.2", - "promise-retry": "^2.0.1", - "socks-proxy-agent": "^6.0.0", - "ssri": "^8.0.0" - } - }, - "npm-registry-fetch": { - "version": "11.0.0", - "resolved": "https://registry.npmjs.org/npm-registry-fetch/-/npm-registry-fetch-11.0.0.tgz", - "integrity": "sha512-jmlgSxoDNuhAtxUIG6pVwwtz840i994dL14FoNVZisrmZW5kWd63IUTNv1m/hyRSGSqWjCUp/YZlS1BJyNp9XA==", - "dev": true, - "requires": { - "make-fetch-happen": "^9.0.1", - "minipass": "^3.1.3", - "minipass-fetch": "^1.3.0", - "minipass-json-stream": "^1.0.1", - "minizlib": "^2.0.0", - "npm-package-arg": "^8.0.0" - } - }, - "socks-proxy-agent": { - "version": "6.1.1", - "resolved": "https://registry.npmjs.org/socks-proxy-agent/-/socks-proxy-agent-6.1.1.tgz", - "integrity": "sha512-t8J0kG3csjA4g6FTbsMOWws+7R7vuRC8aQ/wy3/1OWmsgwA68zs/+cExQ0koSitUDXqhufF/YJr9wtNMZHw5Ew==", - "dev": true, - "requires": { - "agent-base": "^6.0.2", - "debug": "^4.3.1", - "socks": "^2.6.1" - } - } - } - }, - "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 - }, - "listener-tracker": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/listener-tracker/-/listener-tracker-2.0.0.tgz", - "integrity": "sha1-OWCLQ1wJAfpVECF8FFJyjWvBm18=" - }, - "load-json-file": { - "version": "6.2.0", - "resolved": "https://registry.npmjs.org/load-json-file/-/load-json-file-6.2.0.tgz", - "integrity": "sha512-gUD/epcRms75Cw8RT1pUdHugZYM5ce64ucs2GEISABwkRsOQr0q2wm/MV2TKThycIe5e0ytRweW2RZxclogCdQ==", - "dev": true, - "requires": { - "graceful-fs": "^4.1.15", - "parse-json": "^5.0.0", - "strip-bom": "^4.0.0", - "type-fest": "^0.6.0" - }, - "dependencies": { - "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 - } - } - }, - "loader-runner": { - "version": "4.2.0", - "resolved": "https://registry.npmjs.org/loader-runner/-/loader-runner-4.2.0.tgz", - "integrity": "sha512-92+huvxMvYlMzMt0iIOukcwYBFpkYJdpl2xsZ7LrlayO7E8SOv+JJUEK17B/dJIHAOLMfh2dZZ/Y18WgmGtYNw==" - }, - "loader-utils": { - "version": "1.4.0", - "resolved": "https://registry.npmjs.org/loader-utils/-/loader-utils-1.4.0.tgz", - "integrity": "sha512-qH0WSMBtn/oHuwjy/NucEgbx5dbxxnxup9s4PVXJUDHZBQY+s0NWA9rJf53RBnQZxfch7euUui7hpoAPvALZdA==", - "requires": { - "big.js": "^5.2.2", - "emojis-list": "^3.0.0", - "json5": "^1.0.1" - }, - "dependencies": { - "json5": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/json5/-/json5-1.0.1.tgz", - "integrity": "sha512-aKS4WQjPenRxiQsC93MNfjx+nbF4PAdYzmd/1JIj8HYzqfbu86beTuNgXDzPknWk0n0uARlyewZo4s++ES36Ow==", - "requires": { - "minimist": "^1.2.0" - } - } - } - }, - "locate-path": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/locate-path/-/locate-path-2.0.0.tgz", - "integrity": "sha1-K1aLJl7slExtnA3pw9u7ygNUzY4=", - "requires": { - "p-locate": "^2.0.0", - "path-exists": "^3.0.0" - }, - "dependencies": { - "path-exists": { - "version": "3.0.0", - "resolved": "https://registry.npmjs.org/path-exists/-/path-exists-3.0.0.tgz", - "integrity": "sha1-zg6+ql94yxiSXqfYENe1mwEP1RU=" - } - } - }, - "lodash": { - "version": "4.17.21", - "resolved": "https://registry.npmjs.org/lodash/-/lodash-4.17.21.tgz", - "integrity": "sha512-v2kDEe57lecTulaDIuNTPy3Ry4gLGJ6Z1O3vE1krgXZNrsQ+LFTGHVxVjcXPs17LhbZVGedAJv8XZ1tvj5FvSg==" - }, - "lodash._baseassign": { - "version": "3.2.0", - "resolved": "https://registry.npmjs.org/lodash._baseassign/-/lodash._baseassign-3.2.0.tgz", - "integrity": "sha1-jDigmVAPIVrQnlnxci/QxSv+Ck4=", - "requires": { - "lodash._basecopy": "^3.0.0", - "lodash.keys": "^3.0.0" - } - }, - "lodash._basecopy": { - "version": "3.0.1", - "resolved": "https://registry.npmjs.org/lodash._basecopy/-/lodash._basecopy-3.0.1.tgz", - "integrity": "sha1-jaDmqHbPNEwK2KVIghEd08XHyjY=" - }, - "lodash._basecreate": { - "version": "3.0.3", - "resolved": "https://registry.npmjs.org/lodash._basecreate/-/lodash._basecreate-3.0.3.tgz", - "integrity": "sha1-G8ZhYU2qf8MRt9A78WgGoCE8+CE=" - }, - "lodash._getnative": { - "version": "3.9.1", - "resolved": "https://registry.npmjs.org/lodash._getnative/-/lodash._getnative-3.9.1.tgz", - "integrity": "sha1-VwvH3t5G1hzc3mh9ZdPuy6o6r/U=" - }, - "lodash._isiterateecall": { - "version": "3.0.9", - "resolved": "https://registry.npmjs.org/lodash._isiterateecall/-/lodash._isiterateecall-3.0.9.tgz", - "integrity": "sha1-UgOte6Ql+uhCRg5pbbnPPmqsBXw=" - }, - "lodash._reinterpolate": { - "version": "3.0.0", - "resolved": "https://registry.npmjs.org/lodash._reinterpolate/-/lodash._reinterpolate-3.0.0.tgz", - "integrity": "sha1-DM8tiRZq8Ds2Y8eWU4t1rG4RTZ0=", - "dev": true - }, - "lodash.create": { - "version": "3.1.1", - "resolved": "https://registry.npmjs.org/lodash.create/-/lodash.create-3.1.1.tgz", - "integrity": "sha1-1/KEnw29p+BGgruM1yqwIkYd6+c=", - "requires": { - "lodash._baseassign": "^3.0.0", - "lodash._basecreate": "^3.0.0", - "lodash._isiterateecall": "^3.0.0" - } - }, - "lodash.debounce": { - "version": "4.0.8", - "resolved": "https://registry.npmjs.org/lodash.debounce/-/lodash.debounce-4.0.8.tgz", - "integrity": "sha1-gteb/zCmfEAF/9XiUVMArZyk168=" - }, - "lodash.flattendeep": { - "version": "4.4.0", - "resolved": "https://registry.npmjs.org/lodash.flattendeep/-/lodash.flattendeep-4.4.0.tgz", - "integrity": "sha1-+wMJF/hqMTTlvJvsDWngAT3f7bI=", - "dev": true - }, - "lodash.includes": { - "version": "4.3.0", - "resolved": "https://registry.npmjs.org/lodash.includes/-/lodash.includes-4.3.0.tgz", - "integrity": "sha1-YLuYqHy5I8aMoeUTJUgzFISfVT8=" - }, - "lodash.isarguments": { - "version": "3.1.0", - "resolved": "https://registry.npmjs.org/lodash.isarguments/-/lodash.isarguments-3.1.0.tgz", - "integrity": "sha1-L1c9hcaiQon/AGY7SRwdM4/zRYo=" - }, - "lodash.isarray": { - "version": "3.0.4", - "resolved": "https://registry.npmjs.org/lodash.isarray/-/lodash.isarray-3.0.4.tgz", - "integrity": "sha1-eeTriMNqgSKvhvhEqpvNhRtfu1U=" - }, - "lodash.isboolean": { - "version": "3.0.3", - "resolved": "https://registry.npmjs.org/lodash.isboolean/-/lodash.isboolean-3.0.3.tgz", - "integrity": "sha1-bC4XHbKiV82WgC/UOwGyDV9YcPY=" - }, - "lodash.isinteger": { - "version": "4.0.4", - "resolved": "https://registry.npmjs.org/lodash.isinteger/-/lodash.isinteger-4.0.4.tgz", - "integrity": "sha1-YZwK89A/iwTDH1iChAt3sRzWg0M=" - }, - "lodash.ismatch": { - "version": "4.4.0", - "resolved": "https://registry.npmjs.org/lodash.ismatch/-/lodash.ismatch-4.4.0.tgz", - "integrity": "sha1-dWy1FQyjum8RCFp4hJZF8Yj4Xzc=", - "dev": true - }, - "lodash.isnumber": { - "version": "3.0.3", - "resolved": "https://registry.npmjs.org/lodash.isnumber/-/lodash.isnumber-3.0.3.tgz", - "integrity": "sha1-POdoEMWSjQM1IwGsKHMX8RwLH/w=" - }, - "lodash.isplainobject": { - "version": "4.0.6", - "resolved": "https://registry.npmjs.org/lodash.isplainobject/-/lodash.isplainobject-4.0.6.tgz", - "integrity": "sha1-fFJqUtibRcRcxpC4gWO+BJf1UMs=" - }, - "lodash.isstring": { - "version": "4.0.1", - "resolved": "https://registry.npmjs.org/lodash.isstring/-/lodash.isstring-4.0.1.tgz", - "integrity": "sha1-1SfftUVuynzJu5XV2ur4i6VKVFE=" - }, - "lodash.keys": { - "version": "3.1.2", - "resolved": "https://registry.npmjs.org/lodash.keys/-/lodash.keys-3.1.2.tgz", - "integrity": "sha1-TbwEcrFWvlCgsoaFXRvQsMZWCYo=", - "requires": { - "lodash._getnative": "^3.0.0", - "lodash.isarguments": "^3.0.0", - "lodash.isarray": "^3.0.0" - } - }, - "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 - }, - "lodash.once": { - "version": "4.1.1", - "resolved": "https://registry.npmjs.org/lodash.once/-/lodash.once-4.1.1.tgz", - "integrity": "sha1-DdOXEhPHxW34gJd9UEyI+0cal6w=" - }, - "lodash.template": { - "version": "4.5.0", - "resolved": "https://registry.npmjs.org/lodash.template/-/lodash.template-4.5.0.tgz", - "integrity": "sha512-84vYFxIkmidUiFxidA/KjjH9pAycqW+h980j7Fuz5qxRtO9pgB7MDFTdys1N7A5mcucRiDyEq4fusljItR1T/A==", - "dev": true, - "requires": { - "lodash._reinterpolate": "^3.0.0", - "lodash.templatesettings": "^4.0.0" - } - }, - "lodash.templatesettings": { - "version": "4.2.0", - "resolved": "https://registry.npmjs.org/lodash.templatesettings/-/lodash.templatesettings-4.2.0.tgz", - "integrity": "sha512-stgLz+i3Aa9mZgnjr/O+v9ruKZsPsndy7qPZOchbqk2cnTU1ZaldKK+v7m54WoKIyxiuMZTKT2H81F8BeAc3ZQ==", - "dev": true, - "requires": { - "lodash._reinterpolate": "^3.0.0" - } - }, - "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==", - "requires": { - "chalk": "^4.1.0", - "is-unicode-supported": "^0.1.0" - } - }, - "long-timeout": { - "version": "0.1.1", - "resolved": "https://registry.npmjs.org/long-timeout/-/long-timeout-0.1.1.tgz", - "integrity": "sha1-lyHXiLR+C8taJMLivuGg2lXatRQ=" - }, - "longest": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/longest/-/longest-1.0.1.tgz", - "integrity": "sha1-MKCy2jj3N3DoKUoNIuZiXtd9AJc=" - }, - "loose-envify": { - "version": "1.4.0", - "resolved": "https://registry.npmjs.org/loose-envify/-/loose-envify-1.4.0.tgz", - "integrity": "sha512-lyuxPGr/Wfhrlem2CL/UcnUc1zcqKAImBDzukY7Y5F/yQiNdko6+fRLevlw1HgMySw7f611UIY408EtxRSoK3Q==", - "requires": { - "js-tokens": "^3.0.0 || ^4.0.0" - } - }, - "lowercase-keys": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/lowercase-keys/-/lowercase-keys-1.0.1.tgz", - "integrity": "sha512-G2Lj61tXDnVFFOi8VZds+SoQjtQC3dgokKdDG2mTm1tx4m50NUHBOZSBwQQHyy0V12A0JTG4icfZQH+xPyh8VA==", - "dev": true - }, - "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==", - "requires": { - "yallist": "^4.0.0" - } - }, - "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==", - "requires": { - "semver": "^6.0.0" - }, - "dependencies": { - "semver": { - "version": "6.3.0", - "resolved": "https://registry.npmjs.org/semver/-/semver-6.3.0.tgz", - "integrity": "sha512-b39TBaTSfV6yBrapU89p5fKekE2m/NwnDocOVruQFS1/veMgdzuPcnOM34M6CwxW8jH/lxEa5rBoDeUwu5HHTw==" - } - } - }, - "make-error": { - "version": "1.3.6", - "resolved": "https://registry.npmjs.org/make-error/-/make-error-1.3.6.tgz", - "integrity": "sha512-s8UhlNe7vPKomQhC1qFelMokr/Sc3AgNbso3n74mVPA5LTZwkB9NlXf4XPamLxJE8h0gh73rM94xvwRT2CVInw==" - }, - "make-fetch-happen": { - "version": "8.0.14", - "resolved": "https://registry.npmjs.org/make-fetch-happen/-/make-fetch-happen-8.0.14.tgz", - "integrity": "sha512-EsS89h6l4vbfJEtBZnENTOFk8mCRpY5ru36Xe5bcX1KYIli2mkSHqoFsp5O1wMDvTJJzxe/4THpCTtygjeeGWQ==", - "dev": true, - "requires": { - "agentkeepalive": "^4.1.3", - "cacache": "^15.0.5", - "http-cache-semantics": "^4.1.0", - "http-proxy-agent": "^4.0.1", - "https-proxy-agent": "^5.0.0", - "is-lambda": "^1.0.1", - "lru-cache": "^6.0.0", - "minipass": "^3.1.3", - "minipass-collect": "^1.0.2", - "minipass-fetch": "^1.3.2", - "minipass-flush": "^1.0.5", - "minipass-pipeline": "^1.2.4", - "promise-retry": "^2.0.1", - "socks-proxy-agent": "^5.0.0", - "ssri": "^8.0.0" - } - }, - "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 - }, - "marko": { - "version": "4.24.2", - "resolved": "https://registry.npmjs.org/marko/-/marko-4.24.2.tgz", - "integrity": "sha512-SbrJXLLNPfi4arDOo9yOL1feuWLmm6t1k8pI2wu6rdEXzvUXeaiMfBOZ82d59ZQwPDLnziGqcScgmSk/ShdPEA==", - "requires": { - "acorn": "^7.4.0", - "app-module-path": "^2.2.0", - "argly": "^1.0.0", - "browser-refresh-client": "^1.0.0", - "camelcase": "^5.0.0", - "char-props": "~0.1.5", - "complain": "^1.6.0", - "deresolve": "^1.1.2", - "escodegen": "^1.8.1", - "espree": "^7.3.0", - "estraverse": "^4.3.0", - "events-light": "^1.0.0", - "he": "^1.1.0", - "htmljs-parser": "^2.11.1", - "lasso-caching-fs": "^1.0.1", - "lasso-modules-client": "^2.0.4", - "lasso-package-root": "^1.0.1", - "listener-tracker": "^2.0.0", - "minimatch": "^3.0.2", - "property-handlers": "^1.0.0", - "raptor-regexp": "^1.0.0", - "raptor-util": "^3.2.0", - "resolve-from": "^2.0.0", - "self-closing-tags": "^1.0.1", - "simple-sha1": "^2.1.0", - "strip-json-comments": "^2.0.1", - "warp10": "^2.0.1" - }, - "dependencies": { - "acorn": { - "version": "7.4.1", - "resolved": "https://registry.npmjs.org/acorn/-/acorn-7.4.1.tgz", - "integrity": "sha512-nQyp0o1/mNdbTO1PO6kHkwSrmgZ0MT/jCCpNiwbUjGoRN4dlBhqJtoQuCnEOKzgTVwg0ZWiCoQy6SxMebQVh8A==" - }, - "app-module-path": { - "version": "2.2.0", - "resolved": "https://registry.npmjs.org/app-module-path/-/app-module-path-2.2.0.tgz", - "integrity": "sha1-ZBqlXft9am8KgUHEucCqULbCTdU=" - }, - "eslint-visitor-keys": { - "version": "1.3.0", - "resolved": "https://registry.npmjs.org/eslint-visitor-keys/-/eslint-visitor-keys-1.3.0.tgz", - "integrity": "sha512-6J72N8UNa462wa/KFODt/PJ3IU60SDpC3QXC1Hjc1BXXpfL2C9R5+AU7jhe0F6GREqVMh4Juu+NY7xn+6dipUQ==" - }, - "espree": { - "version": "7.3.1", - "resolved": "https://registry.npmjs.org/espree/-/espree-7.3.1.tgz", - "integrity": "sha512-v3JCNCE64umkFpmkFGqzVKsOT0tN1Zr+ueqLZfpV1Ob8e+CEgPWa+OxCoGH3tnhimMKIaBm4m/vaRpJ/krRz2g==", - "requires": { - "acorn": "^7.4.0", - "acorn-jsx": "^5.3.1", - "eslint-visitor-keys": "^1.3.0" - } - }, - "resolve-from": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/resolve-from/-/resolve-from-2.0.0.tgz", - "integrity": "sha1-lICrIOlP+h2egKgEx+oUdhGWa1c=" - }, - "strip-json-comments": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/strip-json-comments/-/strip-json-comments-2.0.1.tgz", - "integrity": "sha1-PFMZQukIwml8DsNEhYwobHygpgo=" - } - } - }, - "math-random": { - "version": "1.0.4", - "resolved": "https://registry.npmjs.org/math-random/-/math-random-1.0.4.tgz", - "integrity": "sha512-rUxjysqif/BZQH2yhd5Aaq7vXMSx9NdEsQcyA07uEzIvxgI7zIr33gGsh+RU0/XjmQpCW7RsVof1vlkvQVCK5A==" - }, - "media-typer": { - "version": "0.3.0", - "resolved": "https://registry.npmjs.org/media-typer/-/media-typer-0.3.0.tgz", - "integrity": "sha1-hxDXrwqmJvj/+hzgAWhUUmMlV0g=" - }, - "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 - }, - "meow": { - "version": "8.1.2", - "resolved": "https://registry.npmjs.org/meow/-/meow-8.1.2.tgz", - "integrity": "sha512-r85E3NdZ+mpYk1C6RjPFEMSE+s1iZMuHtsHAqY0DT3jZczl0diWUZ8g6oU7h0M9cD2EL+PzaYghhCLzR0ZNn5Q==", - "dev": true, - "requires": { - "@types/minimist": "^1.2.0", - "camelcase-keys": "^6.2.2", - "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" - }, - "dependencies": { - "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, - "requires": { - "locate-path": "^5.0.0", - "path-exists": "^4.0.0" - } - }, - "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 - }, - "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, - "requires": { - "p-locate": "^4.1.0" - } - }, - "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, - "requires": { - "p-try": "^2.0.0" - } - }, - "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, - "requires": { - "p-limit": "^2.2.0" - } - }, - "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 - }, - "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, - "requires": { - "@types/normalize-package-data": "^2.4.0", - "normalize-package-data": "^2.5.0", - "parse-json": "^5.0.0", - "type-fest": "^0.6.0" - }, - "dependencies": { - "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, - "requires": { - "hosted-git-info": "^2.1.4", - "resolve": "^1.10.0", - "semver": "2 || 3 || 4 || 5", - "validate-npm-package-license": "^3.0.1" - } - }, - "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 - } - } - }, - "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, - "requires": { - "find-up": "^4.1.0", - "read-pkg": "^5.2.0", - "type-fest": "^0.8.1" - }, - "dependencies": { - "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 - } - } - }, - "semver": { - "version": "5.7.1", - "resolved": "https://registry.npmjs.org/semver/-/semver-5.7.1.tgz", - "integrity": "sha512-sauaDf/PZdVgrLTNYHRtpXa1iRiKcaebiKQ1BJdpQlWH2lCvexQdX55snPFyK7QzpudqbCI0qXFfOasHdyNDGQ==", - "dev": true - }, - "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 - } - } - }, - "merge-descriptors": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/merge-descriptors/-/merge-descriptors-1.0.1.tgz", - "integrity": "sha1-sAqqVW3YtEVoFQ7J0blT8/kMu2E=" - }, - "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==" - }, - "merge2": { - "version": "1.4.1", - "resolved": "https://registry.npmjs.org/merge2/-/merge2-1.4.1.tgz", - "integrity": "sha512-8q7VEgMJW4J8tcfVPy8g09NcQwZdbwFEqhe/WZkoIzjn/3TGDwtOCYtXGxA3O8tPzpczCCDgv+P2P5y00ZJOOg==", - "dev": true - }, - "methods": { - "version": "1.1.2", - "resolved": "https://registry.npmjs.org/methods/-/methods-1.1.2.tgz", - "integrity": "sha1-VSmk1nZUE07cxSZmVoNbD4Ua/O4=" - }, - "micromatch": { - "version": "4.0.4", - "resolved": "https://registry.npmjs.org/micromatch/-/micromatch-4.0.4.tgz", - "integrity": "sha512-pRmzw/XUcwXGpD9aI9q/0XOwLNygjETJ8y0ao0wdqprrzDa4YnxLcz7fQRZr8voh8V10kGhABbNcHVk5wHgWwg==", - "requires": { - "braces": "^3.0.1", - "picomatch": "^2.2.3" - } - }, - "mime": { - "version": "1.6.0", - "resolved": "https://registry.npmjs.org/mime/-/mime-1.6.0.tgz", - "integrity": "sha512-x0Vn8spI+wuJ1O6S7gnbaQg8Pxh4NNHb7KSINmEWKiPE4RKOplvijn+NkmYmmRgP68mc70j2EbeTFRsrswaQeg==" - }, - "mime-db": { - "version": "1.51.0", - "resolved": "https://registry.npmjs.org/mime-db/-/mime-db-1.51.0.tgz", - "integrity": "sha512-5y8A56jg7XVQx2mbv1lu49NR4dokRnhZYTtL+KGfaa27uq4pSTXkwQkFJl4pkRMyNFz/EtYDSkiiEHx3F7UN6g==" - }, - "mime-types": { - "version": "2.1.34", - "resolved": "https://registry.npmjs.org/mime-types/-/mime-types-2.1.34.tgz", - "integrity": "sha512-6cP692WwGIs9XXdOO4++N+7qjqv0rqxxVvJ3VHPh/Sc9mVZcQP+ZGhkKiTvWMQRr2tbHkJP/Yn7Y0npb3ZBs4A==", - "requires": { - "mime-db": "1.51.0" - } - }, - "mimic-fn": { - "version": "2.1.0", - "resolved": "https://registry.npmjs.org/mimic-fn/-/mimic-fn-2.1.0.tgz", - "integrity": "sha512-OqbOk5oEQeAZ8WXWydlu9HJjz9WVdEIvamMCcXmuqUYjTknH/sqsWvhQ3vgwKFRR1HpjvNBKQ37nbJgYzGqGcg==" - }, - "mimic-response": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/mimic-response/-/mimic-response-1.0.1.tgz", - "integrity": "sha512-j5EctnkH7amfV/q5Hgmoal1g2QHFJRraOtmx0JpIqkxhBhI/lJSl1nMpQ45hVarwNETOoWEimndZ4QK0RHxuxQ==", - "dev": true - }, - "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 - }, - "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==", - "optional": true - }, - "minimalistic-crypto-utils": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/minimalistic-crypto-utils/-/minimalistic-crypto-utils-1.0.1.tgz", - "integrity": "sha1-9sAMHAsIIkblxNmd+4x8CDsrWCo=", - "optional": true - }, - "minimatch": { - "version": "3.0.4", - "resolved": "https://registry.npmjs.org/minimatch/-/minimatch-3.0.4.tgz", - "integrity": "sha512-yJHVQEhyqPLUTgt9B83PXu6W3rx4MvvHvSUvToogpwoGDOUQ+yDrR0HRot+yOCdCO7u4hX3pWft6kWBBcqh0UA==", - "requires": { - "brace-expansion": "^1.1.7" - } - }, - "minimist": { - "version": "1.2.5", - "resolved": "https://registry.npmjs.org/minimist/-/minimist-1.2.5.tgz", - "integrity": "sha512-FM9nNUYrRBAELZQT3xeZQ7fmMOBg6nWNmJKTcgsJeaLstP/UODVpGsr5OhXhhXg6f+qtJ8uiZ+PUxkDWcgIXLw==" - }, - "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, - "requires": { - "arrify": "^1.0.1", - "is-plain-obj": "^1.1.0", - "kind-of": "^6.0.3" - } - }, - "minipass": { - "version": "3.1.6", - "resolved": "https://registry.npmjs.org/minipass/-/minipass-3.1.6.tgz", - "integrity": "sha512-rty5kpw9/z8SX9dmxblFA6edItUmwJgMeYDZRrwlIVN27i8gysGbznJwUggw2V/FVqFSDdWy040ZPS811DYAqQ==", - "dev": true, - "requires": { - "yallist": "^4.0.0" - } - }, - "minipass-collect": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/minipass-collect/-/minipass-collect-1.0.2.tgz", - "integrity": "sha512-6T6lH0H8OG9kITm/Jm6tdooIbogG9e0tLgpY6mphXSm/A9u8Nq1ryBG+Qspiub9LjWlBPsPS3tWQ/Botq4FdxA==", - "dev": true, - "requires": { - "minipass": "^3.0.0" - } - }, - "minipass-fetch": { - "version": "1.4.1", - "resolved": "https://registry.npmjs.org/minipass-fetch/-/minipass-fetch-1.4.1.tgz", - "integrity": "sha512-CGH1eblLq26Y15+Azk7ey4xh0J/XfJfrCox5LDJiKqI2Q2iwOLOKrlmIaODiSQS8d18jalF6y2K2ePUm0CmShw==", - "dev": true, - "requires": { - "encoding": "^0.1.12", - "minipass": "^3.1.0", - "minipass-sized": "^1.0.3", - "minizlib": "^2.0.0" - } - }, - "minipass-flush": { - "version": "1.0.5", - "resolved": "https://registry.npmjs.org/minipass-flush/-/minipass-flush-1.0.5.tgz", - "integrity": "sha512-JmQSYYpPUqX5Jyn1mXaRwOda1uQ8HP5KAT/oDSLCzt1BYRhQU0/hDtsB1ufZfEEzMZ9aAVmsBw8+FWsIXlClWw==", - "dev": true, - "requires": { - "minipass": "^3.0.0" - } - }, - "minipass-json-stream": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/minipass-json-stream/-/minipass-json-stream-1.0.1.tgz", - "integrity": "sha512-ODqY18UZt/I8k+b7rl2AENgbWE8IDYam+undIJONvigAz8KR5GWblsFTEfQs0WODsjbSXWlm+JHEv8Gr6Tfdbg==", - "dev": true, - "requires": { - "jsonparse": "^1.3.1", - "minipass": "^3.0.0" - } - }, - "minipass-pipeline": { - "version": "1.2.4", - "resolved": "https://registry.npmjs.org/minipass-pipeline/-/minipass-pipeline-1.2.4.tgz", - "integrity": "sha512-xuIq7cIOt09RPRJ19gdi4b+RiNvDFYe5JH+ggNvBqGqpQXcru3PcRmOZuHBKWK1Txf9+cQ+HMVN4d6z46LZP7A==", - "dev": true, - "requires": { - "minipass": "^3.0.0" - } - }, - "minipass-sized": { - "version": "1.0.3", - "resolved": "https://registry.npmjs.org/minipass-sized/-/minipass-sized-1.0.3.tgz", - "integrity": "sha512-MbkQQ2CTiBMlA2Dm/5cY+9SWFEN8pzzOXi6rlM5Xxq0Yqbda5ZQy9sU75a673FE9ZK0Zsbr6Y5iP6u9nktfg2g==", - "dev": true, - "requires": { - "minipass": "^3.0.0" - } - }, - "minizlib": { - "version": "2.1.2", - "resolved": "https://registry.npmjs.org/minizlib/-/minizlib-2.1.2.tgz", - "integrity": "sha512-bAxsR8BVfj60DWXHE3u30oHzfl4G7khkSuPW+qvpd7jFRHm7dLxOjUk1EHACJ/hxLY8phGJ0YhYHZo7jil7Qdg==", - "dev": true, - "requires": { - "minipass": "^3.0.0", - "yallist": "^4.0.0" - } - }, - "mkdirp": { - "version": "1.0.4", - "resolved": "https://registry.npmjs.org/mkdirp/-/mkdirp-1.0.4.tgz", - "integrity": "sha512-vVqVZQyf3WLx2Shd0qJ9xuvqgAyKPLAiqITEtqW0oIUjzo3PePDd6fW9iFz30ef7Ysp/oiWqbhszeGWW2T6Gzw==", - "dev": true - }, - "mkdirp-infer-owner": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/mkdirp-infer-owner/-/mkdirp-infer-owner-2.0.0.tgz", - "integrity": "sha512-sdqtiFt3lkOaYvTXSRIUjkIdPTcxgv5+fgqYE/5qgwdw12cOrAuzzgzvVExIkH/ul1oeHN3bCLOWSG3XOqbKKw==", - "dev": true, - "requires": { - "chownr": "^2.0.0", - "infer-owner": "^1.0.4", - "mkdirp": "^1.0.3" - } - }, - "mocha": { - "version": "9.1.3", - "resolved": "https://registry.npmjs.org/mocha/-/mocha-9.1.3.tgz", - "integrity": "sha512-Xcpl9FqXOAYqI3j79pEtHBBnQgVXIhpULjGQa7DVb0Po+VzmSIK9kanAiWLHoRR/dbZ2qpdPshuXr8l1VaHCzw==", - "requires": { - "@ungap/promise-all-settled": "1.1.2", - "ansi-colors": "4.1.1", - "browser-stdout": "1.3.1", - "chokidar": "3.5.2", - "debug": "4.3.2", - "diff": "5.0.0", - "escape-string-regexp": "4.0.0", - "find-up": "5.0.0", - "glob": "7.1.7", - "growl": "1.10.5", - "he": "1.2.0", - "js-yaml": "4.1.0", - "log-symbols": "4.1.0", - "minimatch": "3.0.4", - "ms": "2.1.3", - "nanoid": "3.1.25", - "serialize-javascript": "6.0.0", - "strip-json-comments": "3.1.1", - "supports-color": "8.1.1", - "which": "2.0.2", - "workerpool": "6.1.5", - "yargs": "16.2.0", - "yargs-parser": "20.2.4", - "yargs-unparser": "2.0.0" - }, - "dependencies": { - "debug": { - "version": "4.3.2", - "resolved": "https://registry.npmjs.org/debug/-/debug-4.3.2.tgz", - "integrity": "sha512-mOp8wKcvj7XxC78zLgw/ZA+6TSgkoE2C/ienthhRD298T7UNwAg9diBpLRxC0mOezLl4B0xV7M0cCO6P/O0Xhw==", - "requires": { - "ms": "2.1.2" - }, - "dependencies": { - "ms": { - "version": "2.1.2", - "resolved": "https://registry.npmjs.org/ms/-/ms-2.1.2.tgz", - "integrity": "sha512-sGkPx+VjMtmA6MX27oA4FBFELFCZZ4S4XqeGOXCv68tT+jb3vk/RyaKWP0PTKyWtmLSM0b+adUTEvbs1PEaH2w==" - } - } - }, - "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==", - "requires": { - "locate-path": "^6.0.0", - "path-exists": "^4.0.0" - } - }, - "glob": { - "version": "7.1.7", - "resolved": "https://registry.npmjs.org/glob/-/glob-7.1.7.tgz", - "integrity": "sha512-OvD9ENzPLbegENnYP5UUfJIirTg4+XwMWGaQfQTY0JenxNvvIKP3U3/tAQSPIu/lHxXYSZmpXlUHeqAIdKzBLQ==", - "requires": { - "fs.realpath": "^1.0.0", - "inflight": "^1.0.4", - "inherits": "2", - "minimatch": "^3.0.4", - "once": "^1.3.0", - "path-is-absolute": "^1.0.0" - } - }, - "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==", - "requires": { - "p-locate": "^5.0.0" - } - }, - "ms": { - "version": "2.1.3", - "resolved": "https://registry.npmjs.org/ms/-/ms-2.1.3.tgz", - "integrity": "sha512-6FlzubTLZG3J2a/NVCAleEhjzq5oxgHyaCU9yYXvcLsvoVaHJq/s5xXI6/XXP6tz7R9xAOtHnSO/tXtF3WRTlA==" - }, - "p-limit": { - "version": "3.1.0", - "resolved": "https://registry.npmjs.org/p-limit/-/p-limit-3.1.0.tgz", - "integrity": "sha512-TYOanM3wGwNGsZN2cVTYPArw454xnXj5qmWF1bEoAc4+cU/ol7GVh7odevjp1FNHduHc3KZMcFduxU5Xc6uJRQ==", - "requires": { - "yocto-queue": "^0.1.0" - } - }, - "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==", - "requires": { - "p-limit": "^3.0.2" - } - }, - "supports-color": { - "version": "8.1.1", - "resolved": "https://registry.npmjs.org/supports-color/-/supports-color-8.1.1.tgz", - "integrity": "sha512-MpUEN2OodtUzxvKQl72cUF7RQ5EiHsGvSsVG0ia9c5RbWGL2CI4C7EpPS8UTBIplnlzZiNuV56w+FuNxy3ty2Q==", - "requires": { - "has-flag": "^4.0.0" - } - } - } - }, - "mocha-puppeteer": { - "version": "0.14.0", - "resolved": "https://registry.npmjs.org/mocha-puppeteer/-/mocha-puppeteer-0.14.0.tgz", - "integrity": "sha512-wajn5TWDZkvBvlkf00ksfuvy3oJ87NWMzl2Hy7f8lJXWLfYcKt/6A/R8X2eNZS7T9iW1353OuxlDxre7gUCf7g==", - "requires": { - "argly": "^1.2.0", - "babel-plugin-istanbul": "^4.1.4", - "babel-polyfill": "^6.26.0", - "bluebird": "^3.5.0", - "body-parser": "^1.18.2", - "express": "^4.15.4", - "fs-walk": "0.0.1", - "lasso": "^2.11.16", - "lasso-babel-transform": "^1.0.1", - "marko": "^4.4.26", - "mocha": "^3.5.0", - "puppeteer": "^0.12.0", - "rimraf": "^2.6.1", - "superagent": "^3.6.0", - "uuid": "^3.1.0" - }, - "dependencies": { - "browser-stdout": { - "version": "1.3.0", - "resolved": "https://registry.npmjs.org/browser-stdout/-/browser-stdout-1.3.0.tgz", - "integrity": "sha1-81HTKWnTL6XXpVZxVCY9korjvR8=" - }, - "commander": { - "version": "2.9.0", - "resolved": "https://registry.npmjs.org/commander/-/commander-2.9.0.tgz", - "integrity": "sha1-nJkJQXbhIkDLItbFFGCYQA/g99Q=", - "requires": { - "graceful-readlink": ">= 1.0.0" - } - }, - "debug": { - "version": "2.6.8", - "resolved": "https://registry.npmjs.org/debug/-/debug-2.6.8.tgz", - "integrity": "sha1-5zFTHKLt4n0YgiJCfaF4IdaP9Pw=", - "requires": { - "ms": "2.0.0" - } - }, - "diff": { - "version": "3.2.0", - "resolved": "https://registry.npmjs.org/diff/-/diff-3.2.0.tgz", - "integrity": "sha1-yc45Okt8vQsFinJck98pkCeGj/k=" - }, - "escape-string-regexp": { - "version": "1.0.5", - "resolved": "https://registry.npmjs.org/escape-string-regexp/-/escape-string-regexp-1.0.5.tgz", - "integrity": "sha1-G2HAViGQqN/2rjuyzwIAyhMLhtQ=" - }, - "growl": { - "version": "1.9.2", - "resolved": "https://registry.npmjs.org/growl/-/growl-1.9.2.tgz", - "integrity": "sha1-Dqd0NxXbjY3ixe3hd14bRayFwC8=" - }, - "has-flag": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/has-flag/-/has-flag-1.0.0.tgz", - "integrity": "sha1-nZ55MWXOAXoA8AQYxD+UKnsdEfo=" - }, - "he": { - "version": "1.1.1", - "resolved": "https://registry.npmjs.org/he/-/he-1.1.1.tgz", - "integrity": "sha1-k0EP0hsAlzUVH4howvJx80J+I/0=" - }, - "minimist": { - "version": "0.0.8", - "resolved": "https://registry.npmjs.org/minimist/-/minimist-0.0.8.tgz", - "integrity": "sha1-hX/Kv8M5fSYluCKCYuhqp6ARsF0=" - }, - "mkdirp": { - "version": "0.5.1", - "resolved": "https://registry.npmjs.org/mkdirp/-/mkdirp-0.5.1.tgz", - "integrity": "sha1-MAV0OOrGz3+MR2fzhkjWaX11yQM=", - "requires": { - "minimist": "0.0.8" - } - }, - "mocha": { - "version": "3.5.3", - "resolved": "https://registry.npmjs.org/mocha/-/mocha-3.5.3.tgz", - "integrity": "sha512-/6na001MJWEtYxHOV1WLfsmR4YIynkUEhBwzsb+fk2qmQ3iqsi258l/Q2MWHJMImAcNpZ8DEdYAK72NHoIQ9Eg==", - "requires": { - "browser-stdout": "1.3.0", - "commander": "2.9.0", - "debug": "2.6.8", - "diff": "3.2.0", - "escape-string-regexp": "1.0.5", - "glob": "7.1.1", - "growl": "1.9.2", - "he": "1.1.1", - "json3": "3.3.2", - "lodash.create": "3.1.1", - "mkdirp": "0.5.1", - "supports-color": "3.1.2" - }, - "dependencies": { - "glob": { - "version": "7.1.1", - "resolved": "https://registry.npmjs.org/glob/-/glob-7.1.1.tgz", - "integrity": "sha1-gFIR3wT6rxxjo2ADBs31reULLsg=", - "requires": { - "fs.realpath": "^1.0.0", - "inflight": "^1.0.4", - "inherits": "2", - "minimatch": "^3.0.2", - "once": "^1.3.0", - "path-is-absolute": "^1.0.0" - } - } - } - }, - "ms": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/ms/-/ms-2.0.0.tgz", - "integrity": "sha1-VgiurfwAvmwpAd9fmGF4jeDVl8g=" - }, - "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==", - "requires": { - "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" - } - }, - "rimraf": { - "version": "2.7.1", - "resolved": "https://registry.npmjs.org/rimraf/-/rimraf-2.7.1.tgz", - "integrity": "sha512-uWjbaKIK3T1OSVptzX7Nl6PvQ3qAGtKEtVRjRuazjfL3Bx5eI409VZSqgND+4UNnmzLVdPj9FqFJNPqBZFve4w==", - "requires": { - "glob": "^7.1.3" - } - }, - "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==", - "requires": { - "safe-buffer": "~5.1.0" - } - }, - "superagent": { - "version": "3.8.3", - "resolved": "https://registry.npmjs.org/superagent/-/superagent-3.8.3.tgz", - "integrity": "sha512-GLQtLMCoEIK4eDv6OGtkOoSMt3D+oq0y3dsxMuYuDvaNUvuT8eFBuLmfR0iYYzHC1e8hpzC6ZsxbuP6DIalMFA==", - "requires": { - "component-emitter": "^1.2.0", - "cookiejar": "^2.1.0", - "debug": "^3.1.0", - "extend": "^3.0.0", - "form-data": "^2.3.1", - "formidable": "^1.2.0", - "methods": "^1.1.1", - "mime": "^1.4.1", - "qs": "^6.5.1", - "readable-stream": "^2.3.5" - }, - "dependencies": { - "debug": { - "version": "3.2.7", - "resolved": "https://registry.npmjs.org/debug/-/debug-3.2.7.tgz", - "integrity": "sha512-CFjzYYAi4ThfiQvizrFQevTTXHtnCqWfe7x1AhgEscTz6ZbLbfoLRLPugTQyBth6f8ZERVUSyWHFD/7Wu4t1XQ==", - "requires": { - "ms": "^2.1.1" - } - }, - "ms": { - "version": "2.1.3", - "resolved": "https://registry.npmjs.org/ms/-/ms-2.1.3.tgz", - "integrity": "sha512-6FlzubTLZG3J2a/NVCAleEhjzq5oxgHyaCU9yYXvcLsvoVaHJq/s5xXI6/XXP6tz7R9xAOtHnSO/tXtF3WRTlA==" - } - } - }, - "supports-color": { - "version": "3.1.2", - "resolved": "https://registry.npmjs.org/supports-color/-/supports-color-3.1.2.tgz", - "integrity": "sha1-cqJiiU2dQIuVbKBf83su2KbiotU=", - "requires": { - "has-flag": "^1.0.0" - } - }, - "uuid": { - "version": "3.4.0", - "resolved": "https://registry.npmjs.org/uuid/-/uuid-3.4.0.tgz", - "integrity": "sha512-HjSDRw6gZE5JMggctHBcjVak08+KEVhSIiDzFnT9S9aegmp85S/bReBVTb4QTFaRNptJ9kuYaNhnbNEOkbKb/A==" - } - } - }, - "modify-values": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/modify-values/-/modify-values-1.0.1.tgz", - "integrity": "sha512-xV2bxeN6F7oYjZWTe/YPAy6MN2M+sL4u/Rlm2AHCIVGfo2p1yGmBHQ6vHehl4bRTZBdHu3TSkWdYgkwpYzAGSw==", - "dev": true - }, - "mongodb": { - "version": "4.2.2", - "resolved": "https://registry.npmjs.org/mongodb/-/mongodb-4.2.2.tgz", - "integrity": "sha512-zt8rCTnTKyMQppyt63qMnrLM5dbADgUk18ORPF1XbtHLIYCyc9hattaYHi0pqMvNxDpgGgUofSVzS+UQErgTug==", - "requires": { - "bson": "^4.6.0", - "denque": "^2.0.1", - "mongodb-connection-string-url": "^2.3.2", - "saslprep": "^1.0.3" - } - }, - "mongodb-connection-string-url": { - "version": "2.4.1", - "resolved": "https://registry.npmjs.org/mongodb-connection-string-url/-/mongodb-connection-string-url-2.4.1.tgz", - "integrity": "sha512-d5Kd2bVsKcSA7YI/yo57fSTtMwRQdFkvc5IZwod1RRxJtECeWPPSo7zqcUGJELifRA//Igs4spVtYAmvFCatug==", - "requires": { - "@types/whatwg-url": "^8.2.1", - "whatwg-url": "^11.0.0" - }, - "dependencies": { - "tr46": { - "version": "3.0.0", - "resolved": "https://registry.npmjs.org/tr46/-/tr46-3.0.0.tgz", - "integrity": "sha512-l7FvfAHlcmulp8kr+flpQZmVwtu7nfRV7NZujtN0OqES8EL4O4e0qqzL0DC5gAvx/ZC/9lk6rhcUwYvkBnBnYA==", - "requires": { - "punycode": "^2.1.1" - } - }, - "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==" - }, - "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==", - "requires": { - "tr46": "^3.0.0", - "webidl-conversions": "^7.0.0" - } - } - } - }, - "ms": { - "version": "2.1.2", - "resolved": "https://registry.npmjs.org/ms/-/ms-2.1.2.tgz", - "integrity": "sha512-sGkPx+VjMtmA6MX27oA4FBFELFCZZ4S4XqeGOXCv68tT+jb3vk/RyaKWP0PTKyWtmLSM0b+adUTEvbs1PEaH2w==" - }, - "multimatch": { - "version": "5.0.0", - "resolved": "https://registry.npmjs.org/multimatch/-/multimatch-5.0.0.tgz", - "integrity": "sha512-ypMKuglUrZUD99Tk2bUQ+xNQj43lPEfAeX2o9cTteAmShXy2VHDJpuwu1o0xqoKCt9jLVAvwyFKdLTPXKAfJyA==", - "dev": true, - "requires": { - "@types/minimatch": "^3.0.3", - "array-differ": "^3.0.0", - "array-union": "^2.1.0", - "arrify": "^2.0.1", - "minimatch": "^3.0.4" - }, - "dependencies": { - "arrify": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/arrify/-/arrify-2.0.1.tgz", - "integrity": "sha512-3duEwti880xqi4eAMN8AyR4a0ByT90zoYdLlevfrvU43vb0YZwZVfxOgxWrLXXXpyugL0hNZc9G6BiB5B3nUug==", - "dev": true - } - } - }, - "mute-stream": { - "version": "0.0.8", - "resolved": "https://registry.npmjs.org/mute-stream/-/mute-stream-0.0.8.tgz", - "integrity": "sha512-nnbWWOkoWyUsTjKrhgD0dcz22mdkSnpYqbEjIm2nhwhuxlSkpywJmBo8h0ZqJdkp73mb90SssHkN4rsRaBAfAA==", - "dev": true - }, - "nanoid": { - "version": "3.1.25", - "resolved": "https://registry.npmjs.org/nanoid/-/nanoid-3.1.25.tgz", - "integrity": "sha512-rdwtIXaXCLFAQbnfqDRnI6jaRHp9fTcYBjtFKE8eezcZ7LuLjhUaQGNeMXf1HmRoCH32CLz6XwX0TtxEOS/A3Q==" - }, - "natural-compare": { - "version": "1.4.0", - "resolved": "https://registry.npmjs.org/natural-compare/-/natural-compare-1.4.0.tgz", - "integrity": "sha1-Sr6/7tdUHywnrPspvbvRXI1bpPc=", - "dev": true - }, - "negotiator": { - "version": "0.6.2", - "resolved": "https://registry.npmjs.org/negotiator/-/negotiator-0.6.2.tgz", - "integrity": "sha512-hZXc7K2e+PgeI1eDBe/10Ard4ekbfrrqG8Ep+8Jmf4JID2bNg7NvCPOZN+kfF574pFQI7mum2AUqDidoKqcTOw==" - }, - "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==" - }, - "node-fetch": { - "version": "2.6.6", - "resolved": "https://registry.npmjs.org/node-fetch/-/node-fetch-2.6.6.tgz", - "integrity": "sha512-Z8/6vRlTUChSdIgMa51jxQ4lrw/Jy5SOW10ObaA47/RElsAN2c5Pn8bTgFGWn/ibwzXTE8qwr1Yzx28vsecXEA==", - "requires": { - "whatwg-url": "^5.0.0" - }, - "dependencies": { - "tr46": { - "version": "0.0.3", - "resolved": "https://registry.npmjs.org/tr46/-/tr46-0.0.3.tgz", - "integrity": "sha1-gYT9NH2snNwYWZLzpmIuFLnZq2o=" - }, - "webidl-conversions": { - "version": "3.0.1", - "resolved": "https://registry.npmjs.org/webidl-conversions/-/webidl-conversions-3.0.1.tgz", - "integrity": "sha1-JFNCdeKnvGvnvIZhHMFq4KVlSHE=" - }, - "whatwg-url": { - "version": "5.0.0", - "resolved": "https://registry.npmjs.org/whatwg-url/-/whatwg-url-5.0.0.tgz", - "integrity": "sha1-lmRU6HZUYuN2RNNib2dCzotwll0=", - "requires": { - "tr46": "~0.0.3", - "webidl-conversions": "^3.0.0" - } - } - } - }, - "node-gyp": { - "version": "5.1.1", - "resolved": "https://registry.npmjs.org/node-gyp/-/node-gyp-5.1.1.tgz", - "integrity": "sha512-WH0WKGi+a4i4DUt2mHnvocex/xPLp9pYt5R6M2JdFB7pJ7Z34hveZ4nDTGTiLXCkitA9T8HFZjhinBCiVHYcWw==", - "dev": true, - "requires": { - "env-paths": "^2.2.0", - "glob": "^7.1.4", - "graceful-fs": "^4.2.2", - "mkdirp": "^0.5.1", - "nopt": "^4.0.1", - "npmlog": "^4.1.2", - "request": "^2.88.0", - "rimraf": "^2.6.3", - "semver": "^5.7.1", - "tar": "^4.4.12", - "which": "^1.3.1" - }, - "dependencies": { - "chownr": { - "version": "1.1.4", - "resolved": "https://registry.npmjs.org/chownr/-/chownr-1.1.4.tgz", - "integrity": "sha512-jJ0bqzaylmJtVnNgzTeSOs8DPavpbYgEr/b0YL8/2GO3xJEhInFmhKMUnEJQjZumK7KXGFhUy89PrsJWlakBVg==", - "dev": true - }, - "fs-minipass": { - "version": "1.2.7", - "resolved": "https://registry.npmjs.org/fs-minipass/-/fs-minipass-1.2.7.tgz", - "integrity": "sha512-GWSSJGFy4e9GUeCcbIkED+bgAoFyj7XF1mV8rma3QW4NIqX9Kyx79N/PF61H5udOV3aY1IaMLs6pGbH71nlCTA==", - "dev": true, - "requires": { - "minipass": "^2.6.0" - } - }, - "minipass": { - "version": "2.9.0", - "resolved": "https://registry.npmjs.org/minipass/-/minipass-2.9.0.tgz", - "integrity": "sha512-wxfUjg9WebH+CUDX/CdbRlh5SmfZiy/hpkxaRI16Y9W56Pa75sWgd/rvFilSgrauD9NyFymP/+JFV3KwzIsJeg==", - "dev": true, - "requires": { - "safe-buffer": "^5.1.2", - "yallist": "^3.0.0" - } - }, - "minizlib": { - "version": "1.3.3", - "resolved": "https://registry.npmjs.org/minizlib/-/minizlib-1.3.3.tgz", - "integrity": "sha512-6ZYMOEnmVsdCeTJVE0W9ZD+pVnE8h9Hma/iOwwRDsdQoePpoX56/8B6z3P9VNwppJuBKNRuFDRNRqRWexT9G9Q==", - "dev": true, - "requires": { - "minipass": "^2.9.0" - } - }, - "mkdirp": { - "version": "0.5.5", - "resolved": "https://registry.npmjs.org/mkdirp/-/mkdirp-0.5.5.tgz", - "integrity": "sha512-NKmAlESf6jMGym1++R0Ra7wvhV+wFW63FaSOFPwRahvea0gMUcGUhVeAg/0BC0wiv9ih5NYPB1Wn1UEI1/L+xQ==", - "dev": true, - "requires": { - "minimist": "^1.2.5" - } - }, - "rimraf": { - "version": "2.7.1", - "resolved": "https://registry.npmjs.org/rimraf/-/rimraf-2.7.1.tgz", - "integrity": "sha512-uWjbaKIK3T1OSVptzX7Nl6PvQ3qAGtKEtVRjRuazjfL3Bx5eI409VZSqgND+4UNnmzLVdPj9FqFJNPqBZFve4w==", - "dev": true, - "requires": { - "glob": "^7.1.3" - } - }, - "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 - }, - "semver": { - "version": "5.7.1", - "resolved": "https://registry.npmjs.org/semver/-/semver-5.7.1.tgz", - "integrity": "sha512-sauaDf/PZdVgrLTNYHRtpXa1iRiKcaebiKQ1BJdpQlWH2lCvexQdX55snPFyK7QzpudqbCI0qXFfOasHdyNDGQ==", - "dev": true - }, - "tar": { - "version": "4.4.19", - "resolved": "https://registry.npmjs.org/tar/-/tar-4.4.19.tgz", - "integrity": "sha512-a20gEsvHnWe0ygBY8JbxoM4w3SJdhc7ZAuxkLqh+nvNQN2IOt0B5lLgM490X5Hl8FF0dl0tOf2ewFYAlIFgzVA==", - "dev": true, - "requires": { - "chownr": "^1.1.4", - "fs-minipass": "^1.2.7", - "minipass": "^2.9.0", - "minizlib": "^1.3.3", - "mkdirp": "^0.5.5", - "safe-buffer": "^5.2.1", - "yallist": "^3.1.1" - } - }, - "which": { - "version": "1.3.1", - "resolved": "https://registry.npmjs.org/which/-/which-1.3.1.tgz", - "integrity": "sha512-HxJdYWq1MTIQbJ3nw0cqssHoTNU267KlrDuGZ1WYlxDStUtKUhOaJmh112/TZmHxxUfuJqPXSOm7tDyas0OSIQ==", - "dev": true, - "requires": { - "isexe": "^2.0.0" - } - }, - "yallist": { - "version": "3.1.1", - "resolved": "https://registry.npmjs.org/yallist/-/yallist-3.1.1.tgz", - "integrity": "sha512-a4UGQaWPH59mOXUYnAG2ewncQS4i4F43Tv3JoAM+s2VDAmS9NsK8GpDMLrCHPksFT7h3K6TOoUNn2pb7RoXx4g==", - "dev": true - } - } - }, - "node-preload": { - "version": "0.2.1", - "resolved": "https://registry.npmjs.org/node-preload/-/node-preload-0.2.1.tgz", - "integrity": "sha512-RM5oyBy45cLEoHqCeh+MNuFAxO0vTFBLskvQbOKnEE7YTTSN4tbN8QWDIPQ6L+WvKsB/qLEGpYe2ZZ9d4W9OIQ==", - "dev": true, - "requires": { - "process-on-spawn": "^1.0.0" - } - }, - "node-releases": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/node-releases/-/node-releases-2.0.1.tgz", - "integrity": "sha512-CqyzN6z7Q6aMeF/ktcMVTzhAHCEpf8SOarwpzpf8pNBY2k5/oM34UHldUwp8VKI7uxct2HxSRdJjBaZeESzcxA==" - }, - "nopt": { - "version": "4.0.3", - "resolved": "https://registry.npmjs.org/nopt/-/nopt-4.0.3.tgz", - "integrity": "sha512-CvaGwVMztSMJLOeXPrez7fyfObdZqNUK1cPAEzLHrTybIua9pMdmmPR5YwtfNftIOMv3DPUhFaxsZMNTQO20Kg==", - "dev": true, - "requires": { - "abbrev": "1", - "osenv": "^0.1.4" - } - }, - "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, - "requires": { - "hosted-git-info": "^4.0.1", - "is-core-module": "^2.5.0", - "semver": "^7.3.4", - "validate-npm-package-license": "^3.0.1" - } - }, - "normalize-path": { - "version": "3.0.0", - "resolved": "https://registry.npmjs.org/normalize-path/-/normalize-path-3.0.0.tgz", - "integrity": "sha512-6eZs5Ls3WtCisHWp9S2GUy8dqkpGi4BVSz3GaqiE6ezub0512ESztXUwUB6C6IKbQkY2Pnb/mD4WYojCRwcwLA==" - }, - "normalize-url": { - "version": "6.1.0", - "resolved": "https://registry.npmjs.org/normalize-url/-/normalize-url-6.1.0.tgz", - "integrity": "sha512-DlL+XwOy3NxAQ8xuC0okPgK46iuVNAK01YN7RueYBqqFeGsBjV9XmCAzAdgt+667bCl5kPh9EqKKDwnaPG1I7A==", - "dev": true - }, - "npm-bundled": { - "version": "1.1.2", - "resolved": "https://registry.npmjs.org/npm-bundled/-/npm-bundled-1.1.2.tgz", - "integrity": "sha512-x5DHup0SuyQcmL3s7Rx/YQ8sbw/Hzg0rj48eN0dV7hf5cmQq5PXIeioroH3raV1QC1yh3uTYuMThvEQF3iKgGQ==", - "dev": true, - "requires": { - "npm-normalize-package-bin": "^1.0.1" - } - }, - "npm-check-updates": { - "version": "12.1.0", - "resolved": "https://registry.npmjs.org/npm-check-updates/-/npm-check-updates-12.1.0.tgz", - "integrity": "sha512-9GtSetBvcth7MuL+0MpOmWgdfiEgZcWRfnvoYnNZxbZpleHZCT0Z3HnbsL6/EAT2M+ye7FTZ+YjmDmZptt7Rkg==", - "dev": true, - "requires": { - "chalk": "^4.1.2", - "cint": "^8.2.1", - "cli-table": "^0.3.11", - "commander": "^8.3.0", - "fast-memoize": "^2.5.2", - "find-up": "5.0.0", - "fp-and-or": "^0.1.3", - "get-stdin": "^8.0.0", - "globby": "^11.0.4", - "hosted-git-info": "^4.0.2", - "json-parse-helpfulerror": "^1.0.3", - "jsonlines": "^0.1.1", - "libnpmconfig": "^1.2.1", - "lodash": "^4.17.21", - "minimatch": "^3.0.4", - "p-map": "^4.0.0", - "pacote": "^12.0.2", - "parse-github-url": "^1.0.2", - "progress": "^2.0.3", - "prompts": "^2.4.2", - "rc-config-loader": "^4.0.0", - "remote-git-tags": "^3.0.0", - "rimraf": "^3.0.2", - "semver": "^7.3.5", - "semver-utils": "^1.1.4", - "source-map-support": "^0.5.21", - "spawn-please": "^1.0.0", - "update-notifier": "^5.1.0" - }, - "dependencies": { - "@npmcli/run-script": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/@npmcli/run-script/-/run-script-2.0.0.tgz", - "integrity": "sha512-fSan/Pu11xS/TdaTpTB0MRn9guwGU8dye+x56mEVgBEd/QsybBbYcAL0phPXi8SGWFEChkQd6M9qL4y6VOpFig==", - "dev": true, - "requires": { - "@npmcli/node-gyp": "^1.0.2", - "@npmcli/promise-spawn": "^1.3.2", - "node-gyp": "^8.2.0", - "read-package-json-fast": "^2.0.1" - } - }, - "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==", - "dev": true, - "requires": { - "delegates": "^1.0.0", - "readable-stream": "^3.6.0" - } - }, - "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, - "requires": { - "locate-path": "^6.0.0", - "path-exists": "^4.0.0" - } - }, - "gauge": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/gauge/-/gauge-4.0.0.tgz", - "integrity": "sha512-F8sU45yQpjQjxKkm1UOAhf0U/O0aFt//Fl7hsrNVto+patMHjs7dPI9mFOGUKbhrgKm0S3EjW3scMFuQmWSROw==", - "dev": true, - "requires": { - "ansi-regex": "^5.0.1", - "aproba": "^1.0.3 || ^2.0.0", - "color-support": "^1.1.2", - "console-control-strings": "^1.0.0", - "has-unicode": "^2.0.1", - "signal-exit": "^3.0.0", - "string-width": "^4.2.3", - "strip-ansi": "^6.0.1", - "wide-align": "^1.1.2" - } - }, - "ignore-walk": { - "version": "4.0.1", - "resolved": "https://registry.npmjs.org/ignore-walk/-/ignore-walk-4.0.1.tgz", - "integrity": "sha512-rzDQLaW4jQbh2YrOFlJdCtX8qgJTehFRYiUB2r1osqTeDzV/3+Jh8fz1oAPzUThf3iku8Ds4IDqawI5d8mUiQw==", - "dev": true, - "requires": { - "minimatch": "^3.0.4" - } - }, - "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, - "requires": { - "p-locate": "^5.0.0" - } - }, - "make-fetch-happen": { - "version": "9.1.0", - "resolved": "https://registry.npmjs.org/make-fetch-happen/-/make-fetch-happen-9.1.0.tgz", - "integrity": "sha512-+zopwDy7DNknmwPQplem5lAZX/eCOzSvSNNcSKm5eVwTkOBzoktEfXsa9L23J/GIRhxRsaxzkPEhrJEpE2F4Gg==", - "dev": true, - "requires": { - "agentkeepalive": "^4.1.3", - "cacache": "^15.2.0", - "http-cache-semantics": "^4.1.0", - "http-proxy-agent": "^4.0.1", - "https-proxy-agent": "^5.0.0", - "is-lambda": "^1.0.1", - "lru-cache": "^6.0.0", - "minipass": "^3.1.3", - "minipass-collect": "^1.0.2", - "minipass-fetch": "^1.3.2", - "minipass-flush": "^1.0.5", - "minipass-pipeline": "^1.2.4", - "negotiator": "^0.6.2", - "promise-retry": "^2.0.1", - "socks-proxy-agent": "^6.0.0", - "ssri": "^8.0.0" - } - }, - "node-gyp": { - "version": "8.4.1", - "resolved": "https://registry.npmjs.org/node-gyp/-/node-gyp-8.4.1.tgz", - "integrity": "sha512-olTJRgUtAb/hOXG0E93wZDs5YiJlgbXxTwQAFHyNlRsXQnYzUaF2aGgujZbw+hR8aF4ZG/rST57bWMWD16jr9w==", - "dev": true, - "requires": { - "env-paths": "^2.2.0", - "glob": "^7.1.4", - "graceful-fs": "^4.2.6", - "make-fetch-happen": "^9.1.0", - "nopt": "^5.0.0", - "npmlog": "^6.0.0", - "rimraf": "^3.0.2", - "semver": "^7.3.5", - "tar": "^6.1.2", - "which": "^2.0.2" - } - }, - "nopt": { - "version": "5.0.0", - "resolved": "https://registry.npmjs.org/nopt/-/nopt-5.0.0.tgz", - "integrity": "sha512-Tbj67rffqceeLpcRXrT7vKAN8CwfPeIBgM7E6iBkmKLV7bEMwpGgYLGv0jACUsECaa/vuxP0IjEont6umdMgtQ==", - "dev": true, - "requires": { - "abbrev": "1" - } - }, - "npm-packlist": { - "version": "3.0.0", - "resolved": "https://registry.npmjs.org/npm-packlist/-/npm-packlist-3.0.0.tgz", - "integrity": "sha512-L/cbzmutAwII5glUcf2DBRNY/d0TFd4e/FnaZigJV6JD85RHZXJFGwCndjMWiiViiWSsWt3tiOLpI3ByTnIdFQ==", - "dev": true, - "requires": { - "glob": "^7.1.6", - "ignore-walk": "^4.0.1", - "npm-bundled": "^1.1.1", - "npm-normalize-package-bin": "^1.0.1" - } - }, - "npm-registry-fetch": { - "version": "11.0.0", - "resolved": "https://registry.npmjs.org/npm-registry-fetch/-/npm-registry-fetch-11.0.0.tgz", - "integrity": "sha512-jmlgSxoDNuhAtxUIG6pVwwtz840i994dL14FoNVZisrmZW5kWd63IUTNv1m/hyRSGSqWjCUp/YZlS1BJyNp9XA==", - "dev": true, - "requires": { - "make-fetch-happen": "^9.0.1", - "minipass": "^3.1.3", - "minipass-fetch": "^1.3.0", - "minipass-json-stream": "^1.0.1", - "minizlib": "^2.0.0", - "npm-package-arg": "^8.0.0" - } - }, - "npmlog": { - "version": "6.0.0", - "resolved": "https://registry.npmjs.org/npmlog/-/npmlog-6.0.0.tgz", - "integrity": "sha512-03ppFRGlsyUaQFbGC2C8QWJN/C/K7PsfyD9aQdhVKAQIH4sQBc8WASqFBP7O+Ut4d2oo5LoeoboB3cGdBZSp6Q==", - "dev": true, - "requires": { - "are-we-there-yet": "^2.0.0", - "console-control-strings": "^1.1.0", - "gauge": "^4.0.0", - "set-blocking": "^2.0.0" - } - }, - "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, - "requires": { - "yocto-queue": "^0.1.0" - } - }, - "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, - "requires": { - "p-limit": "^3.0.2" - } - }, - "pacote": { - "version": "12.0.2", - "resolved": "https://registry.npmjs.org/pacote/-/pacote-12.0.2.tgz", - "integrity": "sha512-Ar3mhjcxhMzk+OVZ8pbnXdb0l8+pimvlsqBGRNkble2NVgyqOGE3yrCGi/lAYq7E7NRDMz89R1Wx5HIMCGgeYg==", - "dev": true, - "requires": { - "@npmcli/git": "^2.1.0", - "@npmcli/installed-package-contents": "^1.0.6", - "@npmcli/promise-spawn": "^1.2.0", - "@npmcli/run-script": "^2.0.0", - "cacache": "^15.0.5", - "chownr": "^2.0.0", - "fs-minipass": "^2.1.0", - "infer-owner": "^1.0.4", - "minipass": "^3.1.3", - "mkdirp": "^1.0.3", - "npm-package-arg": "^8.0.1", - "npm-packlist": "^3.0.0", - "npm-pick-manifest": "^6.0.0", - "npm-registry-fetch": "^11.0.0", - "promise-retry": "^2.0.1", - "read-package-json-fast": "^2.0.1", - "rimraf": "^3.0.2", - "ssri": "^8.0.1", - "tar": "^6.1.0" - } - }, - "socks-proxy-agent": { - "version": "6.1.1", - "resolved": "https://registry.npmjs.org/socks-proxy-agent/-/socks-proxy-agent-6.1.1.tgz", - "integrity": "sha512-t8J0kG3csjA4g6FTbsMOWws+7R7vuRC8aQ/wy3/1OWmsgwA68zs/+cExQ0koSitUDXqhufF/YJr9wtNMZHw5Ew==", - "dev": true, - "requires": { - "agent-base": "^6.0.2", - "debug": "^4.3.1", - "socks": "^2.6.1" - } - } - } - }, - "npm-install-checks": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/npm-install-checks/-/npm-install-checks-4.0.0.tgz", - "integrity": "sha512-09OmyDkNLYwqKPOnbI8exiOZU2GVVmQp7tgez2BPi5OZC8M82elDAps7sxC4l//uSUtotWqoEIDwjRvWH4qz8w==", - "dev": true, - "requires": { - "semver": "^7.1.1" - } - }, - "npm-lifecycle": { - "version": "3.1.5", - "resolved": "https://registry.npmjs.org/npm-lifecycle/-/npm-lifecycle-3.1.5.tgz", - "integrity": "sha512-lDLVkjfZmvmfvpvBzA4vzee9cn+Me4orq0QF8glbswJVEbIcSNWib7qGOffolysc3teCqbbPZZkzbr3GQZTL1g==", - "dev": true, - "requires": { - "byline": "^5.0.0", - "graceful-fs": "^4.1.15", - "node-gyp": "^5.0.2", - "resolve-from": "^4.0.0", - "slide": "^1.1.6", - "uid-number": "0.0.6", - "umask": "^1.1.0", - "which": "^1.3.1" - }, - "dependencies": { - "which": { - "version": "1.3.1", - "resolved": "https://registry.npmjs.org/which/-/which-1.3.1.tgz", - "integrity": "sha512-HxJdYWq1MTIQbJ3nw0cqssHoTNU267KlrDuGZ1WYlxDStUtKUhOaJmh112/TZmHxxUfuJqPXSOm7tDyas0OSIQ==", - "dev": true, - "requires": { - "isexe": "^2.0.0" - } - } - } - }, - "npm-normalize-package-bin": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/npm-normalize-package-bin/-/npm-normalize-package-bin-1.0.1.tgz", - "integrity": "sha512-EPfafl6JL5/rU+ot6P3gRSCpPDW5VmIzX959Ob1+ySFUuuYHWHekXpwdUZcKP5C+DS4GEtdJluwBjnsNDl+fSA==", - "dev": true - }, - "npm-package-arg": { - "version": "8.1.5", - "resolved": "https://registry.npmjs.org/npm-package-arg/-/npm-package-arg-8.1.5.tgz", - "integrity": "sha512-LhgZrg0n0VgvzVdSm1oiZworPbTxYHUJCgtsJW8mGvlDpxTM1vSJc3m5QZeUkhAHIzbz3VCHd/R4osi1L1Tg/Q==", - "dev": true, - "requires": { - "hosted-git-info": "^4.0.1", - "semver": "^7.3.4", - "validate-npm-package-name": "^3.0.0" - } - }, - "npm-packlist": { - "version": "2.2.2", - "resolved": "https://registry.npmjs.org/npm-packlist/-/npm-packlist-2.2.2.tgz", - "integrity": "sha512-Jt01acDvJRhJGthnUJVF/w6gumWOZxO7IkpY/lsX9//zqQgnF7OJaxgQXcerd4uQOLu7W5bkb4mChL9mdfm+Zg==", - "dev": true, - "requires": { - "glob": "^7.1.6", - "ignore-walk": "^3.0.3", - "npm-bundled": "^1.1.1", - "npm-normalize-package-bin": "^1.0.1" - } - }, - "npm-pick-manifest": { - "version": "6.1.1", - "resolved": "https://registry.npmjs.org/npm-pick-manifest/-/npm-pick-manifest-6.1.1.tgz", - "integrity": "sha512-dBsdBtORT84S8V8UTad1WlUyKIY9iMsAmqxHbLdeEeBNMLQDlDWWra3wYUx9EBEIiG/YwAy0XyNHDd2goAsfuA==", - "dev": true, - "requires": { - "npm-install-checks": "^4.0.0", - "npm-normalize-package-bin": "^1.0.1", - "npm-package-arg": "^8.1.2", - "semver": "^7.3.4" - } - }, - "npm-registry-fetch": { - "version": "9.0.0", - "resolved": "https://registry.npmjs.org/npm-registry-fetch/-/npm-registry-fetch-9.0.0.tgz", - "integrity": "sha512-PuFYYtnQ8IyVl6ib9d3PepeehcUeHN9IO5N/iCRhyg9tStQcqGQBRVHmfmMWPDERU3KwZoHFvbJ4FPXPspvzbA==", - "dev": true, - "requires": { - "@npmcli/ci-detect": "^1.0.0", - "lru-cache": "^6.0.0", - "make-fetch-happen": "^8.0.9", - "minipass": "^3.1.3", - "minipass-fetch": "^1.3.0", - "minipass-json-stream": "^1.0.1", - "minizlib": "^2.0.0", - "npm-package-arg": "^8.0.0" - } - }, - "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==", - "requires": { - "path-key": "^3.0.0" - } - }, - "npmlog": { - "version": "4.1.2", - "resolved": "https://registry.npmjs.org/npmlog/-/npmlog-4.1.2.tgz", - "integrity": "sha512-2uUqazuKlTaSI/dC8AzicUck7+IrEaOnN/e0jd3Xtt1KcGpwx30v50mL7oPyr/h9bL3E4aZccVwpwP+5W9Vjkg==", - "dev": true, - "requires": { - "are-we-there-yet": "~1.1.2", - "console-control-strings": "~1.1.0", - "gauge": "~2.7.3", - "set-blocking": "~2.0.0" - } - }, - "number-is-nan": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/number-is-nan/-/number-is-nan-1.0.1.tgz", - "integrity": "sha1-CXtgK1NCKlIsGvuHkDGDNpQaAR0=", - "dev": true - }, - "nyc": { - "version": "15.1.0", - "resolved": "https://registry.npmjs.org/nyc/-/nyc-15.1.0.tgz", - "integrity": "sha512-jMW04n9SxKdKi1ZMGhvUTHBN0EICCRkHemEoE5jm6mTYcqcdas0ATzgUgejlQUHMvpnOZqGB5Xxsv9KxJW1j8A==", - "dev": true, - "requires": { - "@istanbuljs/load-nyc-config": "^1.0.0", - "@istanbuljs/schema": "^0.1.2", - "caching-transform": "^4.0.0", - "convert-source-map": "^1.7.0", - "decamelize": "^1.2.0", - "find-cache-dir": "^3.2.0", - "find-up": "^4.1.0", - "foreground-child": "^2.0.0", - "get-package-type": "^0.1.0", - "glob": "^7.1.6", - "istanbul-lib-coverage": "^3.0.0", - "istanbul-lib-hook": "^3.0.0", - "istanbul-lib-instrument": "^4.0.0", - "istanbul-lib-processinfo": "^2.0.2", - "istanbul-lib-report": "^3.0.0", - "istanbul-lib-source-maps": "^4.0.0", - "istanbul-reports": "^3.0.2", - "make-dir": "^3.0.0", - "node-preload": "^0.2.1", - "p-map": "^3.0.0", - "process-on-spawn": "^1.0.0", - "resolve-from": "^5.0.0", - "rimraf": "^3.0.0", - "signal-exit": "^3.0.2", - "spawn-wrap": "^2.0.0", - "test-exclude": "^6.0.0", - "yargs": "^15.0.2" - }, - "dependencies": { - "cliui": { - "version": "6.0.0", - "resolved": "https://registry.npmjs.org/cliui/-/cliui-6.0.0.tgz", - "integrity": "sha512-t6wbgtoCXvAzst7QgXxJYqPt0usEfbgQdftEPbLL/cvv6HPE5VgvqCuAIDR0NgU52ds6rFwqrgakNLrHEjCbrQ==", - "dev": true, - "requires": { - "string-width": "^4.2.0", - "strip-ansi": "^6.0.0", - "wrap-ansi": "^6.2.0" - } - }, - "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, - "requires": { - "locate-path": "^5.0.0", - "path-exists": "^4.0.0" - } - }, - "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, - "requires": { - "p-locate": "^4.1.0" - } - }, - "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, - "requires": { - "p-try": "^2.0.0" - } - }, - "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, - "requires": { - "p-limit": "^2.2.0" - } - }, - "p-map": { - "version": "3.0.0", - "resolved": "https://registry.npmjs.org/p-map/-/p-map-3.0.0.tgz", - "integrity": "sha512-d3qXVTF/s+W+CdJ5A29wywV2n8CQQYahlgz2bFiA+4eVNJbHJodPZ+/gXwPGh0bOqA+j8S+6+ckmvLGPk1QpxQ==", - "dev": true, - "requires": { - "aggregate-error": "^3.0.0" - } - }, - "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 - }, - "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 - }, - "wrap-ansi": { - "version": "6.2.0", - "resolved": "https://registry.npmjs.org/wrap-ansi/-/wrap-ansi-6.2.0.tgz", - "integrity": "sha512-r6lPcBGxZXlIcymEu7InxDMhdW0KDxpLgoFLcguasxCaJ/SOIZwINatK9KY/tf+ZrlywOKU0UDj3ATXUBfxJXA==", - "dev": true, - "requires": { - "ansi-styles": "^4.0.0", - "string-width": "^4.1.0", - "strip-ansi": "^6.0.0" - } - }, - "y18n": { - "version": "4.0.3", - "resolved": "https://registry.npmjs.org/y18n/-/y18n-4.0.3.tgz", - "integrity": "sha512-JKhqTOwSrqNA1NY5lSztJ1GrBiUodLMmIZuLiDaMRJ+itFd+ABVE8XBjOvIWL+rSqNDC74LCSFmlb/U4UZ4hJQ==", - "dev": true - }, - "yargs": { - "version": "15.4.1", - "resolved": "https://registry.npmjs.org/yargs/-/yargs-15.4.1.tgz", - "integrity": "sha512-aePbxDmcYW++PaqBsJ+HYUFwCdv4LVvdnhBy78E57PIor8/OVvhMrADFFEDh8DHDFRv/O9i3lPhsENjO7QX0+A==", - "dev": true, - "requires": { - "cliui": "^6.0.0", - "decamelize": "^1.2.0", - "find-up": "^4.1.0", - "get-caller-file": "^2.0.1", - "require-directory": "^2.1.1", - "require-main-filename": "^2.0.0", - "set-blocking": "^2.0.0", - "string-width": "^4.2.0", - "which-module": "^2.0.0", - "y18n": "^4.0.0", - "yargs-parser": "^18.1.2" - } - }, - "yargs-parser": { - "version": "18.1.3", - "resolved": "https://registry.npmjs.org/yargs-parser/-/yargs-parser-18.1.3.tgz", - "integrity": "sha512-o50j0JeToy/4K6OZcaQmW6lyXXKhq7csREXcDwk2omFPJEwUNOVtJKvmDr9EI1fAJZUyZcRF7kxGBWmRXudrCQ==", - "dev": true, - "requires": { - "camelcase": "^5.0.0", - "decamelize": "^1.2.0" - } - } - } - }, - "oauth-sign": { - "version": "0.9.0", - "resolved": "https://registry.npmjs.org/oauth-sign/-/oauth-sign-0.9.0.tgz", - "integrity": "sha512-fexhUFFPTGV8ybAtSIGbV6gOkSv8UtRbDBnAyLQw4QPKkgNlsH2ByPGtMUqdWkos6YCRmAqViwgZrJc/mRDzZQ==" - }, - "object-assign": { - "version": "4.1.1", - "resolved": "https://registry.npmjs.org/object-assign/-/object-assign-4.1.1.tgz", - "integrity": "sha1-IQmtx5ZYh8/AXLvUQsrIv7s2CGM=" - }, - "object-inspect": { - "version": "1.12.0", - "resolved": "https://registry.npmjs.org/object-inspect/-/object-inspect-1.12.0.tgz", - "integrity": "sha512-Ho2z80bVIvJloH+YzRmpZVQe87+qASmBUKZDWgx9cu+KDrX2ZDH/3tMy+gXbZETVGs2M8YdxObOh7XAtim9Y0g==" - }, - "object-keys": { - "version": "1.1.1", - "resolved": "https://registry.npmjs.org/object-keys/-/object-keys-1.1.1.tgz", - "integrity": "sha512-NuAESUOUMrlIXOfHKzD6bpPu3tYt3xvjNdRIQ+FeT0lNb4K8WR70CaDxhuNguS2XG+GjkyMwOzsN5ZktImfhLA==" - }, - "object.assign": { - "version": "4.1.2", - "resolved": "https://registry.npmjs.org/object.assign/-/object.assign-4.1.2.tgz", - "integrity": "sha512-ixT2L5THXsApyiUPYKmW+2EHpXXe5Ii3M+f4e+aJFAHao5amFRW6J0OO6c/LU8Be47utCx2GL89hxGB6XSmKuQ==", - "requires": { - "call-bind": "^1.0.0", - "define-properties": "^1.1.3", - "has-symbols": "^1.0.1", - "object-keys": "^1.1.1" - } - }, - "object.getownpropertydescriptors": { - "version": "2.1.3", - "resolved": "https://registry.npmjs.org/object.getownpropertydescriptors/-/object.getownpropertydescriptors-2.1.3.tgz", - "integrity": "sha512-VdDoCwvJI4QdC6ndjpqFmoL3/+HxffFBbcJzKi5hwLLqqx3mdbedRpfZDdK0SrOSauj8X4GzBvnDZl4vTN7dOw==", - "dev": true, - "requires": { - "call-bind": "^1.0.2", - "define-properties": "^1.1.3", - "es-abstract": "^1.19.1" - } - }, - "object.omit": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/object.omit/-/object.omit-2.0.1.tgz", - "integrity": "sha1-Gpx0SCnznbuFjHbKNXmuKlTr0fo=", - "requires": { - "for-own": "^0.1.4", - "is-extendable": "^0.1.1" - } - }, - "object.values": { - "version": "1.1.5", - "resolved": "https://registry.npmjs.org/object.values/-/object.values-1.1.5.tgz", - "integrity": "sha512-QUZRW0ilQ3PnPpbNtgdNV1PDbEqLIiSFB3l+EnGtBQ/8SUTLj1PZwtQHABZtLgwpJZTSZhuGLOGk57Drx2IvYg==", - "dev": true, - "requires": { - "call-bind": "^1.0.2", - "define-properties": "^1.1.3", - "es-abstract": "^1.19.1" - } - }, - "on-finished": { - "version": "2.3.0", - "resolved": "https://registry.npmjs.org/on-finished/-/on-finished-2.3.0.tgz", - "integrity": "sha1-IPEzZIGwg811M3mSoWlxqi2QaUc=", - "requires": { - "ee-first": "1.1.1" - } - }, - "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==" - }, - "once": { - "version": "1.4.0", - "resolved": "https://registry.npmjs.org/once/-/once-1.4.0.tgz", - "integrity": "sha1-WDsap3WWHUsROsF9nFC6753Xa9E=", - "requires": { - "wrappy": "1" - } - }, - "onetime": { - "version": "5.1.2", - "resolved": "https://registry.npmjs.org/onetime/-/onetime-5.1.2.tgz", - "integrity": "sha512-kbpaSSGJTWdAY5KPVeMOKXSrPtr8C8C7wodJbcsd51jRnmD+GZu8Y0VoU6Dm5Z4vWr0Ig/1NKuWRKf7j5aaYSg==", - "requires": { - "mimic-fn": "^2.1.0" - } - }, - "only": { - "version": "0.0.2", - "resolved": "https://registry.npmjs.org/only/-/only-0.0.2.tgz", - "integrity": "sha1-Kv3oTQPlC5qO3EROMGEKcCle37Q=" - }, - "optionator": { - "version": "0.9.1", - "resolved": "https://registry.npmjs.org/optionator/-/optionator-0.9.1.tgz", - "integrity": "sha512-74RlY5FCnhq4jRxVUPKDaRwrVNXMqsGsiW6AJw4XK8hmtm10wC0ypZBLw5IIp85NZMr91+qd1RvvENwg7jjRFw==", - "dev": true, - "requires": { - "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" - } - }, - "os-homedir": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/os-homedir/-/os-homedir-1.0.2.tgz", - "integrity": "sha1-/7xJiDNuDoM94MFox+8VISGqf7M=" - }, - "os-tmpdir": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/os-tmpdir/-/os-tmpdir-1.0.2.tgz", - "integrity": "sha1-u+Z0BseaqFxc/sdm/lc0VV36EnQ=" - }, - "osenv": { - "version": "0.1.5", - "resolved": "https://registry.npmjs.org/osenv/-/osenv-0.1.5.tgz", - "integrity": "sha512-0CWcCECdMVc2Rw3U5w9ZjqX6ga6ubk1xDVKxtBQPK7wis/0F2r9T6k4ydGYhecl7YUBxBVxhL5oisPsNxAPe2g==", - "dev": true, - "requires": { - "os-homedir": "^1.0.0", - "os-tmpdir": "^1.0.0" - } - }, - "p-cancelable": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/p-cancelable/-/p-cancelable-1.1.0.tgz", - "integrity": "sha512-s73XxOZ4zpt1edZYZzvhqFa6uvQc1vwUa0K0BdtIZgQMAJj9IbebH+JkgKZc9h+B05PKHLOTl4ajG1BmNrVZlw==", - "dev": true - }, - "p-finally": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/p-finally/-/p-finally-1.0.0.tgz", - "integrity": "sha1-P7z7FbiZpEEjs0ttzBi3JDNqLK4=", - "dev": true - }, - "p-limit": { - "version": "1.3.0", - "resolved": "https://registry.npmjs.org/p-limit/-/p-limit-1.3.0.tgz", - "integrity": "sha512-vvcXsLAJ9Dr5rQOPk7toZQZJApBl2K4J6dANSsEuh6QI41JYcsS/qhTGa9ErIUUgK3WNQoJYvylxvjqmiqEA9Q==", - "requires": { - "p-try": "^1.0.0" - } - }, - "p-locate": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/p-locate/-/p-locate-2.0.0.tgz", - "integrity": "sha1-IKAQOyIqcMj9OcwuWAaA893l7EM=", - "requires": { - "p-limit": "^1.1.0" - } - }, - "p-map": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/p-map/-/p-map-4.0.0.tgz", - "integrity": "sha512-/bjOqmgETBYB5BoEeGVea8dmvHb2m9GLy1E9W43yeyfP6QQCZGFNa+XRceJEuDB6zqr+gKpIAmlLebMpykw/MQ==", - "dev": true, - "requires": { - "aggregate-error": "^3.0.0" - } - }, - "p-map-series": { - "version": "2.1.0", - "resolved": "https://registry.npmjs.org/p-map-series/-/p-map-series-2.1.0.tgz", - "integrity": "sha512-RpYIIK1zXSNEOdwxcfe7FdvGcs7+y5n8rifMhMNWvaxRNMPINJHF5GDeuVxWqnfrcHPSCnp7Oo5yNXHId9Av2Q==", - "dev": true - }, - "p-pipe": { - "version": "3.1.0", - "resolved": "https://registry.npmjs.org/p-pipe/-/p-pipe-3.1.0.tgz", - "integrity": "sha512-08pj8ATpzMR0Y80x50yJHn37NF6vjrqHutASaX5LiH5npS9XPvrUmscd9MF5R4fuYRHOxQR1FfMIlF7AzwoPqw==", - "dev": true - }, - "p-queue": { - "version": "6.6.2", - "resolved": "https://registry.npmjs.org/p-queue/-/p-queue-6.6.2.tgz", - "integrity": "sha512-RwFpb72c/BhQLEXIZ5K2e+AhgNVmIejGlTgiB9MzZ0e93GRvqZ7uSi0dvRF7/XIXDeNkra2fNHBxTyPDGySpjQ==", - "dev": true, - "requires": { - "eventemitter3": "^4.0.4", - "p-timeout": "^3.2.0" - } - }, - "p-reduce": { - "version": "2.1.0", - "resolved": "https://registry.npmjs.org/p-reduce/-/p-reduce-2.1.0.tgz", - "integrity": "sha512-2USApvnsutq8uoxZBGbbWM0JIYLiEMJ9RlaN7fAzVNb9OZN0SHjjTTfIcb667XynS5Y1VhwDJVDa72TnPzAYWw==", - "dev": true - }, - "p-timeout": { - "version": "3.2.0", - "resolved": "https://registry.npmjs.org/p-timeout/-/p-timeout-3.2.0.tgz", - "integrity": "sha512-rhIwUycgwwKcP9yTOOFK/AKsAopjjCakVqLHePO3CC6Mir1Z99xT+R63jZxAT5lFZLa2inS5h+ZS2GvR99/FBg==", - "dev": true, - "requires": { - "p-finally": "^1.0.0" - } - }, - "p-try": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/p-try/-/p-try-1.0.0.tgz", - "integrity": "sha1-y8ec26+P1CKOE/Yh8rGiN8GyB7M=" - }, - "p-waterfall": { - "version": "2.1.1", - "resolved": "https://registry.npmjs.org/p-waterfall/-/p-waterfall-2.1.1.tgz", - "integrity": "sha512-RRTnDb2TBG/epPRI2yYXsimO0v3BXC8Yd3ogr1545IaqKK17VGhbWVeGGN+XfCm/08OK8635nH31c8bATkHuSw==", - "dev": true, - "requires": { - "p-reduce": "^2.0.0" - } - }, - "package-hash": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/package-hash/-/package-hash-4.0.0.tgz", - "integrity": "sha512-whdkPIooSu/bASggZ96BWVvZTRMOFxnyUG5PnTSGKoJE2gd5mbVNmR2Nj20QFzxYYgAXpoqC+AiXzl+UMRh7zQ==", - "dev": true, - "requires": { - "graceful-fs": "^4.1.15", - "hasha": "^5.0.0", - "lodash.flattendeep": "^4.4.0", - "release-zalgo": "^1.0.0" - } - }, - "package-json": { - "version": "6.5.0", - "resolved": "https://registry.npmjs.org/package-json/-/package-json-6.5.0.tgz", - "integrity": "sha512-k3bdm2n25tkyxcjSKzB5x8kfVxlMdgsbPr0GkZcwHsLpba6cBjqCt1KlcChKEvxHIcTB1FVMuwoijZ26xex5MQ==", - "dev": true, - "requires": { - "got": "^9.6.0", - "registry-auth-token": "^4.0.0", - "registry-url": "^5.0.0", - "semver": "^6.2.0" - }, - "dependencies": { - "semver": { - "version": "6.3.0", - "resolved": "https://registry.npmjs.org/semver/-/semver-6.3.0.tgz", - "integrity": "sha512-b39TBaTSfV6yBrapU89p5fKekE2m/NwnDocOVruQFS1/veMgdzuPcnOM34M6CwxW8jH/lxEa5rBoDeUwu5HHTw==", - "dev": true - } - } - }, - "pacote": { - "version": "11.3.5", - "resolved": "https://registry.npmjs.org/pacote/-/pacote-11.3.5.tgz", - "integrity": "sha512-fT375Yczn4zi+6Hkk2TBe1x1sP8FgFsEIZ2/iWaXY2r/NkhDJfxbcn5paz1+RTFCyNf+dPnaoBDJoAxXSU8Bkg==", - "dev": true, - "requires": { - "@npmcli/git": "^2.1.0", - "@npmcli/installed-package-contents": "^1.0.6", - "@npmcli/promise-spawn": "^1.2.0", - "@npmcli/run-script": "^1.8.2", - "cacache": "^15.0.5", - "chownr": "^2.0.0", - "fs-minipass": "^2.1.0", - "infer-owner": "^1.0.4", - "minipass": "^3.1.3", - "mkdirp": "^1.0.3", - "npm-package-arg": "^8.0.1", - "npm-packlist": "^2.1.4", - "npm-pick-manifest": "^6.0.0", - "npm-registry-fetch": "^11.0.0", - "promise-retry": "^2.0.1", - "read-package-json-fast": "^2.0.1", - "rimraf": "^3.0.2", - "ssri": "^8.0.1", - "tar": "^6.1.0" - }, - "dependencies": { - "make-fetch-happen": { - "version": "9.1.0", - "resolved": "https://registry.npmjs.org/make-fetch-happen/-/make-fetch-happen-9.1.0.tgz", - "integrity": "sha512-+zopwDy7DNknmwPQplem5lAZX/eCOzSvSNNcSKm5eVwTkOBzoktEfXsa9L23J/GIRhxRsaxzkPEhrJEpE2F4Gg==", - "dev": true, - "requires": { - "agentkeepalive": "^4.1.3", - "cacache": "^15.2.0", - "http-cache-semantics": "^4.1.0", - "http-proxy-agent": "^4.0.1", - "https-proxy-agent": "^5.0.0", - "is-lambda": "^1.0.1", - "lru-cache": "^6.0.0", - "minipass": "^3.1.3", - "minipass-collect": "^1.0.2", - "minipass-fetch": "^1.3.2", - "minipass-flush": "^1.0.5", - "minipass-pipeline": "^1.2.4", - "negotiator": "^0.6.2", - "promise-retry": "^2.0.1", - "socks-proxy-agent": "^6.0.0", - "ssri": "^8.0.0" - } - }, - "npm-registry-fetch": { - "version": "11.0.0", - "resolved": "https://registry.npmjs.org/npm-registry-fetch/-/npm-registry-fetch-11.0.0.tgz", - "integrity": "sha512-jmlgSxoDNuhAtxUIG6pVwwtz840i994dL14FoNVZisrmZW5kWd63IUTNv1m/hyRSGSqWjCUp/YZlS1BJyNp9XA==", - "dev": true, - "requires": { - "make-fetch-happen": "^9.0.1", - "minipass": "^3.1.3", - "minipass-fetch": "^1.3.0", - "minipass-json-stream": "^1.0.1", - "minizlib": "^2.0.0", - "npm-package-arg": "^8.0.0" - } - }, - "socks-proxy-agent": { - "version": "6.1.1", - "resolved": "https://registry.npmjs.org/socks-proxy-agent/-/socks-proxy-agent-6.1.1.tgz", - "integrity": "sha512-t8J0kG3csjA4g6FTbsMOWws+7R7vuRC8aQ/wy3/1OWmsgwA68zs/+cExQ0koSitUDXqhufF/YJr9wtNMZHw5Ew==", - "dev": true, - "requires": { - "agent-base": "^6.0.2", - "debug": "^4.3.1", - "socks": "^2.6.1" - } - } - } - }, - "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, - "requires": { - "callsites": "^3.0.0" - } - }, - "parse-github-url": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/parse-github-url/-/parse-github-url-1.0.2.tgz", - "integrity": "sha512-kgBf6avCbO3Cn6+RnzRGLkUsv4ZVqv/VfAYkRsyBcgkshNvVBkRn1FEZcW0Jb+npXQWm2vHPnnOqFteZxRRGNw==", - "dev": true - }, - "parse-glob": { - "version": "3.0.4", - "resolved": "https://registry.npmjs.org/parse-glob/-/parse-glob-3.0.4.tgz", - "integrity": "sha1-ssN2z7EfNVE7rdFz7wu246OIORw=", - "requires": { - "glob-base": "^0.3.0", - "is-dotfile": "^1.0.0", - "is-extglob": "^1.0.0", - "is-glob": "^2.0.0" - }, - "dependencies": { - "is-extglob": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/is-extglob/-/is-extglob-1.0.0.tgz", - "integrity": "sha1-rEaBd8SUNAWgkvyPKXYMb/xiBsA=" - }, - "is-glob": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/is-glob/-/is-glob-2.0.1.tgz", - "integrity": "sha1-0Jb5JqPe1WAPP9/ZEZjLCIjC2GM=", - "requires": { - "is-extglob": "^1.0.0" - } - } - } - }, - "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, - "requires": { - "@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" - } - }, - "parse-path": { - "version": "4.0.3", - "resolved": "https://registry.npmjs.org/parse-path/-/parse-path-4.0.3.tgz", - "integrity": "sha512-9Cepbp2asKnWTJ9x2kpw6Fe8y9JDbqwahGCTvklzd/cEq5C5JC59x2Xb0Kx+x0QZ8bvNquGO8/BWP0cwBHzSAA==", - "dev": true, - "requires": { - "is-ssh": "^1.3.0", - "protocols": "^1.4.0", - "qs": "^6.9.4", - "query-string": "^6.13.8" - } - }, - "parse-url": { - "version": "6.0.0", - "resolved": "https://registry.npmjs.org/parse-url/-/parse-url-6.0.0.tgz", - "integrity": "sha512-cYyojeX7yIIwuJzledIHeLUBVJ6COVLeT4eF+2P6aKVzwvgKQPndCBv3+yQ7pcWjqToYwaligxzSYNNmGoMAvw==", - "dev": true, - "requires": { - "is-ssh": "^1.3.0", - "normalize-url": "^6.1.0", - "parse-path": "^4.0.0", - "protocols": "^1.4.0" - } - }, - "parseqs": { - "version": "0.0.6", - "resolved": "https://registry.npmjs.org/parseqs/-/parseqs-0.0.6.tgz", - "integrity": "sha512-jeAGzMDbfSHHA091hr0r31eYfTig+29g3GKKE/PPbEQ65X0lmMwlEoqmhzu0iztID5uJpZsFlUPDP8ThPL7M8w==" - }, - "parseuri": { - "version": "0.0.6", - "resolved": "https://registry.npmjs.org/parseuri/-/parseuri-0.0.6.tgz", - "integrity": "sha512-AUjen8sAkGgao7UyCX6Ahv0gIK2fABKmYjvP4xmy5JaKvcbTRueIqIPHLAfq30xJddqSE033IOMUSOMCcK3Sow==" - }, - "parseurl": { - "version": "1.3.3", - "resolved": "https://registry.npmjs.org/parseurl/-/parseurl-1.3.3.tgz", - "integrity": "sha512-CiyeOxFT/JZyN5m0z9PfXw4SCBJ6Sygz1Dpl0wqjlhDEGGBP1GnsUVEL0p63hoG1fcj3fHynXi9NYO4nWOL+qQ==" - }, - "path-browserify": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/path-browserify/-/path-browserify-1.0.0.tgz", - "integrity": "sha512-Hkavx/nY4/plImrZPHRk2CL9vpOymZLgEbMNX1U0bjcBL7QN9wODxyx0yaMZURSQaUtSEvDrfAvxa9oPb0at9g==" - }, - "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==" - }, - "path-is-absolute": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/path-is-absolute/-/path-is-absolute-1.0.1.tgz", - "integrity": "sha1-F0uSaHNVNP+8es5r9TpanhtcX18=" - }, - "path-key": { - "version": "3.1.1", - "resolved": "https://registry.npmjs.org/path-key/-/path-key-3.1.1.tgz", - "integrity": "sha512-ojmeN0qd+y0jszEtoY48r0Peq5dwMEkIlCOu6Q5f41lfkswXuKtYrhgoTpLnyIcHm24Uhqx+5Tqm2InSwLhE6Q==" - }, - "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==" - }, - "path-to-regexp": { - "version": "0.1.7", - "resolved": "https://registry.npmjs.org/path-to-regexp/-/path-to-regexp-0.1.7.tgz", - "integrity": "sha1-32BBeABfUi8V60SQ5yR6G/qmf4w=" - }, - "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 - }, - "pend": { - "version": "1.2.0", - "resolved": "https://registry.npmjs.org/pend/-/pend-1.2.0.tgz", - "integrity": "sha1-elfrVQpng/kRUzH89GY9XI4AelA=" - }, - "performance-now": { - "version": "2.1.0", - "resolved": "https://registry.npmjs.org/performance-now/-/performance-now-2.1.0.tgz", - "integrity": "sha1-Ywn04OX6kT7BxpMHrjZLSzd8nns=", - "dev": true - }, - "picocolors": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/picocolors/-/picocolors-1.0.0.tgz", - "integrity": "sha512-1fygroTLlHu66zi26VoTDv8yRgm0Fccecssto+MhsZ0D/DGW2sm8E8AjW7NU5VVTRt5GxbeZ5qBuJr+HyLYkjQ==" - }, - "picomatch": { - "version": "2.3.1", - "resolved": "https://registry.npmjs.org/picomatch/-/picomatch-2.3.1.tgz", - "integrity": "sha512-JU3teHTNjmE2VCGFzuY8EXzCDVwEqB2a8fsIvwaStHhAWJEeVd1o1QD80CU6+ZdEXXSLbSsuLwJjkCBWqRQUVA==" - }, - "pify": { - "version": "5.0.0", - "resolved": "https://registry.npmjs.org/pify/-/pify-5.0.0.tgz", - "integrity": "sha512-eW/gHNMlxdSP6dmG6uJip6FXN0EQBwm2clYYd8Wul42Cwu/DK8HEftzsapcNdYe2MfLiIwZqsDk2RDEsTE79hA==", - "dev": true - }, - "pinkie": { - "version": "2.0.4", - "resolved": "https://registry.npmjs.org/pinkie/-/pinkie-2.0.4.tgz", - "integrity": "sha1-clVrgM+g1IqXToDnckjoDtT3+HA=" - }, - "pinkie-promise": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/pinkie-promise/-/pinkie-promise-2.0.1.tgz", - "integrity": "sha1-ITXW36ejWMBprJsXh3YogihFD/o=", - "requires": { - "pinkie": "^2.0.0" - } - }, - "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==", - "requires": { - "find-up": "^4.0.0" - }, - "dependencies": { - "find-up": { - "version": "4.1.0", - "resolved": "https://registry.npmjs.org/find-up/-/find-up-4.1.0.tgz", - "integrity": "sha512-PpOwAdQ/YlXQ2vj8a3h8IipDuYRi3wceVQQGYWxNINccq40Anw7BlsEXCMbt1Zt+OLA6Fq9suIpIWD0OsnISlw==", - "requires": { - "locate-path": "^5.0.0", - "path-exists": "^4.0.0" - } - }, - "locate-path": { - "version": "5.0.0", - "resolved": "https://registry.npmjs.org/locate-path/-/locate-path-5.0.0.tgz", - "integrity": "sha512-t7hw9pI+WvuwNJXwk5zVHpyhIqzg2qTlklJOf0mVxGSbe3Fp2VieZcduNYjaLDoy6p9uGpQEGWG87WpMKlNq8g==", - "requires": { - "p-locate": "^4.1.0" - } - }, - "p-limit": { - "version": "2.3.0", - "resolved": "https://registry.npmjs.org/p-limit/-/p-limit-2.3.0.tgz", - "integrity": "sha512-//88mFWSJx8lxCzwdAABTJL2MyWB12+eIY7MDL2SqLmAkeKU9qxRvWuSyTjm3FUmpBEMuFfckAIqEaVGUDxb6w==", - "requires": { - "p-try": "^2.0.0" - } - }, - "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==", - "requires": { - "p-limit": "^2.2.0" - } - }, - "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==" - } - } - }, - "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 - }, - "prepend-http": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/prepend-http/-/prepend-http-2.0.0.tgz", - "integrity": "sha1-6SQ0v6XqjBn0HN/UAddBo8gZ2Jc=", - "dev": true - }, - "preserve": { - "version": "0.2.0", - "resolved": "https://registry.npmjs.org/preserve/-/preserve-0.2.0.tgz", - "integrity": "sha1-gV7R9uvGWSb4ZbMQwHE7yzMVzks=" - }, - "private": { - "version": "0.1.8", - "resolved": "https://registry.npmjs.org/private/-/private-0.1.8.tgz", - "integrity": "sha512-VvivMrbvd2nKkiG38qjULzlc+4Vx4wm/whI9pQD35YrARNnhxeiRktSOhSukRLFNlzg6Br/cJPet5J/u19r/mg==" - }, - "process": { - "version": "0.11.10", - "resolved": "https://registry.npmjs.org/process/-/process-0.11.10.tgz", - "integrity": "sha1-czIwDoQBYb2j5podHZGn1LwW8YI=" - }, - "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==" - }, - "process-on-spawn": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/process-on-spawn/-/process-on-spawn-1.0.0.tgz", - "integrity": "sha512-1WsPDsUSMmZH5LeMLegqkPDrsGgsWwk1Exipy2hvB0o/F0ASzbpIctSCcZIK1ykJvtTJULEH+20WOFjMvGnCTg==", - "dev": true, - "requires": { - "fromentries": "^1.2.0" - } - }, - "progress": { - "version": "2.0.3", - "resolved": "https://registry.npmjs.org/progress/-/progress-2.0.3.tgz", - "integrity": "sha512-7PiHtLll5LdnKIMw100I+8xJXR5gW2QwWYkT6iJva0bXitZKa/XMrSbdmg3r2Xnaidz9Qumd0VPaMrZlF9V9sA==" - }, - "promise-inflight": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/promise-inflight/-/promise-inflight-1.0.1.tgz", - "integrity": "sha1-mEcocL8igTL8vdhoEputEsPAKeM=", - "dev": true - }, - "promise-retry": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/promise-retry/-/promise-retry-2.0.1.tgz", - "integrity": "sha512-y+WKFlBR8BGXnsNlIHFGPZmyDf3DFMoLhaflAnyZgV6rG6xu+JwesTo2Q9R6XwYmtmwAFCkAk3e35jEdoeh/3g==", - "dev": true, - "requires": { - "err-code": "^2.0.2", - "retry": "^0.12.0" - } - }, - "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, - "requires": { - "kleur": "^3.0.3", - "sisteransi": "^1.0.5" - } - }, - "promzard": { - "version": "0.3.0", - "resolved": "https://registry.npmjs.org/promzard/-/promzard-0.3.0.tgz", - "integrity": "sha1-JqXW7ox97kyxIggwWs+5O6OCqe4=", - "dev": true, - "requires": { - "read": "1" - } - }, - "property-handlers": { - "version": "1.1.1", - "resolved": "https://registry.npmjs.org/property-handlers/-/property-handlers-1.1.1.tgz", - "integrity": "sha1-yyDTIqq32U//rCj0bJGGvVlHtLQ=" - }, - "proto-list": { - "version": "1.2.4", - "resolved": "https://registry.npmjs.org/proto-list/-/proto-list-1.2.4.tgz", - "integrity": "sha1-IS1b/hMYMGpCD2QCuOJv85ZHqEk=", - "dev": true - }, - "protocols": { - "version": "1.4.8", - "resolved": "https://registry.npmjs.org/protocols/-/protocols-1.4.8.tgz", - "integrity": "sha512-IgjKyaUSjsROSO8/D49Ab7hP8mJgTYcqApOqdPhLoPxAplXmkp+zRvsrSQjFn5by0rhm4VH0GAUELIPpx7B1yg==", - "dev": true - }, - "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==", - "requires": { - "forwarded": "0.2.0", - "ipaddr.js": "1.9.1" - } - }, - "proxy-from-env": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/proxy-from-env/-/proxy-from-env-1.1.0.tgz", - "integrity": "sha512-D+zkORCbA9f1tdWRK0RaCR3GPv50cMxcrz4X8k5LTSUD1Dkw47mKJEZQNunItRTkWwgtaUSo1RVFRIG9ZXiFYg==" - }, - "psl": { - "version": "1.8.0", - "resolved": "https://registry.npmjs.org/psl/-/psl-1.8.0.tgz", - "integrity": "sha512-RIdOzyoavK+hA18OGGWDqUTsCLhtA7IcZ/6NCs4fFJaHBDab+pDDmDIByWFRQJq2Cd7r1OoQxBGKOaztq+hjIQ==", - "dev": true - }, - "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, - "requires": { - "end-of-stream": "^1.1.0", - "once": "^1.3.1" - } - }, - "punycode": { - "version": "2.1.1", - "resolved": "https://registry.npmjs.org/punycode/-/punycode-2.1.1.tgz", - "integrity": "sha512-XRsRjdf+j5ml+y/6GKHPZbrF/8p2Yga0JPtdqTIY2Xe5ohJPD9saDJJLPvp9+NSBprVvevdXZybnj2cv8OEd0A==" - }, - "pupa": { - "version": "2.1.1", - "resolved": "https://registry.npmjs.org/pupa/-/pupa-2.1.1.tgz", - "integrity": "sha512-l1jNAspIBSFqbT+y+5FosojNpVpF94nlI+wDUpqP9enwOTfHx9f0gh5nB96vl+6yTpsJsypeNrwfzPrKuHB41A==", - "dev": true, - "requires": { - "escape-goat": "^2.0.0" - } - }, - "puppeteer": { - "version": "0.12.0", - "resolved": "https://registry.npmjs.org/puppeteer/-/puppeteer-0.12.0.tgz", - "integrity": "sha512-H/bylN7FccwbN7JZoSP+xRozxgJEDNy4uC4p727cyttKUVNXYjFuEMueJYHW0pblnrfLEH341SyFJVWhJMLxKQ==", - "requires": { - "debug": "^2.6.8", - "extract-zip": "^1.6.5", - "https-proxy-agent": "^2.1.0", - "mime": "^1.3.4", - "progress": "^2.0.0", - "proxy-from-env": "^1.0.0", - "rimraf": "^2.6.1", - "ws": "^3.0.0" - }, - "dependencies": { - "agent-base": { - "version": "4.3.0", - "resolved": "https://registry.npmjs.org/agent-base/-/agent-base-4.3.0.tgz", - "integrity": "sha512-salcGninV0nPrwpGNn4VTXBb1SOuXQBiqbrNXoeizJsHrsL6ERFM2Ne3JUSBWRE6aeNJI2ROP/WEEIDUiDe3cg==", - "requires": { - "es6-promisify": "^5.0.0" - } - }, - "debug": { - "version": "2.6.9", - "resolved": "https://registry.npmjs.org/debug/-/debug-2.6.9.tgz", - "integrity": "sha512-bC7ElrdJaJnPbAP+1EotYvqZsb3ecl5wi6Bfi6BJTUcNowp6cvspg0jXznRTKDjm/E7AdgFBVeAPVMNcKGsHMA==", - "requires": { - "ms": "2.0.0" - } - }, - "https-proxy-agent": { - "version": "2.2.4", - "resolved": "https://registry.npmjs.org/https-proxy-agent/-/https-proxy-agent-2.2.4.tgz", - "integrity": "sha512-OmvfoQ53WLjtA9HeYP9RNrWMJzzAz1JGaSFr1nijg0PVR1JaD/xbJq1mdEIIlxGpXp9eSe/O2LgU9DJmTPd0Eg==", - "requires": { - "agent-base": "^4.3.0", - "debug": "^3.1.0" - }, - "dependencies": { - "debug": { - "version": "3.2.7", - "resolved": "https://registry.npmjs.org/debug/-/debug-3.2.7.tgz", - "integrity": "sha512-CFjzYYAi4ThfiQvizrFQevTTXHtnCqWfe7x1AhgEscTz6ZbLbfoLRLPugTQyBth6f8ZERVUSyWHFD/7Wu4t1XQ==", - "requires": { - "ms": "^2.1.1" - } - }, - "ms": { - "version": "2.1.3", - "resolved": "https://registry.npmjs.org/ms/-/ms-2.1.3.tgz", - "integrity": "sha512-6FlzubTLZG3J2a/NVCAleEhjzq5oxgHyaCU9yYXvcLsvoVaHJq/s5xXI6/XXP6tz7R9xAOtHnSO/tXtF3WRTlA==" - } - } - }, - "ms": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/ms/-/ms-2.0.0.tgz", - "integrity": "sha1-VgiurfwAvmwpAd9fmGF4jeDVl8g=" - }, - "rimraf": { - "version": "2.7.1", - "resolved": "https://registry.npmjs.org/rimraf/-/rimraf-2.7.1.tgz", - "integrity": "sha512-uWjbaKIK3T1OSVptzX7Nl6PvQ3qAGtKEtVRjRuazjfL3Bx5eI409VZSqgND+4UNnmzLVdPj9FqFJNPqBZFve4w==", - "requires": { - "glob": "^7.1.3" - } - } - } - }, - "q": { - "version": "1.5.1", - "resolved": "https://registry.npmjs.org/q/-/q-1.5.1.tgz", - "integrity": "sha1-fjL3W0E4EpHQRhHxvxQQmsAGUdc=" - }, - "qs": { - "version": "6.10.2", - "resolved": "https://registry.npmjs.org/qs/-/qs-6.10.2.tgz", - "integrity": "sha512-mSIdjzqznWgfd4pMii7sHtaYF8rx8861hBO80SraY5GT0XQibWZWJSid0avzHGkDIZLImux2S5mXO0Hfct2QCw==", - "requires": { - "side-channel": "^1.0.4" - } - }, - "query-string": { - "version": "6.14.1", - "resolved": "https://registry.npmjs.org/query-string/-/query-string-6.14.1.tgz", - "integrity": "sha512-XDxAeVmpfu1/6IjyT/gXHOl+S0vQ9owggJ30hhWKdHAsNPOcasn5o9BW0eejZqL2e4vMjhAxoW3jVHcD6mbcYw==", - "dev": true, - "requires": { - "decode-uri-component": "^0.2.0", - "filter-obj": "^1.1.0", - "split-on-first": "^1.0.0", - "strict-uri-encode": "^2.0.0" - } - }, - "querystring": { - "version": "0.2.0", - "resolved": "https://registry.npmjs.org/querystring/-/querystring-0.2.0.tgz", - "integrity": "sha1-sgmEkgO7Jd+CDadW50cAWHhSFiA=" - }, - "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 - }, - "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 - }, - "random-bytes": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/random-bytes/-/random-bytes-1.0.0.tgz", - "integrity": "sha1-T2ih3Arli9P7lYSMMDJNt11kNgs=" - }, - "randomatic": { - "version": "3.1.1", - "resolved": "https://registry.npmjs.org/randomatic/-/randomatic-3.1.1.tgz", - "integrity": "sha512-TuDE5KxZ0J461RVjrJZCJc+J+zCkTb1MbH9AQUq68sMhOMcy9jLcb3BrZKgp9q9Ncltdg4QVqWrH02W2EFFVYw==", - "requires": { - "is-number": "^4.0.0", - "kind-of": "^6.0.0", - "math-random": "^1.0.1" - }, - "dependencies": { - "is-number": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/is-number/-/is-number-4.0.0.tgz", - "integrity": "sha512-rSklcAIlf1OmFdyAqbnWTLVelsQ58uvZ66S/ZyawjWqIviTWCjg2PzVGw8WUA+nNuPTqb4wgA+NszrJ+08LlgQ==" - } - } - }, - "randombytes": { - "version": "2.1.0", - "resolved": "https://registry.npmjs.org/randombytes/-/randombytes-2.1.0.tgz", - "integrity": "sha512-vYl3iOX+4CKUWuxGi9Ukhie6fsqXqS9FE2Zaic4tNFD2N2QQaXOMFbuKK4QmDHC0JO6B1Zp41J0LpT0oR68amQ==", - "requires": { - "safe-buffer": "^5.1.0" - } - }, - "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==" - }, - "raptor-async": { - "version": "1.1.3", - "resolved": "https://registry.npmjs.org/raptor-async/-/raptor-async-1.1.3.tgz", - "integrity": "sha1-uDw8m2A9yYXCw6n3jStAc+b2Akw=" - }, - "raptor-cache": { - "version": "1.2.3", - "resolved": "https://registry.npmjs.org/raptor-cache/-/raptor-cache-1.2.3.tgz", - "integrity": "sha1-woEmegoff6bRpURzEfZ06uYbTDM=", - "requires": { - "dissolve": "^0.3.3", - "mkdirp": "^0.5.0", - "property-handlers": "^1.0.0", - "raptor-async": "^1.0.0", - "raptor-logging": "^1.0.1", - "raptor-util": "^1.0.0", - "through": "^2.3.4", - "uuid": "^3.0.0" - }, - "dependencies": { - "mkdirp": { - "version": "0.5.5", - "resolved": "https://registry.npmjs.org/mkdirp/-/mkdirp-0.5.5.tgz", - "integrity": "sha512-NKmAlESf6jMGym1++R0Ra7wvhV+wFW63FaSOFPwRahvea0gMUcGUhVeAg/0BC0wiv9ih5NYPB1Wn1UEI1/L+xQ==", - "requires": { - "minimist": "^1.2.5" - } - }, - "raptor-util": { - "version": "1.1.2", - "resolved": "https://registry.npmjs.org/raptor-util/-/raptor-util-1.1.2.tgz", - "integrity": "sha1-8u6AdqmuPq4uZWcuRqIgB0+i3/M=" - }, - "uuid": { - "version": "3.4.0", - "resolved": "https://registry.npmjs.org/uuid/-/uuid-3.4.0.tgz", - "integrity": "sha512-HjSDRw6gZE5JMggctHBcjVak08+KEVhSIiDzFnT9S9aegmp85S/bReBVTb4QTFaRNptJ9kuYaNhnbNEOkbKb/A==" - } - } - }, - "raptor-css-parser": { - "version": "1.1.5", - "resolved": "https://registry.npmjs.org/raptor-css-parser/-/raptor-css-parser-1.1.5.tgz", - "integrity": "sha1-HeAY2WEhyNwfHDRoZUmv9xZJ0Dc=", - "requires": { - "raptor-async": "^1.0.0", - "raptor-promises": "^1.0.1" - } - }, - "raptor-detect": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/raptor-detect/-/raptor-detect-1.0.1.tgz", - "integrity": "sha1-ClTGOQVu9m39Ur45RfoizG0UZvM=" - }, - "raptor-logging": { - "version": "1.1.3", - "resolved": "https://registry.npmjs.org/raptor-logging/-/raptor-logging-1.1.3.tgz", - "integrity": "sha512-eklLyQmG5Y2oyIrSsvkFjBkjRYvwjemUQpQhjG757KKaNPxIPX9wu34bfQkIcS7OG495CP28CjX9baABLfOzIw==", - "requires": { - "raptor-polyfill": "^1.0.0", - "raptor-stacktraces": "^1.0.0" - } - }, - "raptor-objects": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/raptor-objects/-/raptor-objects-1.0.2.tgz", - "integrity": "sha1-mQ3ONgQTsHni5K8RTy5zRKcc7hE=", - "requires": { - "raptor-util": "^1.0.0" - }, - "dependencies": { - "raptor-util": { - "version": "1.1.2", - "resolved": "https://registry.npmjs.org/raptor-util/-/raptor-util-1.1.2.tgz", - "integrity": "sha1-8u6AdqmuPq4uZWcuRqIgB0+i3/M=" - } - } - }, - "raptor-polyfill": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/raptor-polyfill/-/raptor-polyfill-1.1.0.tgz", - "integrity": "sha512-VhFc5e6EuNGdax7FQ2QWlCdXFi5OBBsclDh0kzZtgBI7lauc8aFs7+htdi5Q3qCRoYXfsucSBsRKf7a3s+YGmA==" - }, - "raptor-promises": { - "version": "1.0.3", - "resolved": "https://registry.npmjs.org/raptor-promises/-/raptor-promises-1.0.3.tgz", - "integrity": "sha1-1XaxEOBCNlT3/fFyHijULk3DwOs=", - "requires": { - "q": "^1.0.1", - "raptor-util": "^1.0.0" - }, - "dependencies": { - "raptor-util": { - "version": "1.1.2", - "resolved": "https://registry.npmjs.org/raptor-util/-/raptor-util-1.1.2.tgz", - "integrity": "sha1-8u6AdqmuPq4uZWcuRqIgB0+i3/M=" - } - } - }, - "raptor-regexp": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/raptor-regexp/-/raptor-regexp-1.0.1.tgz", - "integrity": "sha1-7PD2bGZxwM2fXkjDcFAmxVCZlcA=" - }, - "raptor-stacktraces": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/raptor-stacktraces/-/raptor-stacktraces-1.0.1.tgz", - "integrity": "sha1-f5+ycafdza4pHGprFd3v+8wAinY=" - }, - "raptor-strings": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/raptor-strings/-/raptor-strings-1.0.2.tgz", - "integrity": "sha1-ks4ssBU6/pBHDYA5oCVbTPM6tfw=", - "requires": { - "raptor-polyfill": "^1.0.1" - } - }, - "raptor-util": { - "version": "3.2.0", - "resolved": "https://registry.npmjs.org/raptor-util/-/raptor-util-3.2.0.tgz", - "integrity": "sha1-I7DIA8jxrIocrmfZpjiLSRYcl1g=" - }, - "raw-body": { - "version": "2.4.2", - "resolved": "https://registry.npmjs.org/raw-body/-/raw-body-2.4.2.tgz", - "integrity": "sha512-RPMAFUJP19WIet/99ngh6Iv8fzAbqum4Li7AD6DtGaW2RpMB/11xDoalPiJMTbu6I3hkbMVkATvZrqb9EEqeeQ==", - "requires": { - "bytes": "3.1.1", - "http-errors": "1.8.1", - "iconv-lite": "0.4.24", - "unpipe": "1.0.0" - } - }, - "rc": { - "version": "1.2.8", - "resolved": "https://registry.npmjs.org/rc/-/rc-1.2.8.tgz", - "integrity": "sha512-y3bGgqKj3QBdxLbLkomlohkvsA8gdAiUQlSBJnBhfn+BPxg4bc62d8TcBW15wavDfgexCgccckhcZvywyQYPOw==", - "dev": true, - "requires": { - "deep-extend": "^0.6.0", - "ini": "~1.3.0", - "minimist": "^1.2.0", - "strip-json-comments": "~2.0.1" - }, - "dependencies": { - "strip-json-comments": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/strip-json-comments/-/strip-json-comments-2.0.1.tgz", - "integrity": "sha1-PFMZQukIwml8DsNEhYwobHygpgo=", - "dev": true - } - } - }, - "rc-config-loader": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/rc-config-loader/-/rc-config-loader-4.0.0.tgz", - "integrity": "sha512-//LRTblJEcqbmmro1GCmZ39qZXD+JqzuD8Y5/IZU3Dhp3A1Yr0Xn68ks8MQ6qKfKvYCWDveUmRDKDA40c+sCXw==", - "dev": true, - "requires": { - "debug": "^4.1.1", - "js-yaml": "^4.0.0", - "json5": "^2.1.2", - "require-from-string": "^2.0.2" - } - }, - "read": { - "version": "1.0.7", - "resolved": "https://registry.npmjs.org/read/-/read-1.0.7.tgz", - "integrity": "sha1-s9oZvQUkMal2cdRKQmNK33ELQMQ=", - "dev": true, - "requires": { - "mute-stream": "~0.0.4" - } - }, - "read-cmd-shim": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/read-cmd-shim/-/read-cmd-shim-2.0.0.tgz", - "integrity": "sha512-HJpV9bQpkl6KwjxlJcBoqu9Ba0PQg8TqSNIOrulGt54a0uup0HtevreFHzYzkm0lpnleRdNBzXznKrgxglEHQw==", - "dev": true - }, - "read-package-json": { - "version": "3.0.1", - "resolved": "https://registry.npmjs.org/read-package-json/-/read-package-json-3.0.1.tgz", - "integrity": "sha512-aLcPqxovhJTVJcsnROuuzQvv6oziQx4zd3JvG0vGCL5MjTONUc4uJ90zCBC6R7W7oUKBNoR/F8pkyfVwlbxqng==", - "dev": true, - "requires": { - "glob": "^7.1.1", - "json-parse-even-better-errors": "^2.3.0", - "normalize-package-data": "^3.0.0", - "npm-normalize-package-bin": "^1.0.0" - } - }, - "read-package-json-fast": { - "version": "2.0.3", - "resolved": "https://registry.npmjs.org/read-package-json-fast/-/read-package-json-fast-2.0.3.tgz", - "integrity": "sha512-W/BKtbL+dUjTuRL2vziuYhp76s5HZ9qQhd/dKfWIZveD0O40453QNyZhC0e63lqZrAQ4jiOapVoeJ7JrszenQQ==", - "dev": true, - "requires": { - "json-parse-even-better-errors": "^2.3.0", - "npm-normalize-package-bin": "^1.0.1" - } - }, - "read-package-tree": { - "version": "5.3.1", - "resolved": "https://registry.npmjs.org/read-package-tree/-/read-package-tree-5.3.1.tgz", - "integrity": "sha512-mLUDsD5JVtlZxjSlPPx1RETkNjjvQYuweKwNVt1Sn8kP5Jh44pvYuUHCp6xSVDZWbNxVxG5lyZJ921aJH61sTw==", - "dev": true, - "requires": { - "read-package-json": "^2.0.0", - "readdir-scoped-modules": "^1.0.0", - "util-promisify": "^2.1.0" - }, - "dependencies": { - "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 - }, - "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, - "requires": { - "hosted-git-info": "^2.1.4", - "resolve": "^1.10.0", - "semver": "2 || 3 || 4 || 5", - "validate-npm-package-license": "^3.0.1" - } - }, - "read-package-json": { - "version": "2.1.2", - "resolved": "https://registry.npmjs.org/read-package-json/-/read-package-json-2.1.2.tgz", - "integrity": "sha512-D1KmuLQr6ZSJS0tW8hf3WGpRlwszJOXZ3E8Yd/DNRaM5d+1wVRZdHlpGBLAuovjr28LbWvjpWkBHMxpRGGjzNA==", - "dev": true, - "requires": { - "glob": "^7.1.1", - "json-parse-even-better-errors": "^2.3.0", - "normalize-package-data": "^2.0.0", - "npm-normalize-package-bin": "^1.0.0" - } - }, - "semver": { - "version": "5.7.1", - "resolved": "https://registry.npmjs.org/semver/-/semver-5.7.1.tgz", - "integrity": "sha512-sauaDf/PZdVgrLTNYHRtpXa1iRiKcaebiKQ1BJdpQlWH2lCvexQdX55snPFyK7QzpudqbCI0qXFfOasHdyNDGQ==", - "dev": true - } - } - }, - "read-pkg": { - "version": "3.0.0", - "resolved": "https://registry.npmjs.org/read-pkg/-/read-pkg-3.0.0.tgz", - "integrity": "sha1-nLxoaXj+5l0WwA4rGcI3/Pbjg4k=", - "dev": true, - "requires": { - "load-json-file": "^4.0.0", - "normalize-package-data": "^2.3.2", - "path-type": "^3.0.0" - }, - "dependencies": { - "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 - }, - "load-json-file": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/load-json-file/-/load-json-file-4.0.0.tgz", - "integrity": "sha1-L19Fq5HjMhYjT9U62rZo607AmTs=", - "dev": true, - "requires": { - "graceful-fs": "^4.1.2", - "parse-json": "^4.0.0", - "pify": "^3.0.0", - "strip-bom": "^3.0.0" - } - }, - "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, - "requires": { - "hosted-git-info": "^2.1.4", - "resolve": "^1.10.0", - "semver": "2 || 3 || 4 || 5", - "validate-npm-package-license": "^3.0.1" - } - }, - "parse-json": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/parse-json/-/parse-json-4.0.0.tgz", - "integrity": "sha1-vjX1Qlvh9/bHRxhPmKeIy5lHfuA=", - "dev": true, - "requires": { - "error-ex": "^1.3.1", - "json-parse-better-errors": "^1.0.1" - } - }, - "path-type": { - "version": "3.0.0", - "resolved": "https://registry.npmjs.org/path-type/-/path-type-3.0.0.tgz", - "integrity": "sha512-T2ZUsdZFHgA3u4e5PfPbjd7HDDpxPnQb5jN0SrDsjNSuVXHJqtwTnWqG0B1jZrgmJ/7lj1EmVIByWt1gxGkWvg==", - "dev": true, - "requires": { - "pify": "^3.0.0" - } - }, - "pify": { - "version": "3.0.0", - "resolved": "https://registry.npmjs.org/pify/-/pify-3.0.0.tgz", - "integrity": "sha1-5aSs0sEB/fPZpNB/DbxNtJ3SgXY=", - "dev": true - }, - "semver": { - "version": "5.7.1", - "resolved": "https://registry.npmjs.org/semver/-/semver-5.7.1.tgz", - "integrity": "sha512-sauaDf/PZdVgrLTNYHRtpXa1iRiKcaebiKQ1BJdpQlWH2lCvexQdX55snPFyK7QzpudqbCI0qXFfOasHdyNDGQ==", - "dev": true - }, - "strip-bom": { - "version": "3.0.0", - "resolved": "https://registry.npmjs.org/strip-bom/-/strip-bom-3.0.0.tgz", - "integrity": "sha1-IzTBjpx1n3vdVv3vfprj1YjmjtM=", - "dev": true - } - } - }, - "read-pkg-up": { - "version": "3.0.0", - "resolved": "https://registry.npmjs.org/read-pkg-up/-/read-pkg-up-3.0.0.tgz", - "integrity": "sha1-PtSWaF26D4/hGNBpHcUfSh/5bwc=", - "dev": true, - "requires": { - "find-up": "^2.0.0", - "read-pkg": "^3.0.0" - } - }, - "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==", - "requires": { - "inherits": "^2.0.3", - "string_decoder": "^1.1.1", - "util-deprecate": "^1.0.1" - } - }, - "readdir-scoped-modules": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/readdir-scoped-modules/-/readdir-scoped-modules-1.1.0.tgz", - "integrity": "sha512-asaikDeqAQg7JifRsZn1NJZXo9E+VwlyCfbkZhwyISinqk5zNS6266HS5kah6P0SaQKGF6SkNnZVHUzHFYxYDw==", - "dev": true, - "requires": { - "debuglog": "^1.0.1", - "dezalgo": "^1.0.0", - "graceful-fs": "^4.1.2", - "once": "^1.3.0" - } - }, - "readdirp": { - "version": "3.6.0", - "resolved": "https://registry.npmjs.org/readdirp/-/readdirp-3.6.0.tgz", - "integrity": "sha512-hOS089on8RduqdbhvQ5Z37A0ESjsqz6qnRcffsMU3495FuTdqSm+7bhJ29JvIOsBDEEnan5DPu9t3To9VRlMzA==", - "requires": { - "picomatch": "^2.2.1" - } - }, - "rechoir": { - "version": "0.6.2", - "resolved": "https://registry.npmjs.org/rechoir/-/rechoir-0.6.2.tgz", - "integrity": "sha1-hSBLVNuoLVdC4oyWdW70OvUOM4Q=", - "requires": { - "resolve": "^1.1.6" - } - }, - "redent": { - "version": "3.0.0", - "resolved": "https://registry.npmjs.org/redent/-/redent-3.0.0.tgz", - "integrity": "sha512-6tDA8g98We0zd0GvVeMT9arEOnTw9qM03L9cJXaCjrip1OO764RDBLBfrB4cwzNGDj5OA5ioymC9GkizgWJDUg==", - "dev": true, - "requires": { - "indent-string": "^4.0.0", - "strip-indent": "^3.0.0" - } - }, - "regenerate": { - "version": "1.4.2", - "resolved": "https://registry.npmjs.org/regenerate/-/regenerate-1.4.2.tgz", - "integrity": "sha512-zrceR/XhGYU/d/opr2EKO7aRHUeiBI8qjtfHqADTwZd6Szfy16la6kqD0MIUs5z5hx6AaKa+PixpPrR289+I0A==" - }, - "regenerate-unicode-properties": { - "version": "9.0.0", - "resolved": "https://registry.npmjs.org/regenerate-unicode-properties/-/regenerate-unicode-properties-9.0.0.tgz", - "integrity": "sha512-3E12UeNSPfjrgwjkR81m5J7Aw/T55Tu7nUyZVQYCKEOs+2dkxEY+DpPtZzO4YruuiPb7NkYLVcyJC4+zCbk5pA==", - "requires": { - "regenerate": "^1.4.2" - } - }, - "regenerator-runtime": { - "version": "0.10.5", - "resolved": "https://registry.npmjs.org/regenerator-runtime/-/regenerator-runtime-0.10.5.tgz", - "integrity": "sha1-M2w+/BIgrc7dosn6tntaeVWjNlg=" - }, - "regenerator-transform": { - "version": "0.14.5", - "resolved": "https://registry.npmjs.org/regenerator-transform/-/regenerator-transform-0.14.5.tgz", - "integrity": "sha512-eOf6vka5IO151Jfsw2NO9WpGX58W6wWmefK3I1zEGr0lOD0u8rwPaNqQL1aRxUaxLeKO3ArNh3VYg1KbaD+FFw==", - "requires": { - "@babel/runtime": "^7.8.4" - } - }, - "regex-cache": { - "version": "0.4.4", - "resolved": "https://registry.npmjs.org/regex-cache/-/regex-cache-0.4.4.tgz", - "integrity": "sha512-nVIZwtCjkC9YgvWkpM55B5rBhBYRZhAaJbgcFYXXsHnbZ9UZI9nnVWYZpBlCqv9ho2eZryPnWrZGsOdPwVWXWQ==", - "requires": { - "is-equal-shallow": "^0.1.3" - } - }, - "regexpp": { - "version": "3.2.0", - "resolved": "https://registry.npmjs.org/regexpp/-/regexpp-3.2.0.tgz", - "integrity": "sha512-pq2bWo9mVD43nbts2wGv17XLiNLya+GklZ8kaDLV2Z08gDCsGpnKn9BFMepvWuHCbyVvY7J5o5+BVvoQbmlJLg==", - "dev": true - }, - "regexpu-core": { - "version": "4.8.0", - "resolved": "https://registry.npmjs.org/regexpu-core/-/regexpu-core-4.8.0.tgz", - "integrity": "sha512-1F6bYsoYiz6is+oz70NWur2Vlh9KWtswuRuzJOfeYUrfPX2o8n74AnUVaOGDbUqVGO9fNHu48/pjJO4sNVwsOg==", - "requires": { - "regenerate": "^1.4.2", - "regenerate-unicode-properties": "^9.0.0", - "regjsgen": "^0.5.2", - "regjsparser": "^0.7.0", - "unicode-match-property-ecmascript": "^2.0.0", - "unicode-match-property-value-ecmascript": "^2.0.0" - } - }, - "registry-auth-token": { - "version": "4.2.1", - "resolved": "https://registry.npmjs.org/registry-auth-token/-/registry-auth-token-4.2.1.tgz", - "integrity": "sha512-6gkSb4U6aWJB4SF2ZvLb76yCBjcvufXBqvvEx1HbmKPkutswjW1xNVRY0+daljIYRbogN7O0etYSlbiaEQyMyw==", - "dev": true, - "requires": { - "rc": "^1.2.8" - } - }, - "registry-url": { - "version": "5.1.0", - "resolved": "https://registry.npmjs.org/registry-url/-/registry-url-5.1.0.tgz", - "integrity": "sha512-8acYXXTI0AkQv6RAOjE3vOaIXZkT9wo4LOFbBKYQEEnnMNBpKqdUrI6S4NT0KPIo/WVvJ5tE/X5LF/TQUf0ekw==", - "dev": true, - "requires": { - "rc": "^1.2.8" - } - }, - "regjsgen": { - "version": "0.5.2", - "resolved": "https://registry.npmjs.org/regjsgen/-/regjsgen-0.5.2.tgz", - "integrity": "sha512-OFFT3MfrH90xIW8OOSyUrk6QHD5E9JOTeGodiJeBS3J6IwlgzJMNE/1bZklWz5oTg+9dCMyEetclvCVXOPoN3A==" - }, - "regjsparser": { - "version": "0.7.0", - "resolved": "https://registry.npmjs.org/regjsparser/-/regjsparser-0.7.0.tgz", - "integrity": "sha512-A4pcaORqmNMDVwUjWoTzuhwMGpP+NykpfqAsEgI1FSH/EzC7lrN5TMd+kN8YCovX+jMpu8eaqXgXPCa0g8FQNQ==", - "requires": { - "jsesc": "~0.5.0" - }, - "dependencies": { - "jsesc": { - "version": "0.5.0", - "resolved": "https://registry.npmjs.org/jsesc/-/jsesc-0.5.0.tgz", - "integrity": "sha1-597mbjXW/Bb3EP6R1c9p9w8IkR0=" - } - } - }, - "release-zalgo": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/release-zalgo/-/release-zalgo-1.0.0.tgz", - "integrity": "sha1-CXALflB0Mpc5Mw5TXFqQ+2eFFzA=", - "dev": true, - "requires": { - "es6-error": "^4.0.1" - } - }, - "remote-git-tags": { - "version": "3.0.0", - "resolved": "https://registry.npmjs.org/remote-git-tags/-/remote-git-tags-3.0.0.tgz", - "integrity": "sha512-C9hAO4eoEsX+OXA4rla66pXZQ+TLQ8T9dttgQj18yuKlPMTVkIkdYXvlMC55IuUsIkV6DpmQYi10JKFLaU+l7w==", - "dev": true - }, - "remove-trailing-separator": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/remove-trailing-separator/-/remove-trailing-separator-1.1.0.tgz", - "integrity": "sha1-wkvOKig62tW8P1jg1IJJuSN52O8=" - }, - "repeat-element": { - "version": "1.1.4", - "resolved": "https://registry.npmjs.org/repeat-element/-/repeat-element-1.1.4.tgz", - "integrity": "sha512-LFiNfRcSu7KK3evMyYOuCzv3L10TW7yC1G2/+StMjK8Y6Vqd2MG7r/Qjw4ghtuCOjFvlnms/iMmLqpvW/ES/WQ==" - }, - "repeat-string": { - "version": "1.6.1", - "resolved": "https://registry.npmjs.org/repeat-string/-/repeat-string-1.6.1.tgz", - "integrity": "sha1-jcrkcOHIirwtYA//Sndihtp15jc=" - }, - "repeating": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/repeating/-/repeating-2.0.1.tgz", - "integrity": "sha1-UhTFOpJtNVJwdSf7q0FdvAjQbdo=", - "requires": { - "is-finite": "^1.0.0" - } - }, - "request": { - "version": "2.88.2", - "resolved": "https://registry.npmjs.org/request/-/request-2.88.2.tgz", - "integrity": "sha512-MsvtOrfG9ZcrOwAW+Qi+F6HbD0CWXEh9ou77uOb7FM2WPhwT7smM833PzanhJLsgXjN89Ir6V2PczXNnMpwKhw==", - "dev": true, - "requires": { - "aws-sign2": "~0.7.0", - "aws4": "^1.8.0", - "caseless": "~0.12.0", - "combined-stream": "~1.0.6", - "extend": "~3.0.2", - "forever-agent": "~0.6.1", - "form-data": "~2.3.2", - "har-validator": "~5.1.3", - "http-signature": "~1.2.0", - "is-typedarray": "~1.0.0", - "isstream": "~0.1.2", - "json-stringify-safe": "~5.0.1", - "mime-types": "~2.1.19", - "oauth-sign": "~0.9.0", - "performance-now": "^2.1.0", - "qs": "~6.5.2", - "safe-buffer": "^5.1.2", - "tough-cookie": "~2.5.0", - "tunnel-agent": "^0.6.0", - "uuid": "^3.3.2" - }, - "dependencies": { - "qs": { - "version": "6.5.2", - "resolved": "https://registry.npmjs.org/qs/-/qs-6.5.2.tgz", - "integrity": "sha512-N5ZAX4/LxJmF+7wN74pUD6qAh9/wnvdQcjq9TZjevvXzSUo7bfmw91saqMjzGS2xq91/odN2dW/WOl7qQHNDGA==", - "dev": true - }, - "uuid": { - "version": "3.4.0", - "resolved": "https://registry.npmjs.org/uuid/-/uuid-3.4.0.tgz", - "integrity": "sha512-HjSDRw6gZE5JMggctHBcjVak08+KEVhSIiDzFnT9S9aegmp85S/bReBVTb4QTFaRNptJ9kuYaNhnbNEOkbKb/A==", - "dev": true - } - } - }, - "request-compose": { - "version": "2.1.4", - "resolved": "https://registry.npmjs.org/request-compose/-/request-compose-2.1.4.tgz", - "integrity": "sha512-F8xik9Dxd5i2aHZ0/L/oIrCM1kKSgvp9BKYxGXk91lSWF9TbicWpnuxdOchxIhEWwvLdSBWZIAbCOeXfGfqaqA==" - }, - "request-oauth": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/request-oauth/-/request-oauth-1.0.1.tgz", - "integrity": "sha512-85THTg1RgOYtqQw42JON6AqvHLptlj1biw265Tsq4fD4cPdUvhDB2Qh9NTv17yCD322ROuO9aOmpc4GyayGVBA==", - "requires": { - "oauth-sign": "^0.9.0", - "qs": "^6.9.6", - "uuid": "^8.3.2" - } - }, - "require-directory": { - "version": "2.1.1", - "resolved": "https://registry.npmjs.org/require-directory/-/require-directory-2.1.1.tgz", - "integrity": "sha1-jGStX9MNqxyXbiNE/+f3kqam30I=" - }, - "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==" - }, - "require-main-filename": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/require-main-filename/-/require-main-filename-2.0.0.tgz", - "integrity": "sha512-NKN5kMDylKuldxYLSUfrbo5Tuzh4hd+2E8NPPX02mZtn1VuREQToYe/ZdlJy+J3uCpfaiGF05e7B8W0iXbQHmg==", - "dev": true - }, - "resolve": { - "version": "1.21.0", - "resolved": "https://registry.npmjs.org/resolve/-/resolve-1.21.0.tgz", - "integrity": "sha512-3wCbTpk5WJlyE4mSOtDLhqQmGFi0/TD9VPwmiolnk8U0wRgMEktqCXd3vy5buTO3tljvalNvKrjHEfrd2WpEKA==", - "requires": { - "is-core-module": "^2.8.0", - "path-parse": "^1.0.7", - "supports-preserve-symlinks-flag": "^1.0.0" - } - }, - "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==", - "requires": { - "resolve-from": "^5.0.0" - }, - "dependencies": { - "resolve-from": { - "version": "5.0.0", - "resolved": "https://registry.npmjs.org/resolve-from/-/resolve-from-5.0.0.tgz", - "integrity": "sha512-qYg9KP24dD5qka9J47d0aVky0N+b4fTU89LN9iDnjB5waksiC49rvMB0PrUJQGoTmH50XPiqOvAjDfaijGxYZw==" - } - } - }, - "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==" - }, - "responselike": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/responselike/-/responselike-1.0.2.tgz", - "integrity": "sha1-kYcg7ztjHFZCvgaPFa3lpG9Loec=", - "dev": true, - "requires": { - "lowercase-keys": "^1.0.0" - } - }, - "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, - "requires": { - "onetime": "^5.1.0", - "signal-exit": "^3.0.2" - } - }, - "retry": { - "version": "0.12.0", - "resolved": "https://registry.npmjs.org/retry/-/retry-0.12.0.tgz", - "integrity": "sha1-G0KmJmoh8HQh0bC1S33BZ7AcATs=", - "dev": true - }, - "reusify": { - "version": "1.0.4", - "resolved": "https://registry.npmjs.org/reusify/-/reusify-1.0.4.tgz", - "integrity": "sha512-U9nH88a3fc/ekCF1l0/UP1IosiuIjyTh7hBvXVMHYgVcfGvt897Xguj2UOLDeI5BG2m7/uwyaLVT6fbtCwTyzw==", - "dev": true - }, - "right-align": { - "version": "0.1.3", - "resolved": "https://registry.npmjs.org/right-align/-/right-align-0.1.3.tgz", - "integrity": "sha1-YTObci/mo1FWiSENJOFMlhSGE+8=", - "requires": { - "align-text": "^0.1.1" - } - }, - "rimraf": { - "version": "3.0.2", - "resolved": "https://registry.npmjs.org/rimraf/-/rimraf-3.0.2.tgz", - "integrity": "sha512-JZkJMZkAGFFPP2YqXZXPbMlMBgsxzE8ILs4lMIX/2o0L9UBw9O/Y3o6wFw/i9YLapcUJWwqbi3kdxIPdC62TIA==", - "dev": true, - "requires": { - "glob": "^7.1.3" - } - }, - "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 - }, - "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, - "requires": { - "queue-microtask": "^1.2.2" - } - }, - "rusha": { - "version": "0.8.14", - "resolved": "https://registry.npmjs.org/rusha/-/rusha-0.8.14.tgz", - "integrity": "sha512-cLgakCUf6PedEu15t8kbsjnwIFFR2D4RfL+W3iWFJ4iac7z4B0ZI8fxy4R3J956kAI68HclCFGL8MPoUVC3qVA==" - }, - "rxjs": { - "version": "7.5.1", - "resolved": "https://registry.npmjs.org/rxjs/-/rxjs-7.5.1.tgz", - "integrity": "sha512-KExVEeZWxMZnZhUZtsJcFwz8IvPvgu4G2Z2QyqjZQzUGr32KDYuSxrEYO4w3tFFNbfLozcrKUTvTPi+E9ywJkQ==", - "requires": { - "tslib": "^2.1.0" - }, - "dependencies": { - "tslib": { - "version": "2.3.1", - "resolved": "https://registry.npmjs.org/tslib/-/tslib-2.3.1.tgz", - "integrity": "sha512-77EbyPPpMz+FRFRuAFlWMtmgUWGe9UOG2Z25NqCwiIjRhOf5iKGuzSe5P2w1laq+FkRy4p+PCuVkJSGkzTEKVw==" - } - } - }, - "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==" - }, - "safer-buffer": { - "version": "2.1.2", - "resolved": "https://registry.npmjs.org/safer-buffer/-/safer-buffer-2.1.2.tgz", - "integrity": "sha512-YZo3K82SD7Riyi0E1EQPojLz7kpepnSQI9IyPbHHg1XXXevb5dJI7tpyN2ADxGcQbHG7vcyRHk0cbwqcQriUtg==" - }, - "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, - "requires": { - "sparse-bitfield": "^3.0.3" - } - }, - "schema-utils": { - "version": "2.7.1", - "resolved": "https://registry.npmjs.org/schema-utils/-/schema-utils-2.7.1.tgz", - "integrity": "sha512-SHiNtMOUGWBQJwzISiVYKu82GiV4QYGePp3odlY1tuKO7gPtphAT5R/py0fA6xtbgLL/RvtJZnU9b8s0F1q0Xg==", - "requires": { - "@types/json-schema": "^7.0.5", - "ajv": "^6.12.4", - "ajv-keywords": "^3.5.2" - }, - "dependencies": { - "ajv": { - "version": "6.12.6", - "resolved": "https://registry.npmjs.org/ajv/-/ajv-6.12.6.tgz", - "integrity": "sha512-j3fVLgvTo527anyYyJOGTYJbG+vnnQYvE0m5mmkc1TK+nxAppkCLMIL0aZ4dblVCNoGShhm+kzE4ZUykBoMg4g==", - "requires": { - "fast-deep-equal": "^3.1.1", - "fast-json-stable-stringify": "^2.0.0", - "json-schema-traverse": "^0.4.1", - "uri-js": "^4.2.2" - } - }, - "ajv-keywords": { - "version": "3.5.2", - "resolved": "https://registry.npmjs.org/ajv-keywords/-/ajv-keywords-3.5.2.tgz", - "integrity": "sha512-5p6WTN0DdTGVQk6VjcEju19IgaHudalcfabD7yhDGeA6bcQnmL+CpveLJq/3hvfwd1aof6L386Ougkx6RfyMIQ==", - "requires": {} - }, - "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==" - } - } - }, - "self-closing-tags": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/self-closing-tags/-/self-closing-tags-1.0.1.tgz", - "integrity": "sha512-7t6hNbYMxM+VHXTgJmxwgZgLGktuXtVVD5AivWzNTdJBM4DBjnDKDzkf2SrNjihaArpeJYNjxkELBu1evI4lQA==" - }, - "semver": { - "version": "7.3.5", - "resolved": "https://registry.npmjs.org/semver/-/semver-7.3.5.tgz", - "integrity": "sha512-PoeGJYh8HK4BTO/a9Tf6ZG3veo/A7ZVsYrSA6J8ny9nb3B1VrpkuN+z9OE5wfE5p6H4LchYZsegiQgbJD94ZFQ==", - "requires": { - "lru-cache": "^6.0.0" - } - }, - "semver-diff": { - "version": "3.1.1", - "resolved": "https://registry.npmjs.org/semver-diff/-/semver-diff-3.1.1.tgz", - "integrity": "sha512-GX0Ix/CJcHyB8c4ykpHGIAvLyOwOobtM/8d+TQkAd81/bEjgPHrfba41Vpesr7jX/t8Uh+R3EX9eAS5be+jQYg==", - "dev": true, - "requires": { - "semver": "^6.3.0" - }, - "dependencies": { - "semver": { - "version": "6.3.0", - "resolved": "https://registry.npmjs.org/semver/-/semver-6.3.0.tgz", - "integrity": "sha512-b39TBaTSfV6yBrapU89p5fKekE2m/NwnDocOVruQFS1/veMgdzuPcnOM34M6CwxW8jH/lxEa5rBoDeUwu5HHTw==", - "dev": true - } - } - }, - "semver-utils": { - "version": "1.1.4", - "resolved": "https://registry.npmjs.org/semver-utils/-/semver-utils-1.1.4.tgz", - "integrity": "sha512-EjnoLE5OGmDAVV/8YDoN5KiajNadjzIp9BAHOhYeQHt7j0UWxjmgsx4YD48wp4Ue1Qogq38F1GNUJNqF1kKKxA==", - "dev": true - }, - "send": { - "version": "0.17.2", - "resolved": "https://registry.npmjs.org/send/-/send-0.17.2.tgz", - "integrity": "sha512-UJYB6wFSJE3G00nEivR5rgWp8c2xXvJ3OPWPhmuteU0IKj8nKbG3DrjiOmLwpnHGYWAVwA69zmTm++YG0Hmwww==", - "requires": { - "debug": "2.6.9", - "depd": "~1.1.2", - "destroy": "~1.0.4", - "encodeurl": "~1.0.2", - "escape-html": "~1.0.3", - "etag": "~1.8.1", - "fresh": "0.5.2", - "http-errors": "1.8.1", - "mime": "1.6.0", - "ms": "2.1.3", - "on-finished": "~2.3.0", - "range-parser": "~1.2.1", - "statuses": "~1.5.0" - }, - "dependencies": { - "debug": { - "version": "2.6.9", - "resolved": "https://registry.npmjs.org/debug/-/debug-2.6.9.tgz", - "integrity": "sha512-bC7ElrdJaJnPbAP+1EotYvqZsb3ecl5wi6Bfi6BJTUcNowp6cvspg0jXznRTKDjm/E7AdgFBVeAPVMNcKGsHMA==", - "requires": { - "ms": "2.0.0" - }, - "dependencies": { - "ms": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/ms/-/ms-2.0.0.tgz", - "integrity": "sha1-VgiurfwAvmwpAd9fmGF4jeDVl8g=" - } - } - }, - "ms": { - "version": "2.1.3", - "resolved": "https://registry.npmjs.org/ms/-/ms-2.1.3.tgz", - "integrity": "sha512-6FlzubTLZG3J2a/NVCAleEhjzq5oxgHyaCU9yYXvcLsvoVaHJq/s5xXI6/XXP6tz7R9xAOtHnSO/tXtF3WRTlA==" - } - } - }, - "serialize-javascript": { - "version": "6.0.0", - "resolved": "https://registry.npmjs.org/serialize-javascript/-/serialize-javascript-6.0.0.tgz", - "integrity": "sha512-Qr3TosvguFt8ePWqsvRfrKyQXIiW+nGbYpy8XK24NQHE83caxWt+mIymTT19DGFbNWNLfEwsrkSmN64lVWB9ag==", - "requires": { - "randombytes": "^2.1.0" - } - }, - "serve-static": { - "version": "1.14.2", - "resolved": "https://registry.npmjs.org/serve-static/-/serve-static-1.14.2.tgz", - "integrity": "sha512-+TMNA9AFxUEGuC0z2mevogSnn9MXKb4fa7ngeRMJaaGv8vTwnIEkKi+QGvPt33HSnf8pRS+WGM0EbMtCJLKMBQ==", - "requires": { - "encodeurl": "~1.0.2", - "escape-html": "~1.0.3", - "parseurl": "~1.3.3", - "send": "0.17.2" - } - }, - "set-blocking": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/set-blocking/-/set-blocking-2.0.0.tgz", - "integrity": "sha1-BF+XgtARrppoA93TgrJDkrPYkPc=", - "dev": true - }, - "setprototypeof": { - "version": "1.2.0", - "resolved": "https://registry.npmjs.org/setprototypeof/-/setprototypeof-1.2.0.tgz", - "integrity": "sha512-E5LDX7Wrp85Kil5bhZv46j8jOeboKq5JMmYM3gVGdGH8xFpPWXUMsNrlODCrkoxMEeNi/XZIwuRvY4XNwYMJpw==" - }, - "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==", - "requires": { - "kind-of": "^6.0.2" - } - }, - "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==", - "requires": { - "shebang-regex": "^3.0.0" - } - }, - "shebang-regex": { - "version": "3.0.0", - "resolved": "https://registry.npmjs.org/shebang-regex/-/shebang-regex-3.0.0.tgz", - "integrity": "sha512-7++dFhtcx3353uBaq8DDR4NuxBetBzC7ZQOhmTQInHEd6bSrXdiEyzCvG07Z44UYdLShWUyXt5M/yhz8ekcb1A==" - }, - "shelljs": { - "version": "0.8.4", - "resolved": "https://registry.npmjs.org/shelljs/-/shelljs-0.8.4.tgz", - "integrity": "sha512-7gk3UZ9kOfPLIAbslLzyWeGiEqx9e3rxwZM0KE6EL8GlGwjym9Mrlx5/p33bWTu9YG6vcS4MBxYZDHYr5lr8BQ==", - "requires": { - "glob": "^7.0.0", - "interpret": "^1.0.0", - "rechoir": "^0.6.2" - } - }, - "shx": { - "version": "0.3.3", - "resolved": "https://registry.npmjs.org/shx/-/shx-0.3.3.tgz", - "integrity": "sha512-nZJ3HFWVoTSyyB+evEKjJ1STiixGztlqwKLTUNV5KqMWtGey9fTd4KU1gdZ1X9BV6215pswQ/Jew9NsuS/fNDA==", - "requires": { - "minimist": "^1.2.3", - "shelljs": "^0.8.4" - } - }, - "side-channel": { - "version": "1.0.4", - "resolved": "https://registry.npmjs.org/side-channel/-/side-channel-1.0.4.tgz", - "integrity": "sha512-q5XPytqFEIKHkGdiMIrY10mvLRvnQh42/+GoBlFW3b2LXLE2xxJpZFdm94we0BaoV3RwJyGqg5wS7epxTv0Zvw==", - "requires": { - "call-bind": "^1.0.0", - "get-intrinsic": "^1.0.2", - "object-inspect": "^1.9.0" - } - }, - "sift": { - "version": "15.1.3", - "resolved": "https://registry.npmjs.org/sift/-/sift-15.1.3.tgz", - "integrity": "sha512-/JZRQtE1pe4t93jKvAKDCgpOSfFX/tFNoYn5hUB4nuVyihGFp5pS5mQu6p7XOo0oQvj+jrgVyIteAI6lO+EE8A==" - }, - "signal-exit": { - "version": "3.0.6", - "resolved": "https://registry.npmjs.org/signal-exit/-/signal-exit-3.0.6.tgz", - "integrity": "sha512-sDl4qMFpijcGw22U5w63KmD3cZJfBuFlVNbVMKje2keoKML7X2UzWbc4XrmEbDwg0NXJc3yv4/ox7b+JWb57kQ==" - }, - "simple-sha1": { - "version": "2.1.2", - "resolved": "https://registry.npmjs.org/simple-sha1/-/simple-sha1-2.1.2.tgz", - "integrity": "sha512-TQl9rm4rdKAVmhO++sXAb8TNN0D6JAD5iyI1mqEPNpxUzTRrtm4aOG1pDf/5W/qCFihiaoK6uuL9rvQz1x1VKw==", - "requires": { - "rusha": "^0.8.1" - } - }, - "sisteransi": { - "version": "1.0.5", - "resolved": "https://registry.npmjs.org/sisteransi/-/sisteransi-1.0.5.tgz", - "integrity": "sha512-bLGGlR1QxBcynn2d5YmDX4MGjlZvy2MRBDRNHLJ8VI6l6+9FUiyTFNJ0IveOSP0bcXgVDPRcfGqA0pjaqUpfVg==", - "dev": true - }, - "slash": { - "version": "3.0.0", - "resolved": "https://registry.npmjs.org/slash/-/slash-3.0.0.tgz", - "integrity": "sha512-g9Q1haeby36OSStwb4ntCGGGaKsaVSjQ68fBxoQcutl5fS1vuY18H3wSt3jFyFtrkx+Kz0V1G85A4MyAdDMi2Q==", - "dev": true - }, - "slide": { - "version": "1.1.6", - "resolved": "https://registry.npmjs.org/slide/-/slide-1.1.6.tgz", - "integrity": "sha1-VusCfWW00tzmyy4tMsTUr8nh1wc=", - "dev": true - }, - "smart-buffer": { - "version": "4.2.0", - "resolved": "https://registry.npmjs.org/smart-buffer/-/smart-buffer-4.2.0.tgz", - "integrity": "sha512-94hK0Hh8rPqQl2xXc3HsaBoOXKV20MToPkcXvwbISWLEs+64sBq5kFgn2kJDHb1Pry9yrP0dxrCI9RRci7RXKg==", - "dev": true - }, - "socket.io": { - "version": "4.4.0", - "resolved": "https://registry.npmjs.org/socket.io/-/socket.io-4.4.0.tgz", - "integrity": "sha512-bnpJxswR9ov0Bw6ilhCvO38/1WPtE3eA2dtxi2Iq4/sFebiDJQzgKNYA7AuVVdGW09nrESXd90NbZqtDd9dzRQ==", - "requires": { - "accepts": "~1.3.4", - "base64id": "~2.0.0", - "debug": "~4.3.2", - "engine.io": "~6.1.0", - "socket.io-adapter": "~2.3.3", - "socket.io-parser": "~4.0.4" - } - }, - "socket.io-adapter": { - "version": "2.3.3", - "resolved": "https://registry.npmjs.org/socket.io-adapter/-/socket.io-adapter-2.3.3.tgz", - "integrity": "sha512-Qd/iwn3VskrpNO60BeRyCyr8ZWw9CPZyitW4AQwmRZ8zCiyDiL+znRnWX6tDHXnWn1sJrM1+b6Mn6wEDJJ4aYQ==" - }, - "socket.io-client": { - "version": "4.4.0", - "resolved": "https://registry.npmjs.org/socket.io-client/-/socket.io-client-4.4.0.tgz", - "integrity": "sha512-g7riSEJXi7qCFImPow98oT8X++MSsHz6MMFRXkWNJ6uEROSHOa3kxdrsYWMq85dO+09CFMkcqlpjvbVXQl4z6g==", - "requires": { - "@socket.io/component-emitter": "~3.0.0", - "backo2": "~1.0.2", - "debug": "~4.3.2", - "engine.io-client": "~6.1.1", - "parseuri": "0.0.6", - "socket.io-parser": "~4.1.1" - }, - "dependencies": { - "socket.io-parser": { - "version": "4.1.1", - "resolved": "https://registry.npmjs.org/socket.io-parser/-/socket.io-parser-4.1.1.tgz", - "integrity": "sha512-USQVLSkDWE5nbcY760ExdKaJxCE65kcsG/8k5FDGZVVxpD1pA7hABYXYkCUvxUuYYh/+uQw0N/fvBzfT8o07KA==", - "requires": { - "@socket.io/component-emitter": "~3.0.0", - "debug": "~4.3.1" - } - } - } - }, - "socket.io-parser": { - "version": "4.0.4", - "resolved": "https://registry.npmjs.org/socket.io-parser/-/socket.io-parser-4.0.4.tgz", - "integrity": "sha512-t+b0SS+IxG7Rxzda2EVvyBZbvFPBCjJoyHuE0P//7OAsN23GItzDRdWa6ALxZI/8R5ygK7jAR6t028/z+7295g==", - "requires": { - "@types/component-emitter": "^1.2.10", - "component-emitter": "~1.3.0", - "debug": "~4.3.1" - } - }, - "socks": { - "version": "2.6.1", - "resolved": "https://registry.npmjs.org/socks/-/socks-2.6.1.tgz", - "integrity": "sha512-kLQ9N5ucj8uIcxrDwjm0Jsqk06xdpBjGNQtpXy4Q8/QY2k+fY7nZH8CARy+hkbG+SGAovmzzuauCpBlb8FrnBA==", - "dev": true, - "requires": { - "ip": "^1.1.5", - "smart-buffer": "^4.1.0" - } - }, - "socks-proxy-agent": { - "version": "5.0.1", - "resolved": "https://registry.npmjs.org/socks-proxy-agent/-/socks-proxy-agent-5.0.1.tgz", - "integrity": "sha512-vZdmnjb9a2Tz6WEQVIurybSwElwPxMZaIc7PzqbJTrezcKNznv6giT7J7tZDZ1BojVaa1jvO/UiUdhDVB0ACoQ==", - "dev": true, - "requires": { - "agent-base": "^6.0.2", - "debug": "4", - "socks": "^2.3.3" - } - }, - "sort-keys": { - "version": "4.2.0", - "resolved": "https://registry.npmjs.org/sort-keys/-/sort-keys-4.2.0.tgz", - "integrity": "sha512-aUYIEU/UviqPgc8mHR6IW1EGxkAXpeRETYcrzg8cLAvUPZcpAlleSXHV2mY7G12GphSH6Gzv+4MMVSSkbdteHg==", - "dev": true, - "requires": { - "is-plain-obj": "^2.0.0" - }, - "dependencies": { - "is-plain-obj": { - "version": "2.1.0", - "resolved": "https://registry.npmjs.org/is-plain-obj/-/is-plain-obj-2.1.0.tgz", - "integrity": "sha512-YWnfyRwxL/+SsrWYfOpUtz5b3YD+nyfkHvjbcanzk8zgyO4ASD67uVMRt8k5bM4lLMDnXfriRhOpemw+NfT1eA==", - "dev": true - } - } - }, - "source-map": { - "version": "0.6.1", - "resolved": "https://registry.npmjs.org/source-map/-/source-map-0.6.1.tgz", - "integrity": "sha512-UjgapumWlbMhkBgzT7Ykc5YXUT46F0iKu8SGXq0bcwP5dz/h0Plj6enJqjz1Zbq2l5WaqYnrVbwWOWMyF3F47g==" - }, - "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==", - "requires": { - "buffer-from": "^1.0.0", - "source-map": "^0.6.0" - } - }, - "sparse-bitfield": { - "version": "3.0.3", - "resolved": "https://registry.npmjs.org/sparse-bitfield/-/sparse-bitfield-3.0.3.tgz", - "integrity": "sha1-/0rm5oZWBWuks+eSqzM004JzyhE=", - "optional": true, - "requires": { - "memory-pager": "^1.0.2" - } - }, - "spawn-please": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/spawn-please/-/spawn-please-1.0.0.tgz", - "integrity": "sha512-Kz33ip6NRNKuyTRo3aDWyWxeGeM0ORDO552Fs6E1nj4pLWPkl37SrRtTnq+MEopVaqgmaO6bAvVS+v64BJ5M/A==", - "dev": true - }, - "spawn-wrap": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/spawn-wrap/-/spawn-wrap-2.0.0.tgz", - "integrity": "sha512-EeajNjfN9zMnULLwhZZQU3GWBoFNkbngTUPfaawT4RkMiviTxcX0qfhVbGey39mfctfDHkWtuecgQ8NJcyQWHg==", - "dev": true, - "requires": { - "foreground-child": "^2.0.0", - "is-windows": "^1.0.2", - "make-dir": "^3.0.0", - "rimraf": "^3.0.0", - "signal-exit": "^3.0.2", - "which": "^2.0.1" - } - }, - "spdx-correct": { - "version": "3.1.1", - "resolved": "https://registry.npmjs.org/spdx-correct/-/spdx-correct-3.1.1.tgz", - "integrity": "sha512-cOYcUWwhCuHCXi49RhFRCyJEK3iPj1Ziz9DpViV3tbZOwXD49QzIN3MpOLJNxh2qwq2lJJZaKMVw9qNi4jTC0w==", - "requires": { - "spdx-expression-parse": "^3.0.0", - "spdx-license-ids": "^3.0.0" - } - }, - "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==" - }, - "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==", - "requires": { - "spdx-exceptions": "^2.1.0", - "spdx-license-ids": "^3.0.0" - } - }, - "spdx-license-ids": { - "version": "3.0.11", - "resolved": "https://registry.npmjs.org/spdx-license-ids/-/spdx-license-ids-3.0.11.tgz", - "integrity": "sha512-Ctl2BrFiM0X3MANYgj3CkygxhRmr9mi6xhejbdO960nF6EDJApTYpn0BQnDKlnNBULKiCN1n3w9EBkHK8ZWg+g==" - }, - "split": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/split/-/split-1.0.1.tgz", - "integrity": "sha512-mTyOoPbrivtXnwnIxZRFYRrPNtEFKlpB2fvjSnCQUiAA6qAZzqwna5envK4uk6OIeP17CsdF3rSBGYVBsU0Tkg==", - "dev": true, - "requires": { - "through": "2" - } - }, - "split-on-first": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/split-on-first/-/split-on-first-1.1.0.tgz", - "integrity": "sha512-43ZssAJaMusuKWL8sKUBQXHWOpq8d6CfN/u1p4gUzfJkM05C8rxTmYrkIPTXapZpORA6LkkzcUulJ8FqA7Uudw==", - "dev": true - }, - "split2": { - "version": "3.2.2", - "resolved": "https://registry.npmjs.org/split2/-/split2-3.2.2.tgz", - "integrity": "sha512-9NThjpgZnifTkJpzTZ7Eue85S49QwpNhZTq6GRJwObb6jnLFNGB7Qm73V5HewTROPyxD0C29xqmaI68bQtV+hg==", - "dev": true, - "requires": { - "readable-stream": "^3.0.0" - } - }, - "sprintf-js": { - "version": "1.0.3", - "resolved": "https://registry.npmjs.org/sprintf-js/-/sprintf-js-1.0.3.tgz", - "integrity": "sha1-BOaSb2YolTVPPdAVIDYzuFcpfiw=", - "dev": true - }, - "sqwish": { - "version": "0.2.2", - "resolved": "https://registry.npmjs.org/sqwish/-/sqwish-0.2.2.tgz", - "integrity": "sha1-AP4maBBPEii1u37nOe9gEhu8sFc=" - }, - "sshpk": { - "version": "1.16.1", - "resolved": "https://registry.npmjs.org/sshpk/-/sshpk-1.16.1.tgz", - "integrity": "sha512-HXXqVUq7+pcKeLqqZj6mHFUMvXtOJt1uoUx09pFW6011inTMxqI8BA8PM95myrIyyKwdnzjdFjLiE6KBPVtJIg==", - "dev": true, - "requires": { - "asn1": "~0.2.3", - "assert-plus": "^1.0.0", - "bcrypt-pbkdf": "^1.0.0", - "dashdash": "^1.12.0", - "ecc-jsbn": "~0.1.1", - "getpass": "^0.1.1", - "jsbn": "~0.1.0", - "safer-buffer": "^2.0.2", - "tweetnacl": "~0.14.0" - } - }, - "ssri": { - "version": "8.0.1", - "resolved": "https://registry.npmjs.org/ssri/-/ssri-8.0.1.tgz", - "integrity": "sha512-97qShzy1AiyxvPNIkLWoGua7xoQzzPjQ0HAH4B0rWKo7SZ6USuPcrUiAFrws0UH8RrbWmgq3LMTObhPIHbbBeQ==", - "dev": true, - "requires": { - "minipass": "^3.1.1" - } - }, - "stackframe": { - "version": "1.2.0", - "resolved": "https://registry.npmjs.org/stackframe/-/stackframe-1.2.0.tgz", - "integrity": "sha512-GrdeshiRmS1YLMYgzF16olf2jJ/IzxXY9lhKOskuVziubpTYcYqyOwYeJKzQkwy7uN0fYSsbsC4RQaXf9LCrYA==" - }, - "statuses": { - "version": "1.5.0", - "resolved": "https://registry.npmjs.org/statuses/-/statuses-1.5.0.tgz", - "integrity": "sha1-Fhx9rBd2Wf2YEfQ3cfqZOBR4Yow=" - }, - "stream-browserify": { - "version": "2.0.2", - "resolved": "https://registry.npmjs.org/stream-browserify/-/stream-browserify-2.0.2.tgz", - "integrity": "sha512-nX6hmklHs/gr2FuxYDltq8fJA1GDlxKQCz8O/IM4atRqBH8OORmBNgfvW5gG10GT/qQ9u0CzIvr2X5Pkt6ntqg==", - "requires": { - "inherits": "~2.0.1", - "readable-stream": "^2.0.2" - }, - "dependencies": { - "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==", - "requires": { - "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" - } - }, - "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==", - "requires": { - "safe-buffer": "~5.1.0" - } - } - } - }, - "strict-uri-encode": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/strict-uri-encode/-/strict-uri-encode-2.0.0.tgz", - "integrity": "sha1-ucczDHBChi9rFC3CdLvMWGbONUY=", - "dev": true - }, - "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==", - "requires": { - "safe-buffer": "~5.2.0" - }, - "dependencies": { - "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==" - } - } - }, - "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==", - "requires": { - "emoji-regex": "^8.0.0", - "is-fullwidth-code-point": "^3.0.0", - "strip-ansi": "^6.0.1" - } - }, - "string.prototype.trimend": { - "version": "1.0.4", - "resolved": "https://registry.npmjs.org/string.prototype.trimend/-/string.prototype.trimend-1.0.4.tgz", - "integrity": "sha512-y9xCjw1P23Awk8EvTpcyL2NIr1j7wJ39f+k6lvRnSMz+mz9CGz9NYPelDk42kOz6+ql8xjfK8oYzy3jAP5QU5A==", - "dev": true, - "requires": { - "call-bind": "^1.0.2", - "define-properties": "^1.1.3" - } - }, - "string.prototype.trimstart": { - "version": "1.0.4", - "resolved": "https://registry.npmjs.org/string.prototype.trimstart/-/string.prototype.trimstart-1.0.4.tgz", - "integrity": "sha512-jh6e984OBfvxS50tdY2nRZnoC5/mLFKOREQfw8t5yytkoUsJRNxvI/E39qu1sD0OtWI3OC0XgKSmcWwziwYuZw==", - "dev": true, - "requires": { - "call-bind": "^1.0.2", - "define-properties": "^1.1.3" - } - }, - "strip-ansi": { - "version": "6.0.1", - "resolved": "https://registry.npmjs.org/strip-ansi/-/strip-ansi-6.0.1.tgz", - "integrity": "sha512-Y38VPSHcqkFrCpFnQ9vuSXmquuv5oXOKpGeT6aGrr3o3Gc9AlVa6JBfUSOCnbxGGZF+/0ooI7KrPuUSztUdU5A==", - "requires": { - "ansi-regex": "^5.0.1" - } - }, - "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 - }, - "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==" - }, - "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, - "requires": { - "min-indent": "^1.0.0" - } - }, - "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==" - }, - "strong-log-transformer": { - "version": "2.1.0", - "resolved": "https://registry.npmjs.org/strong-log-transformer/-/strong-log-transformer-2.1.0.tgz", - "integrity": "sha512-B3Hgul+z0L9a236FAUC9iZsL+nVHgoCJnqCbN588DjYxvGXaXaaFbfmQ/JhvKjZwsOukuR72XbHv71Qkug0HxA==", - "dev": true, - "requires": { - "duplexer": "^0.1.1", - "minimist": "^1.2.0", - "through": "^2.3.4" - } - }, - "superagent": { - "version": "6.1.0", - "resolved": "https://registry.npmjs.org/superagent/-/superagent-6.1.0.tgz", - "integrity": "sha512-OUDHEssirmplo3F+1HWKUrUjvnQuA+nZI6i/JJBdXb5eq9IyEQwPyPpqND+SSsxf6TygpBEkUjISVRN4/VOpeg==", - "requires": { - "component-emitter": "^1.3.0", - "cookiejar": "^2.1.2", - "debug": "^4.1.1", - "fast-safe-stringify": "^2.0.7", - "form-data": "^3.0.0", - "formidable": "^1.2.2", - "methods": "^1.1.2", - "mime": "^2.4.6", - "qs": "^6.9.4", - "readable-stream": "^3.6.0", - "semver": "^7.3.2" - }, - "dependencies": { - "form-data": { - "version": "3.0.1", - "resolved": "https://registry.npmjs.org/form-data/-/form-data-3.0.1.tgz", - "integrity": "sha512-RHkBKtLWUVwd7SqRIvCZMEvAMoGUp0XU+seQiZejj0COz3RI3hWP4sCv3gZWWLjJTd7rGwcsF5eKZGii0r/hbg==", - "requires": { - "asynckit": "^0.4.0", - "combined-stream": "^1.0.8", - "mime-types": "^2.1.12" - } - }, - "mime": { - "version": "2.6.0", - "resolved": "https://registry.npmjs.org/mime/-/mime-2.6.0.tgz", - "integrity": "sha512-USPkMeET31rOMiarsBNIHZKLGgvKc/LrjofAnBlOttf5ajRvqiRA8QsenbcooctK6d6Ts6aqZXBA+XbkKthiQg==" - } - } - }, - "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==", - "requires": { - "has-flag": "^4.0.0" - } - }, - "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==" - }, - "tapable": { - "version": "2.2.1", - "resolved": "https://registry.npmjs.org/tapable/-/tapable-2.2.1.tgz", - "integrity": "sha512-GNzQvQTOIP6RyTfE2Qxb8ZVlNmw0n88vp1szwWRimP02mnTsx3Wtn5qRdqY9w2XduFNUgvOwhNnQsjwCp+kqaQ==" - }, - "tar": { - "version": "6.1.11", - "resolved": "https://registry.npmjs.org/tar/-/tar-6.1.11.tgz", - "integrity": "sha512-an/KZQzQUkZCkuoAA64hM92X0Urb6VpRhAFllDzz44U2mcD5scmT3zBc4VgVpkugF580+DQn8eAFSyoQt0tznA==", - "dev": true, - "requires": { - "chownr": "^2.0.0", - "fs-minipass": "^2.0.0", - "minipass": "^3.0.0", - "minizlib": "^2.1.1", - "mkdirp": "^1.0.3", - "yallist": "^4.0.0" - } - }, - "temp-dir": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/temp-dir/-/temp-dir-1.0.0.tgz", - "integrity": "sha1-CnwOom06Oa+n4OvqnB/AvE2qAR0=", - "dev": true - }, - "temp-write": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/temp-write/-/temp-write-4.0.0.tgz", - "integrity": "sha512-HIeWmj77uOOHb0QX7siN3OtwV3CTntquin6TNVg6SHOqCP3hYKmox90eeFOGaY1MqJ9WYDDjkyZrW6qS5AWpbw==", - "dev": true, - "requires": { - "graceful-fs": "^4.1.15", - "is-stream": "^2.0.0", - "make-dir": "^3.0.0", - "temp-dir": "^1.0.0", - "uuid": "^3.3.2" - }, - "dependencies": { - "uuid": { - "version": "3.4.0", - "resolved": "https://registry.npmjs.org/uuid/-/uuid-3.4.0.tgz", - "integrity": "sha512-HjSDRw6gZE5JMggctHBcjVak08+KEVhSIiDzFnT9S9aegmp85S/bReBVTb4QTFaRNptJ9kuYaNhnbNEOkbKb/A==", - "dev": true - } - } - }, - "terser": { - "version": "5.10.0", - "resolved": "https://registry.npmjs.org/terser/-/terser-5.10.0.tgz", - "integrity": "sha512-AMmF99DMfEDiRJfxfY5jj5wNH/bYO09cniSqhfoyxc8sFoYIgkJy86G04UoZU5VjlpnplVu0K6Tx6E9b5+DlHA==", - "requires": { - "commander": "^2.20.0", - "source-map": "~0.7.2", - "source-map-support": "~0.5.20" - }, - "dependencies": { - "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==" - }, - "source-map": { - "version": "0.7.3", - "resolved": "https://registry.npmjs.org/source-map/-/source-map-0.7.3.tgz", - "integrity": "sha512-CkCj6giN3S+n9qrYiBTX5gystlENnRW5jZeNLHpe6aue+SrHcG5VYwujhW9s4dY31mEGsxBDrHR6oI69fTXsaQ==" - } - } - }, - "terser-webpack-plugin": { - "version": "5.3.0", - "resolved": "https://registry.npmjs.org/terser-webpack-plugin/-/terser-webpack-plugin-5.3.0.tgz", - "integrity": "sha512-LPIisi3Ol4chwAaPP8toUJ3L4qCM1G0wao7L3qNv57Drezxj6+VEyySpPw4B1HSO2Eg/hDY/MNF5XihCAoqnsQ==", - "requires": { - "jest-worker": "^27.4.1", - "schema-utils": "^3.1.1", - "serialize-javascript": "^6.0.0", - "source-map": "^0.6.1", - "terser": "^5.7.2" - }, - "dependencies": { - "ajv": { - "version": "6.12.6", - "resolved": "https://registry.npmjs.org/ajv/-/ajv-6.12.6.tgz", - "integrity": "sha512-j3fVLgvTo527anyYyJOGTYJbG+vnnQYvE0m5mmkc1TK+nxAppkCLMIL0aZ4dblVCNoGShhm+kzE4ZUykBoMg4g==", - "requires": { - "fast-deep-equal": "^3.1.1", - "fast-json-stable-stringify": "^2.0.0", - "json-schema-traverse": "^0.4.1", - "uri-js": "^4.2.2" - } - }, - "ajv-keywords": { - "version": "3.5.2", - "resolved": "https://registry.npmjs.org/ajv-keywords/-/ajv-keywords-3.5.2.tgz", - "integrity": "sha512-5p6WTN0DdTGVQk6VjcEju19IgaHudalcfabD7yhDGeA6bcQnmL+CpveLJq/3hvfwd1aof6L386Ougkx6RfyMIQ==", - "requires": {} - }, - "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==" - }, - "schema-utils": { - "version": "3.1.1", - "resolved": "https://registry.npmjs.org/schema-utils/-/schema-utils-3.1.1.tgz", - "integrity": "sha512-Y5PQxS4ITlC+EahLuXaY86TXfR7Dc5lw294alXOq86JAHCihAIZfqv8nNCWvaEJvaC51uN9hbLGeV0cFBdH+Fw==", - "requires": { - "@types/json-schema": "^7.0.8", - "ajv": "^6.12.5", - "ajv-keywords": "^3.5.2" - } - } - } - }, - "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, - "requires": { - "@istanbuljs/schema": "^0.1.2", - "glob": "^7.1.4", - "minimatch": "^3.0.4" - } - }, - "text-extensions": { - "version": "1.9.0", - "resolved": "https://registry.npmjs.org/text-extensions/-/text-extensions-1.9.0.tgz", - "integrity": "sha512-wiBrwC1EhBelW12Zy26JeOUkQ5mRu+5o8rpsJk5+2t+Y5vE7e842qtZDQ2g1NpX/29HdyFeJ4nSIhI47ENSxlQ==", - "dev": true - }, - "text-table": { - "version": "0.2.0", - "resolved": "https://registry.npmjs.org/text-table/-/text-table-0.2.0.tgz", - "integrity": "sha1-f17oI66AUgfACvLfSoTsP8+lcLQ=", - "dev": true - }, - "through": { - "version": "2.3.8", - "resolved": "https://registry.npmjs.org/through/-/through-2.3.8.tgz", - "integrity": "sha1-DdTJ/6q8NXlgsbckEV1+Doai4fU=" - }, - "through2": { - "version": "4.0.2", - "resolved": "https://registry.npmjs.org/through2/-/through2-4.0.2.tgz", - "integrity": "sha512-iOqSav00cVxEEICeD7TjLB1sueEL+81Wpzp2bY17uZjZN0pWZPuo4suZ/61VujxmqSGFfgOcNuTZ85QJwNZQpw==", - "dev": true, - "requires": { - "readable-stream": "3" - } - }, - "tmp": { - "version": "0.0.33", - "resolved": "https://registry.npmjs.org/tmp/-/tmp-0.0.33.tgz", - "integrity": "sha512-jRCJlojKnZ3addtTOjdIqoRuPEKBvNXcGYqzO6zWZX8KfKEpnGY5jfggJQ3EjKuu8D4bJRr0y+cYJFmYbImXGw==", - "dev": true, - "requires": { - "os-tmpdir": "~1.0.2" - } - }, - "to-fast-properties": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/to-fast-properties/-/to-fast-properties-2.0.0.tgz", - "integrity": "sha1-3F5pjL0HkmW8c+A3doGk5Og/YW4=" - }, - "to-readable-stream": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/to-readable-stream/-/to-readable-stream-1.0.0.tgz", - "integrity": "sha512-Iq25XBt6zD5npPhlLVXGFN3/gyR2/qODcKNNyTMd4vbm39HUaOiAM4PMq0eMVC/Tkxz+Zjdsc55g9yyz+Yq00Q==", - "dev": true - }, - "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==", - "requires": { - "is-number": "^7.0.0" - } - }, - "toidentifier": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/toidentifier/-/toidentifier-1.0.1.tgz", - "integrity": "sha512-o5sSPKEkg/DIQNmH43V0/uerLrpzVedkUh8tGNvaeXpfpuwjKenlSox/2O/BTlZUtEe+JG7s5YhEz608PlAHRA==" - }, - "tough-cookie": { - "version": "2.5.0", - "resolved": "https://registry.npmjs.org/tough-cookie/-/tough-cookie-2.5.0.tgz", - "integrity": "sha512-nlLsUzgm1kfLXSXfRZMc1KLAugd4hqJHDTvc2hDIwS3mZAfMEuMbc03SujMF+GEcpaX/qboeycw6iO8JwVv2+g==", - "dev": true, - "requires": { - "psl": "^1.1.28", - "punycode": "^2.1.1" - } - }, - "tr46": { - "version": "2.1.0", - "resolved": "https://registry.npmjs.org/tr46/-/tr46-2.1.0.tgz", - "integrity": "sha512-15Ih7phfcdP5YxqiB+iDtLoaTz4Nd35+IiAv0kQ5FNKHzXgdWqPoTIqEDDJmXceQt4JZk6lVPT8lnDlPpGDppw==", - "dev": true, - "requires": { - "punycode": "^2.1.1" - } - }, - "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 - }, - "trim-right": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/trim-right/-/trim-right-1.0.1.tgz", - "integrity": "sha1-yy4SAwZ+DI3h9hQJS5/kVwTqYAM=" - }, - "ts-loader": { - "version": "9.2.6", - "resolved": "https://registry.npmjs.org/ts-loader/-/ts-loader-9.2.6.tgz", - "integrity": "sha512-QMTC4UFzHmu9wU2VHZEmWWE9cUajjfcdcws+Gh7FhiO+Dy0RnR1bNz0YCHqhI0yRowCE9arVnNxYHqELOy9Hjw==", - "requires": { - "chalk": "^4.1.0", - "enhanced-resolve": "^5.0.0", - "micromatch": "^4.0.0", - "semver": "^7.3.4" - } - }, - "ts-node": { - "version": "10.4.0", - "resolved": "https://registry.npmjs.org/ts-node/-/ts-node-10.4.0.tgz", - "integrity": "sha512-g0FlPvvCXSIO1JDF6S232P5jPYqBkRL9qly81ZgAOSU7rwI0stphCgd2kLiCrU9DjQCrJMWEqcNSjQL02s6d8A==", - "requires": { - "@cspotcode/source-map-support": "0.7.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", - "yn": "3.1.1" - }, - "dependencies": { - "diff": { - "version": "4.0.2", - "resolved": "https://registry.npmjs.org/diff/-/diff-4.0.2.tgz", - "integrity": "sha512-58lmxKSA4BNyLz+HHMUzlOEpg09FV+ev6ZMe3vJihgdxzgcwZ8VoEEPmALCZG9LmqfVoNMMKpttIYTVG6uDY7A==" - } - } - }, - "ts-toolbelt": { - "version": "6.15.5", - "resolved": "https://registry.npmjs.org/ts-toolbelt/-/ts-toolbelt-6.15.5.tgz", - "integrity": "sha512-FZIXf1ksVyLcfr7M317jbB67XFJhOO1YqdTcuGaq9q5jLUoTikukZ+98TPjKiP2jC5CgmYdWWYs0s2nLSU0/1A==" - }, - "tsconfig-paths": { - "version": "3.12.0", - "resolved": "https://registry.npmjs.org/tsconfig-paths/-/tsconfig-paths-3.12.0.tgz", - "integrity": "sha512-e5adrnOYT6zqVnWqZu7i/BQ3BnhzvGbjEjejFXO20lKIKpwTaupkCPgEfv4GZK1IBciJUEhYs3J3p75FdaTFVg==", - "dev": true, - "requires": { - "@types/json5": "^0.0.29", - "json5": "^1.0.1", - "minimist": "^1.2.0", - "strip-bom": "^3.0.0" - }, - "dependencies": { - "json5": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/json5/-/json5-1.0.1.tgz", - "integrity": "sha512-aKS4WQjPenRxiQsC93MNfjx+nbF4PAdYzmd/1JIj8HYzqfbu86beTuNgXDzPknWk0n0uARlyewZo4s++ES36Ow==", - "dev": true, - "requires": { - "minimist": "^1.2.0" - } - }, - "strip-bom": { - "version": "3.0.0", - "resolved": "https://registry.npmjs.org/strip-bom/-/strip-bom-3.0.0.tgz", - "integrity": "sha1-IzTBjpx1n3vdVv3vfprj1YjmjtM=", - "dev": true - } - } - }, - "tslib": { - "version": "1.14.1", - "resolved": "https://registry.npmjs.org/tslib/-/tslib-1.14.1.tgz", - "integrity": "sha512-Xni35NKzjgMrwevysHTCArtLDpPvye8zV/0E4EyYn43P7/7qvQwPh9BGkHewbMulVntbigmcT7rdX3BNo9wRJg==", - "dev": true - }, - "tsscmp": { - "version": "1.0.6", - "resolved": "https://registry.npmjs.org/tsscmp/-/tsscmp-1.0.6.tgz", - "integrity": "sha512-LxhtAkPDTkVCMQjt2h6eBVY28KCjikZqZfMcC15YBeNjkgUpdCfBu5HoiOTDu86v6smE8yOjyEktJ8hlbANHQA==" - }, - "tsutils": { - "version": "3.21.0", - "resolved": "https://registry.npmjs.org/tsutils/-/tsutils-3.21.0.tgz", - "integrity": "sha512-mHKK3iUXL+3UF6xL5k0PEhKRUBKPBCv/+RkEOpjRWxxx27KKRBmmA60A9pgOUvMi8GKhRMPEmjBRPzs2W7O1OA==", - "dev": true, - "requires": { - "tslib": "^1.8.1" - } - }, - "tunnel-agent": { - "version": "0.6.0", - "resolved": "https://registry.npmjs.org/tunnel-agent/-/tunnel-agent-0.6.0.tgz", - "integrity": "sha1-J6XeoGs2sEoKmWZ3SykIaPD8QP0=", - "dev": true, - "requires": { - "safe-buffer": "^5.0.1" - } - }, - "tweetnacl": { - "version": "0.14.5", - "resolved": "https://registry.npmjs.org/tweetnacl/-/tweetnacl-0.14.5.tgz", - "integrity": "sha1-WuaBd/GS1EViadEIr6k/+HQ/T2Q=", - "dev": true - }, - "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, - "requires": { - "prelude-ls": "^1.2.1" - } - }, - "type-detect": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/type-detect/-/type-detect-1.0.0.tgz", - "integrity": "sha1-diIXzAbbJY7EiQihKY6LlRIejqI=" - }, - "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 - }, - "type-is": { - "version": "1.6.18", - "resolved": "https://registry.npmjs.org/type-is/-/type-is-1.6.18.tgz", - "integrity": "sha512-TkRKr9sUTxEH8MdfuCSP7VizJyzRNMjj2J2do2Jr3Kym598JVdEksuzPQCnlFPW4ky9Q+iA+ma9BGm06XQBy8g==", - "requires": { - "media-typer": "0.3.0", - "mime-types": "~2.1.24" - } - }, - "typedarray": { - "version": "0.0.6", - "resolved": "https://registry.npmjs.org/typedarray/-/typedarray-0.0.6.tgz", - "integrity": "sha1-hnrHTjhkGHsdPUfZlqeOxciDB3c=" - }, - "typedarray-to-buffer": { - "version": "3.1.5", - "resolved": "https://registry.npmjs.org/typedarray-to-buffer/-/typedarray-to-buffer-3.1.5.tgz", - "integrity": "sha512-zdu8XMNEDepKKR+XYOXAVPtWui0ly0NtohUscw+UmaHiAWT8hrV1rr//H6V+0DvJ3OQ19S979M0laLfX8rm82Q==", - "dev": true, - "requires": { - "is-typedarray": "^1.0.0" - } - }, - "typescript": { - "version": "4.5.4", - "resolved": "https://registry.npmjs.org/typescript/-/typescript-4.5.4.tgz", - "integrity": "sha512-VgYs2A2QIRuGphtzFV7aQJduJ2gyfTljngLzjpfW9FoYZF6xuw1W0vW9ghCKLfcWrCFxK81CSGRAvS1pn4fIUg==" - }, - "uglify-js": { - "version": "3.14.5", - "resolved": "https://registry.npmjs.org/uglify-js/-/uglify-js-3.14.5.tgz", - "integrity": "sha512-qZukoSxOG0urUTvjc2ERMTcAy+BiFh3weWAkeurLwjrCba73poHmG3E36XEjd/JGukMzwTL7uCxZiAexj8ppvQ==", - "dev": true, - "optional": true - }, - "uglify-to-browserify": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/uglify-to-browserify/-/uglify-to-browserify-1.0.2.tgz", - "integrity": "sha1-bgkk1r2mta/jSeOabWMoUKD4grc=", - "optional": true - }, - "uid-number": { - "version": "0.0.6", - "resolved": "https://registry.npmjs.org/uid-number/-/uid-number-0.0.6.tgz", - "integrity": "sha1-DqEOgDXo61uOREnwbaHHMGY7qoE=", - "dev": true - }, - "uid-safe": { - "version": "2.1.5", - "resolved": "https://registry.npmjs.org/uid-safe/-/uid-safe-2.1.5.tgz", - "integrity": "sha512-KPHm4VL5dDXKz01UuEd88Df+KzynaohSL9fBh096KWAxSKZQDI2uBrVqtvRM4rwrIrRRKsdLNML/lnaaVSRioA==", - "requires": { - "random-bytes": "~1.0.0" - } - }, - "ultron": { - "version": "1.1.1", - "resolved": "https://registry.npmjs.org/ultron/-/ultron-1.1.1.tgz", - "integrity": "sha512-UIEXBNeYmKptWH6z8ZnqTeS8fV74zG0/eRU9VGkpzz+LIJNs8W/zM/L+7ctCkRrgbNnnR0xxw4bKOr0cW0N0Og==" - }, - "umask": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/umask/-/umask-1.1.0.tgz", - "integrity": "sha1-8pzr8B31F5ErtY/5xOUP3o4zMg0=", - "dev": true - }, - "unbox-primitive": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/unbox-primitive/-/unbox-primitive-1.0.1.tgz", - "integrity": "sha512-tZU/3NqK3dA5gpE1KtyiJUrEB0lxnGkMFHptJ7q6ewdZ8s12QrODwNbhIJStmJkd1QDXa1NRA8aF2A1zk/Ypyw==", - "dev": true, - "requires": { - "function-bind": "^1.1.1", - "has-bigints": "^1.0.1", - "has-symbols": "^1.0.2", - "which-boxed-primitive": "^1.0.2" - } - }, - "unc-path-regex": { - "version": "0.1.2", - "resolved": "https://registry.npmjs.org/unc-path-regex/-/unc-path-regex-0.1.2.tgz", - "integrity": "sha1-5z3T17DXxe2G+6xrCufYxqadUPo=" - }, - "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==" - }, - "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==", - "requires": { - "unicode-canonical-property-names-ecmascript": "^2.0.0", - "unicode-property-aliases-ecmascript": "^2.0.0" - } - }, - "unicode-match-property-value-ecmascript": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/unicode-match-property-value-ecmascript/-/unicode-match-property-value-ecmascript-2.0.0.tgz", - "integrity": "sha512-7Yhkc0Ye+t4PNYzOGKedDhXbYIBe1XEQYQxOPyhcXNMJ0WCABqqj6ckydd6pWRZTHV4GuCPKdBAUiMc60tsKVw==" - }, - "unicode-property-aliases-ecmascript": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/unicode-property-aliases-ecmascript/-/unicode-property-aliases-ecmascript-2.0.0.tgz", - "integrity": "sha512-5Zfuy9q/DFr4tfO7ZPeVXb1aPoeQSdeFMLpYuFebehDAhbuevLs5yxSZmIFN1tP5F9Wl4IpJrYojg85/zgyZHQ==" - }, - "unique-filename": { - "version": "1.1.1", - "resolved": "https://registry.npmjs.org/unique-filename/-/unique-filename-1.1.1.tgz", - "integrity": "sha512-Vmp0jIp2ln35UTXuryvjzkjGdRyf9b2lTXuSYUiPmzRcl3FDtYqAwOnTJkAngD9SWhnoJzDbTKwaOrZ+STtxNQ==", - "dev": true, - "requires": { - "unique-slug": "^2.0.0" - } - }, - "unique-slug": { - "version": "2.0.2", - "resolved": "https://registry.npmjs.org/unique-slug/-/unique-slug-2.0.2.tgz", - "integrity": "sha512-zoWr9ObaxALD3DOPfjPSqxt4fnZiWblxHIgeWqW8x7UqDzEtHEQLzji2cuJYQFCU6KmoJikOYAZlrTHHebjx2w==", - "dev": true, - "requires": { - "imurmurhash": "^0.1.4" - } - }, - "unique-string": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/unique-string/-/unique-string-2.0.0.tgz", - "integrity": "sha512-uNaeirEPvpZWSgzwsPGtU2zVSTrn/8L5q/IexZmH0eH6SA73CmAA5U4GwORTxQAZs95TAXLNqeLoPPNO5gZfWg==", - "dev": true, - "requires": { - "crypto-random-string": "^2.0.0" - } - }, - "universal-user-agent": { - "version": "6.0.0", - "resolved": "https://registry.npmjs.org/universal-user-agent/-/universal-user-agent-6.0.0.tgz", - "integrity": "sha512-isyNax3wXoKaulPDZWHQqbmIx1k2tb9fb3GGDBRxCscfYV2Ch7WxPArBsFEG8s/safwXTT7H4QGhaIkTp9447w==", - "dev": true - }, - "universalify": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/universalify/-/universalify-2.0.0.tgz", - "integrity": "sha512-hAZsKq7Yy11Zu1DE0OzWjw7nnLZmJZYTDZZyEFHZdUhV8FkH5MCfoU1XMaxXovpyW5nq5scPqq0ZDP9Zyl04oQ==", - "dev": true - }, - "unpipe": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/unpipe/-/unpipe-1.0.0.tgz", - "integrity": "sha1-sr9O6FFKrmFltIF4KdIbLvSZBOw=" - }, - "upath": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/upath/-/upath-2.0.1.tgz", - "integrity": "sha512-1uEe95xksV1O0CYKXo8vQvN1JEbtJp7lb7C5U9HMsIp6IVwntkH/oNUzyVNQSd4S1sYk2FpSSW44FqMc8qee5w==", - "dev": true - }, - "update-notifier": { - "version": "5.1.0", - "resolved": "https://registry.npmjs.org/update-notifier/-/update-notifier-5.1.0.tgz", - "integrity": "sha512-ItnICHbeMh9GqUy31hFPrD1kcuZ3rpxDZbf4KUDavXwS0bW5m7SLbDQpGX3UYr072cbrF5hFUs3r5tUsPwjfHw==", - "dev": true, - "requires": { - "boxen": "^5.0.0", - "chalk": "^4.1.0", - "configstore": "^5.0.1", - "has-yarn": "^2.1.0", - "import-lazy": "^2.1.0", - "is-ci": "^2.0.0", - "is-installed-globally": "^0.4.0", - "is-npm": "^5.0.0", - "is-yarn-global": "^0.3.0", - "latest-version": "^5.1.0", - "pupa": "^2.1.1", - "semver": "^7.3.4", - "semver-diff": "^3.1.1", - "xdg-basedir": "^4.0.0" - } - }, - "uri-js": { - "version": "4.4.1", - "resolved": "https://registry.npmjs.org/uri-js/-/uri-js-4.4.1.tgz", - "integrity": "sha512-7rKUyy33Q1yc98pQ1DAmLtwX109F7TIfWlW1Ydo8Wl1ii1SeHieeh0HHfPeL2fMXK6z0s8ecKs9frCuLJvndBg==", - "requires": { - "punycode": "^2.1.0" - } - }, - "url": { - "version": "0.11.0", - "resolved": "https://registry.npmjs.org/url/-/url-0.11.0.tgz", - "integrity": "sha1-ODjpfPxgUh63PFJajlW/3Z4uKPE=", - "requires": { - "punycode": "1.3.2", - "querystring": "0.2.0" - }, - "dependencies": { - "punycode": { - "version": "1.3.2", - "resolved": "https://registry.npmjs.org/punycode/-/punycode-1.3.2.tgz", - "integrity": "sha1-llOgNvt8HuQjQvIyXM7v6jkmxI0=" - } - } - }, - "url-parse-lax": { - "version": "3.0.0", - "resolved": "https://registry.npmjs.org/url-parse-lax/-/url-parse-lax-3.0.0.tgz", - "integrity": "sha1-FrXK/Afb42dsGxmZF3gj1lA6yww=", - "dev": true, - "requires": { - "prepend-http": "^2.0.0" - } - }, - "util": { - "version": "0.11.1", - "resolved": "https://registry.npmjs.org/util/-/util-0.11.1.tgz", - "integrity": "sha512-HShAsny+zS2TZfaXxD9tYj4HQGlBezXZMZuM/S5PKLLoZkShZiGk9o5CzukI1LVHZvjdvZ2Sj1aW/Ndn2NB/HQ==", - "requires": { - "inherits": "2.0.3" - }, - "dependencies": { - "inherits": { - "version": "2.0.3", - "resolved": "https://registry.npmjs.org/inherits/-/inherits-2.0.3.tgz", - "integrity": "sha1-Yzwsg+PaQqUC9SRmAiSA9CCCYd4=" - } - } - }, - "util-deprecate": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/util-deprecate/-/util-deprecate-1.0.2.tgz", - "integrity": "sha1-RQ1Nyfpw3nMnYvvS1KKJgUGaDM8=" - }, - "util-promisify": { - "version": "2.1.0", - "resolved": "https://registry.npmjs.org/util-promisify/-/util-promisify-2.1.0.tgz", - "integrity": "sha1-PCI2R2xNMsX/PEcAKt18E7moKlM=", - "dev": true, - "requires": { - "object.getownpropertydescriptors": "^2.0.3" - } - }, - "utils-merge": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/utils-merge/-/utils-merge-1.0.1.tgz", - "integrity": "sha1-n5VxD1CiZ5R7LMwSR0HBAoQn5xM=" - }, - "uuid": { - "version": "8.3.2", - "resolved": "https://registry.npmjs.org/uuid/-/uuid-8.3.2.tgz", - "integrity": "sha512-+NYs2QeMWy+GWFOEm9xnn6HCDp0l7QBD7ml8zLUmJ+93Q5NF0NocErnwkTkXVFNiX3/fpC6afS8Dhb/gz7R7eg==" - }, - "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 - }, - "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==", - "requires": { - "spdx-correct": "^3.0.0", - "spdx-expression-parse": "^3.0.0" - } - }, - "validate-npm-package-name": { - "version": "3.0.0", - "resolved": "https://registry.npmjs.org/validate-npm-package-name/-/validate-npm-package-name-3.0.0.tgz", - "integrity": "sha1-X6kS2B630MdK/BQN5zF/DKffQ34=", - "dev": true, - "requires": { - "builtins": "^1.0.3" - } - }, - "vary": { - "version": "1.1.2", - "resolved": "https://registry.npmjs.org/vary/-/vary-1.1.2.tgz", - "integrity": "sha1-IpnwLG3tMNSllhsLn3RSShj2NPw=" - }, - "verror": { - "version": "1.10.0", - "resolved": "https://registry.npmjs.org/verror/-/verror-1.10.0.tgz", - "integrity": "sha1-OhBcoXBTr1XW4nDB+CiGguGNpAA=", - "dev": true, - "requires": { - "assert-plus": "^1.0.0", - "core-util-is": "1.0.2", - "extsprintf": "^1.2.0" - } - }, - "warp10": { - "version": "2.0.2", - "resolved": "https://registry.npmjs.org/warp10/-/warp10-2.0.2.tgz", - "integrity": "sha512-CC8MD3mBxPvKgBz58QJo8G+jPGo/oaBL2vcT6EWVpWsgzvDNwhiBBLGUDmRqaaVXv1INh8bpJPpVMUP5q1myBw==" - }, - "watchpack": { - "version": "2.3.1", - "resolved": "https://registry.npmjs.org/watchpack/-/watchpack-2.3.1.tgz", - "integrity": "sha512-x0t0JuydIo8qCNctdDrn1OzH/qDzk2+rdCOC3YzumZ42fiMqmQ7T3xQurykYMhYfHaPHTp4ZxAx2NfUo1K6QaA==", - "requires": { - "glob-to-regexp": "^0.4.1", - "graceful-fs": "^4.1.2" - } - }, - "wcwidth": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/wcwidth/-/wcwidth-1.0.1.tgz", - "integrity": "sha1-8LDc+RW8X/FSivrbLA4XtTLaL+g=", - "dev": true, - "requires": { - "defaults": "^1.0.3" - } - }, - "webidl-conversions": { - "version": "6.1.0", - "resolved": "https://registry.npmjs.org/webidl-conversions/-/webidl-conversions-6.1.0.tgz", - "integrity": "sha512-qBIvFLGiBpLjfwmYAaHPXsn+ho5xZnGvyGvsarywGNc8VyQJUMHJ8OBKGGrPER0okBeMDaan4mNBlgBROxuI8w==", - "dev": true - }, - "webpack": { - "version": "5.65.0", - "resolved": "https://registry.npmjs.org/webpack/-/webpack-5.65.0.tgz", - "integrity": "sha512-Q5or2o6EKs7+oKmJo7LaqZaMOlDWQse9Tm5l1WAfU/ujLGN5Pb0SqGeVkN/4bpPmEqEP5RnVhiqsOtWtUVwGRw==", - "requires": { - "@types/eslint-scope": "^3.7.0", - "@types/estree": "^0.0.50", - "@webassemblyjs/ast": "1.11.1", - "@webassemblyjs/wasm-edit": "1.11.1", - "@webassemblyjs/wasm-parser": "1.11.1", - "acorn": "^8.4.1", - "acorn-import-assertions": "^1.7.6", - "browserslist": "^4.14.5", - "chrome-trace-event": "^1.0.2", - "enhanced-resolve": "^5.8.3", - "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.4", - "json-parse-better-errors": "^1.0.2", - "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.3.1", - "webpack-sources": "^3.2.2" - }, - "dependencies": { - "ajv": { - "version": "6.12.6", - "resolved": "https://registry.npmjs.org/ajv/-/ajv-6.12.6.tgz", - "integrity": "sha512-j3fVLgvTo527anyYyJOGTYJbG+vnnQYvE0m5mmkc1TK+nxAppkCLMIL0aZ4dblVCNoGShhm+kzE4ZUykBoMg4g==", - "requires": { - "fast-deep-equal": "^3.1.1", - "fast-json-stable-stringify": "^2.0.0", - "json-schema-traverse": "^0.4.1", - "uri-js": "^4.2.2" - } - }, - "ajv-keywords": { - "version": "3.5.2", - "resolved": "https://registry.npmjs.org/ajv-keywords/-/ajv-keywords-3.5.2.tgz", - "integrity": "sha512-5p6WTN0DdTGVQk6VjcEju19IgaHudalcfabD7yhDGeA6bcQnmL+CpveLJq/3hvfwd1aof6L386Ougkx6RfyMIQ==", - "requires": {} - }, - "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==" - }, - "schema-utils": { - "version": "3.1.1", - "resolved": "https://registry.npmjs.org/schema-utils/-/schema-utils-3.1.1.tgz", - "integrity": "sha512-Y5PQxS4ITlC+EahLuXaY86TXfR7Dc5lw294alXOq86JAHCihAIZfqv8nNCWvaEJvaC51uN9hbLGeV0cFBdH+Fw==", - "requires": { - "@types/json-schema": "^7.0.8", - "ajv": "^6.12.5", - "ajv-keywords": "^3.5.2" - } - } - } - }, - "webpack-cli": { - "version": "4.9.1", - "resolved": "https://registry.npmjs.org/webpack-cli/-/webpack-cli-4.9.1.tgz", - "integrity": "sha512-JYRFVuyFpzDxMDB+v/nanUdQYcZtqFPGzmlW4s+UkPMFhSpfRNmf1z4AwYcHJVdvEFAM7FFCQdNTpsBYhDLusQ==", - "requires": { - "@discoveryjs/json-ext": "^0.5.0", - "@webpack-cli/configtest": "^1.1.0", - "@webpack-cli/info": "^1.4.0", - "@webpack-cli/serve": "^1.6.0", - "colorette": "^2.0.14", - "commander": "^7.0.0", - "execa": "^5.0.0", - "fastest-levenshtein": "^1.0.12", - "import-local": "^3.0.2", - "interpret": "^2.2.0", - "rechoir": "^0.7.0", - "webpack-merge": "^5.7.3" - }, - "dependencies": { - "commander": { - "version": "7.2.0", - "resolved": "https://registry.npmjs.org/commander/-/commander-7.2.0.tgz", - "integrity": "sha512-QrWXB+ZQSVPmIWIhtEO9H+gwHaMGYiF5ChvoJ+K9ZGHG/sVsa6yiesAD1GC/x46sET00Xlwo1u49RVVVzvcSkw==" - }, - "interpret": { - "version": "2.2.0", - "resolved": "https://registry.npmjs.org/interpret/-/interpret-2.2.0.tgz", - "integrity": "sha512-Ju0Bz/cEia55xDwUWEa8+olFpCiQoypjnQySseKtmjNrnps3P+xfpUmGr90T7yjlVJmOtybRvPXhKMbHr+fWnw==" - }, - "rechoir": { - "version": "0.7.1", - "resolved": "https://registry.npmjs.org/rechoir/-/rechoir-0.7.1.tgz", - "integrity": "sha512-/njmZ8s1wVeR6pjTZ+0nCnv8SpZNRMT2D1RLOJQESlYFDBvwpTA4KWJpZ+sBJ4+vhjILRcK7JIFdGCdxEAAitg==", - "requires": { - "resolve": "^1.9.0" - } - } - } - }, - "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==", - "requires": { - "clone-deep": "^4.0.1", - "wildcard": "^2.0.0" - } - }, - "webpack-sources": { - "version": "3.2.2", - "resolved": "https://registry.npmjs.org/webpack-sources/-/webpack-sources-3.2.2.tgz", - "integrity": "sha512-cp5qdmHnu5T8wRg2G3vZZHoJPN14aqQ89SyQ11NpGH5zEMDCclt49rzo+MaRazk7/UeILhAI+/sEtcM+7Fr0nw==" - }, - "whatwg-url": { - "version": "8.7.0", - "resolved": "https://registry.npmjs.org/whatwg-url/-/whatwg-url-8.7.0.tgz", - "integrity": "sha512-gAojqb/m9Q8a5IV96E3fHJM70AzCkgt4uXYX2O7EmuyOnLrViCQlsEBmF9UQIu3/aeAIp2U17rtbpZWNntQqdg==", - "dev": true, - "requires": { - "lodash": "^4.7.0", - "tr46": "^2.1.0", - "webidl-conversions": "^6.1.0" - } - }, - "which": { - "version": "2.0.2", - "resolved": "https://registry.npmjs.org/which/-/which-2.0.2.tgz", - "integrity": "sha512-BLI3Tl1TW3Pvl70l3yq3Y64i+awpwXqsGBYWkkqMtnbXgrMD+yj7rhW0kuEDxzJaYXGjEW5ogapKNMEKNMjibA==", - "requires": { - "isexe": "^2.0.0" - } - }, - "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, - "requires": { - "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" - } - }, - "which-module": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/which-module/-/which-module-2.0.0.tgz", - "integrity": "sha1-2e8H3Od7mQK4o6j6SzHD4/fm6Ho=", - "dev": true - }, - "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==", - "dev": true, - "requires": { - "string-width": "^1.0.2 || 2 || 3 || 4" - } - }, - "widest-line": { - "version": "3.1.0", - "resolved": "https://registry.npmjs.org/widest-line/-/widest-line-3.1.0.tgz", - "integrity": "sha512-NsmoXalsWVDMGupxZ5R08ka9flZjjiLvHVAWYOKtiKM8ujtZWr9cRffak+uSE48+Ob8ObalXpwyeUiyDD6QFgg==", - "dev": true, - "requires": { - "string-width": "^4.0.0" - } - }, - "wildcard": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/wildcard/-/wildcard-2.0.0.tgz", - "integrity": "sha512-JcKqAHLPxcdb9KM49dufGXn2x3ssnfjbcaQdLlfZsL9rH9wgDQjUtDxbo8NE0F6SFvydeu1VhZe7hZuHsB2/pw==" - }, - "window-size": { - "version": "0.1.0", - "resolved": "https://registry.npmjs.org/window-size/-/window-size-0.1.0.tgz", - "integrity": "sha1-VDjNLqk7IC76Ohn+iIeu58lPnJ0=" - }, - "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==" - }, - "wordwrap": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/wordwrap/-/wordwrap-1.0.0.tgz", - "integrity": "sha1-J1hIEIkUVqQXHI0CJkQa3pDLyus=", - "dev": true - }, - "workerpool": { - "version": "6.1.5", - "resolved": "https://registry.npmjs.org/workerpool/-/workerpool-6.1.5.tgz", - "integrity": "sha512-XdKkCK0Zqc6w3iTxLckiuJ81tiD/o5rBE/m+nXpRCB+/Sq4DqkfXZ/x0jW02DG1tGsfUGXbTJyZDP+eu67haSw==" - }, - "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==", - "requires": { - "ansi-styles": "^4.0.0", - "string-width": "^4.1.0", - "strip-ansi": "^6.0.0" - } - }, - "wrappy": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/wrappy/-/wrappy-1.0.2.tgz", - "integrity": "sha1-tSQ9jz7BqjXxNkYFvA0QNuMKtp8=" - }, - "write-file-atomic": { - "version": "3.0.3", - "resolved": "https://registry.npmjs.org/write-file-atomic/-/write-file-atomic-3.0.3.tgz", - "integrity": "sha512-AvHcyZ5JnSfq3ioSyjrBkH9yW4m7Ayk8/9My/DD9onKeu/94fwrMocemO2QAJFAlnnDN+ZDS+ZjAR5ua1/PV/Q==", - "dev": true, - "requires": { - "imurmurhash": "^0.1.4", - "is-typedarray": "^1.0.0", - "signal-exit": "^3.0.2", - "typedarray-to-buffer": "^3.1.5" - } - }, - "write-json-file": { - "version": "4.3.0", - "resolved": "https://registry.npmjs.org/write-json-file/-/write-json-file-4.3.0.tgz", - "integrity": "sha512-PxiShnxf0IlnQuMYOPPhPkhExoCQuTUNPOa/2JWCYTmBquU9njyyDuwRKN26IZBlp4yn1nt+Agh2HOOBl+55HQ==", - "dev": true, - "requires": { - "detect-indent": "^6.0.0", - "graceful-fs": "^4.1.15", - "is-plain-obj": "^2.0.0", - "make-dir": "^3.0.0", - "sort-keys": "^4.0.0", - "write-file-atomic": "^3.0.0" - }, - "dependencies": { - "is-plain-obj": { - "version": "2.1.0", - "resolved": "https://registry.npmjs.org/is-plain-obj/-/is-plain-obj-2.1.0.tgz", - "integrity": "sha512-YWnfyRwxL/+SsrWYfOpUtz5b3YD+nyfkHvjbcanzk8zgyO4ASD67uVMRt8k5bM4lLMDnXfriRhOpemw+NfT1eA==", - "dev": true - } - } - }, - "write-pkg": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/write-pkg/-/write-pkg-4.0.0.tgz", - "integrity": "sha512-v2UQ+50TNf2rNHJ8NyWttfm/EJUBWMJcx6ZTYZr6Qp52uuegWw/lBkCtCbnYZEmPRNL61m+u67dAmGxo+HTULA==", - "dev": true, - "requires": { - "sort-keys": "^2.0.0", - "type-fest": "^0.4.1", - "write-json-file": "^3.2.0" - }, - "dependencies": { - "detect-indent": { - "version": "5.0.0", - "resolved": "https://registry.npmjs.org/detect-indent/-/detect-indent-5.0.0.tgz", - "integrity": "sha1-OHHMCmoALow+Wzz38zYmRnXwa50=", - "dev": true - }, - "make-dir": { - "version": "2.1.0", - "resolved": "https://registry.npmjs.org/make-dir/-/make-dir-2.1.0.tgz", - "integrity": "sha512-LS9X+dc8KLxXCb8dni79fLIIUA5VyZoyjSMCwTluaXA0o27cCK0bhXkpgw+sTXVpPy/lSO57ilRixqk0vDmtRA==", - "dev": true, - "requires": { - "pify": "^4.0.1", - "semver": "^5.6.0" - } - }, - "pify": { - "version": "4.0.1", - "resolved": "https://registry.npmjs.org/pify/-/pify-4.0.1.tgz", - "integrity": "sha512-uB80kBFb/tfd68bVleG9T5GGsGPjJrLAUpR5PZIrhBnIaRTQRjqdJSsIKkOP6OAIFbj7GOrcudc5pNjZ+geV2g==", - "dev": true - }, - "semver": { - "version": "5.7.1", - "resolved": "https://registry.npmjs.org/semver/-/semver-5.7.1.tgz", - "integrity": "sha512-sauaDf/PZdVgrLTNYHRtpXa1iRiKcaebiKQ1BJdpQlWH2lCvexQdX55snPFyK7QzpudqbCI0qXFfOasHdyNDGQ==", - "dev": true - }, - "sort-keys": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/sort-keys/-/sort-keys-2.0.0.tgz", - "integrity": "sha1-ZYU1WEhh7JfXMNbPQYIuH1ZoQSg=", - "dev": true, - "requires": { - "is-plain-obj": "^1.0.0" - } - }, - "type-fest": { - "version": "0.4.1", - "resolved": "https://registry.npmjs.org/type-fest/-/type-fest-0.4.1.tgz", - "integrity": "sha512-IwzA/LSfD2vC1/YDYMv/zHP4rDF1usCwllsDpbolT3D4fUepIO7f9K70jjmUewU/LmGUKJcwcVtDCpnKk4BPMw==", - "dev": true - }, - "write-file-atomic": { - "version": "2.4.3", - "resolved": "https://registry.npmjs.org/write-file-atomic/-/write-file-atomic-2.4.3.tgz", - "integrity": "sha512-GaETH5wwsX+GcnzhPgKcKjJ6M2Cq3/iZp1WyY/X1CSqrW+jVNM9Y7D8EC2sM4ZG/V8wZlSniJnCKWPmBYAucRQ==", - "dev": true, - "requires": { - "graceful-fs": "^4.1.11", - "imurmurhash": "^0.1.4", - "signal-exit": "^3.0.2" - } - }, - "write-json-file": { - "version": "3.2.0", - "resolved": "https://registry.npmjs.org/write-json-file/-/write-json-file-3.2.0.tgz", - "integrity": "sha512-3xZqT7Byc2uORAatYiP3DHUUAVEkNOswEWNs9H5KXiicRTvzYzYqKjYc4G7p+8pltvAw641lVByKVtMpf+4sYQ==", - "dev": true, - "requires": { - "detect-indent": "^5.0.0", - "graceful-fs": "^4.1.15", - "make-dir": "^2.1.0", - "pify": "^4.0.1", - "sort-keys": "^2.0.0", - "write-file-atomic": "^2.4.2" - } - } - } - }, - "ws": { - "version": "3.3.3", - "resolved": "https://registry.npmjs.org/ws/-/ws-3.3.3.tgz", - "integrity": "sha512-nnWLa/NwZSt4KQJu51MYlCcSQ5g7INpOrOMt4XV8j4dqTXdmlUmSHQ8/oLC069ckre0fRsgfvsKwbTdtKLCDkA==", - "requires": { - "async-limiter": "~1.0.0", - "safe-buffer": "~5.1.0", - "ultron": "~1.1.0" - } - }, - "xdg-basedir": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/xdg-basedir/-/xdg-basedir-4.0.0.tgz", - "integrity": "sha512-PSNhEJDejZYV7h50BohL09Er9VaIefr2LMAf3OEmpCkjOi34eYyQYAXUTjEQtZJTKcF0E2UKTh+osDLsgNim9Q==", - "dev": true - }, - "xmlhttprequest-ssl": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/xmlhttprequest-ssl/-/xmlhttprequest-ssl-2.0.0.tgz", - "integrity": "sha512-QKxVRxiRACQcVuQEYFsI1hhkrMlrXHPegbbd1yn9UHOmRxY+si12nQYzri3vbzt8VdTTRviqcKxcyllFas5z2A==" - }, - "xtend": { - "version": "4.0.2", - "resolved": "https://registry.npmjs.org/xtend/-/xtend-4.0.2.tgz", - "integrity": "sha512-LKYU1iAXJXUgAXn9URjiu+MWhyUXHsvfp7mcuYm9dSUKK0/CjtrUwFAxD82/mCWbtLsGjFIad0wIsod4zrTAEQ==", - "dev": true - }, - "y18n": { - "version": "5.0.8", - "resolved": "https://registry.npmjs.org/y18n/-/y18n-5.0.8.tgz", - "integrity": "sha512-0pfFzegeDWJHJIAmTLRP2DwHjdF5s7jo9tuztdQxAhINCdvS+3nGINqPd00AphqJR/0LhANUS6/+7SCb98YOfA==" - }, - "yallist": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/yallist/-/yallist-4.0.0.tgz", - "integrity": "sha512-3wdGidZyq5PB084XLES5TpOSRA3wjXAlIWMhum2kRcv/41Sn2emQ0dycQW4uZXLejwKvg6EsvbdlVL+FYEct7A==" - }, - "yaml": { - "version": "1.10.2", - "resolved": "https://registry.npmjs.org/yaml/-/yaml-1.10.2.tgz", - "integrity": "sha512-r3vXyErRCYJ7wg28yvBY5VSoAF8ZvlcW9/BwUzEtUsjvX/DKs24dIkuwjtuprwJJHsbyUbLApepYTR1BN4uHrg==", - "dev": true - }, - "yargs": { - "version": "16.2.0", - "resolved": "https://registry.npmjs.org/yargs/-/yargs-16.2.0.tgz", - "integrity": "sha512-D1mvvtDG0L5ft/jGWkLpG1+m0eQxOfaBvTNELraWj22wSVUMWxZUvYgJYcKh6jGGIkJFhH4IZPQhR4TKpc8mBw==", - "requires": { - "cliui": "^7.0.2", - "escalade": "^3.1.1", - "get-caller-file": "^2.0.5", - "require-directory": "^2.1.1", - "string-width": "^4.2.0", - "y18n": "^5.0.5", - "yargs-parser": "^20.2.2" - } - }, - "yargs-parser": { - "version": "20.2.4", - "resolved": "https://registry.npmjs.org/yargs-parser/-/yargs-parser-20.2.4.tgz", - "integrity": "sha512-WOkpgNhPTlE73h4VFAFsOnomJVaovO8VqLDzy5saChRBFQFBoMYirowyW+Q9HB4HFF4Z7VZTiG3iSzJJA29yRA==" - }, - "yargs-unparser": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/yargs-unparser/-/yargs-unparser-2.0.0.tgz", - "integrity": "sha512-7pRTIA9Qc1caZ0bZ6RYRGbHJthJWuakf+WmHK0rVeLkNrrGhfoabBNdue6kdINI6r4if7ocq9aD/n7xwKOdzOA==", - "requires": { - "camelcase": "^6.0.0", - "decamelize": "^4.0.0", - "flat": "^5.0.2", - "is-plain-obj": "^2.1.0" - }, - "dependencies": { - "camelcase": { - "version": "6.3.0", - "resolved": "https://registry.npmjs.org/camelcase/-/camelcase-6.3.0.tgz", - "integrity": "sha512-Gmy6FhYlCY7uOElZUSbxo2UCDH8owEk996gkbrpsgGtrJLM3J7jGxl9Ic7Qwwj4ivOE5AWZWRMecDdF7hqGjFA==" - }, - "decamelize": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/decamelize/-/decamelize-4.0.0.tgz", - "integrity": "sha512-9iE1PgSik9HeIIw2JO94IidnE3eBoQrFJ3w7sFuzSX4DpmZ3v5sZpUiV5Swcf6mQEF+Y0ru8Neo+p+nyh2J+hQ==" - }, - "is-plain-obj": { - "version": "2.1.0", - "resolved": "https://registry.npmjs.org/is-plain-obj/-/is-plain-obj-2.1.0.tgz", - "integrity": "sha512-YWnfyRwxL/+SsrWYfOpUtz5b3YD+nyfkHvjbcanzk8zgyO4ASD67uVMRt8k5bM4lLMDnXfriRhOpemw+NfT1eA==" - } - } - }, - "yauzl": { - "version": "2.10.0", - "resolved": "https://registry.npmjs.org/yauzl/-/yauzl-2.10.0.tgz", - "integrity": "sha1-x+sXyT4RLLEIb6bY5R+wZnt5pfk=", - "requires": { - "buffer-crc32": "~0.2.3", - "fd-slicer": "~1.1.0" - } - }, - "yeast": { - "version": "0.1.2", - "resolved": "https://registry.npmjs.org/yeast/-/yeast-0.1.2.tgz", - "integrity": "sha1-AI4G2AlDIMNy28L47XagymyKxBk=" - }, - "ylru": { - "version": "1.2.1", - "resolved": "https://registry.npmjs.org/ylru/-/ylru-1.2.1.tgz", - "integrity": "sha512-faQrqNMzcPCHGVC2aaOINk13K+aaBDUPjGWl0teOXywElLjyVAB6Oe2jj62jHYtwsU49jXhScYbvPENK+6zAvQ==" - }, - "yn": { - "version": "3.1.1", - "resolved": "https://registry.npmjs.org/yn/-/yn-3.1.1.tgz", - "integrity": "sha512-Ux4ygGWsu2c7isFWe8Yu1YluJmqVhxqK2cLXNQA5AcC3QfbGNpM7fu0Y8b/z16pXLnFxZYvWhd3fhBY9DLmC6Q==" - }, - "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==" - } - } + "name": "feathers", + "lockfileVersion": 2, + "requires": true, + "packages": { + "": { + "name": "feathers", + "hasInstallScript": true, + "license": "MIT", + "devDependencies": { + "@typescript-eslint/eslint-plugin": "^5.39.0", + "@typescript-eslint/parser": "^5.39.0", + "c8": "^7.12.0", + "eslint": "^8.24.0", + "eslint-config-prettier": "^8.5.0", + "eslint-plugin-prettier": "^4.2.1", + "lerna": "^5.6.1", + "npm-check-updates": "^16.3.8", + "prettier": "^2.7.1", + "typescript": "^4.8.4" + }, + "engines": { + "node": ">= 14" + }, + "funding": { + "type": "github", + "url": "https://github.com/sponsors/daffl" + } + }, + "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/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/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/@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/@eslint/eslintrc": { + "version": "1.3.3", + "resolved": "https://registry.npmjs.org/@eslint/eslintrc/-/eslintrc-1.3.3.tgz", + "integrity": "sha512-uj3pT6Mg+3t39fvLrj8iuCIJ38zKO9FpGtJ4BBJebJhEwjoT+KLVNCcHT5QC9NGRIEi7fZ0ZR8YRb884auB4Lg==", + "dev": true, + "dependencies": { + "ajv": "^6.12.4", + "debug": "^4.3.2", + "espree": "^9.4.0", + "globals": "^13.15.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/@gar/promisify": { + "version": "1.1.3", + "resolved": "https://registry.npmjs.org/@gar/promisify/-/promisify-1.1.3.tgz", + "integrity": "sha512-k2Ty1JcVojjJFwrg/ThKi2ujJ7XNLYaFGNB/bWT9wGR+oSMJHMa5w+CUq6p/pVrKeNNgA7pCqEcjSnHVoqJQFw==", + "dev": true + }, + "node_modules/@humanwhocodes/config-array": { + "version": "0.10.7", + "resolved": "https://registry.npmjs.org/@humanwhocodes/config-array/-/config-array-0.10.7.tgz", + "integrity": "sha512-MDl6D6sBsaV452/QSdX+4CXIjZhIcI0PELsxUjk4U828yd58vk3bTIvk/6w5FY+4hIy9sLW0sfrV7K7Kc++j/w==", + "dev": true, + "dependencies": { + "@humanwhocodes/object-schema": "^1.2.1", + "debug": "^4.1.1", + "minimatch": "^3.0.4" + }, + "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/@hutson/parse-repository-url": { + "version": "3.0.2", + "resolved": "https://registry.npmjs.org/@hutson/parse-repository-url/-/parse-repository-url-3.0.2.tgz", + "integrity": "sha512-H9XAx3hc0BQHY6l+IFSWHDySypcXsvsuLhgYLUGywmJ5pswRVQJUHpOsobnLYp2ZUaUlKiKDrgWWhosOwAEM8Q==", + "dev": true, + "engines": { + "node": ">=6.9.0" + } + }, + "node_modules/@isaacs/string-locale-compare": { + "version": "1.1.0", + "resolved": "https://registry.npmjs.org/@isaacs/string-locale-compare/-/string-locale-compare-1.1.0.tgz", + "integrity": "sha512-SQ7Kzhh9+D+ZW9MA0zkYv3VXhIDNx+LzM6EJ+/65I3QY+enU6Itte7E5XX7EWrqLW2FN4n06GWzBnPoC3th2aQ==", + "dev": true + }, + "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/@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/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.16", + "resolved": "https://registry.npmjs.org/@jridgewell/trace-mapping/-/trace-mapping-0.3.16.tgz", + "integrity": "sha512-LCQ+NeThyJ4k1W2d+vIKdxuSt9R3pQSZ4P92m7EakaYuXcVWbHuT5bjNcqLd4Rdgi6xYWYDvBJZJLZSLanjDcA==", + "dev": true, + "dependencies": { + "@jridgewell/resolve-uri": "3.1.0", + "@jridgewell/sourcemap-codec": "1.4.14" + } + }, + "node_modules/@lerna/add": { + "version": "5.6.2", + "resolved": "https://registry.npmjs.org/@lerna/add/-/add-5.6.2.tgz", + "integrity": "sha512-NHrm7kYiqP+EviguY7/NltJ3G9vGmJW6v2BASUOhP9FZDhYbq3O+rCDlFdoVRNtcyrSg90rZFMOWHph4KOoCQQ==", + "dev": true, + "dependencies": { + "@lerna/bootstrap": "5.6.2", + "@lerna/command": "5.6.2", + "@lerna/filter-options": "5.6.2", + "@lerna/npm-conf": "5.6.2", + "@lerna/validation-error": "5.6.2", + "dedent": "^0.7.0", + "npm-package-arg": "8.1.1", + "p-map": "^4.0.0", + "pacote": "^13.6.1", + "semver": "^7.3.4" + }, + "engines": { + "node": "^14.15.0 || >=16.0.0" + } + }, + "node_modules/@lerna/bootstrap": { + "version": "5.6.2", + "resolved": "https://registry.npmjs.org/@lerna/bootstrap/-/bootstrap-5.6.2.tgz", + "integrity": "sha512-S2fMOEXbef7nrybQhzBywIGSLhuiQ5huPp1sU+v9Y6XEBsy/2IA+lb0gsZosvPqlRfMtiaFstL+QunaBhlWECA==", + "dev": true, + "dependencies": { + "@lerna/command": "5.6.2", + "@lerna/filter-options": "5.6.2", + "@lerna/has-npm-version": "5.6.2", + "@lerna/npm-install": "5.6.2", + "@lerna/package-graph": "5.6.2", + "@lerna/pulse-till-done": "5.6.2", + "@lerna/rimraf-dir": "5.6.2", + "@lerna/run-lifecycle": "5.6.2", + "@lerna/run-topologically": "5.6.2", + "@lerna/symlink-binary": "5.6.2", + "@lerna/symlink-dependencies": "5.6.2", + "@lerna/validation-error": "5.6.2", + "@npmcli/arborist": "5.3.0", + "dedent": "^0.7.0", + "get-port": "^5.1.1", + "multimatch": "^5.0.0", + "npm-package-arg": "8.1.1", + "npmlog": "^6.0.2", + "p-map": "^4.0.0", + "p-map-series": "^2.1.0", + "p-waterfall": "^2.1.1", + "semver": "^7.3.4" + }, + "engines": { + "node": "^14.15.0 || >=16.0.0" + } + }, + "node_modules/@lerna/changed": { + "version": "5.6.2", + "resolved": "https://registry.npmjs.org/@lerna/changed/-/changed-5.6.2.tgz", + "integrity": "sha512-uUgrkdj1eYJHQGsXXlpH5oEAfu3x0qzeTjgvpdNrxHEdQWi7zWiW59hRadmiImc14uJJYIwVK5q/QLugrsdGFQ==", + "dev": true, + "dependencies": { + "@lerna/collect-updates": "5.6.2", + "@lerna/command": "5.6.2", + "@lerna/listable": "5.6.2", + "@lerna/output": "5.6.2" + }, + "engines": { + "node": "^14.15.0 || >=16.0.0" + } + }, + "node_modules/@lerna/check-working-tree": { + "version": "5.6.2", + "resolved": "https://registry.npmjs.org/@lerna/check-working-tree/-/check-working-tree-5.6.2.tgz", + "integrity": "sha512-6Vf3IB6p+iNIubwVgr8A/KOmGh5xb4SyRmhFtAVqe33yWl2p3yc+mU5nGoz4ET3JLF1T9MhsePj0hNt6qyOTLQ==", + "dev": true, + "dependencies": { + "@lerna/collect-uncommitted": "5.6.2", + "@lerna/describe-ref": "5.6.2", + "@lerna/validation-error": "5.6.2" + }, + "engines": { + "node": "^14.15.0 || >=16.0.0" + } + }, + "node_modules/@lerna/child-process": { + "version": "5.6.2", + "resolved": "https://registry.npmjs.org/@lerna/child-process/-/child-process-5.6.2.tgz", + "integrity": "sha512-QIOQ3jIbWdduHd5892fbo3u7/dQgbhzEBB7cvf+Ys/iCPP8UQrBECi1lfRgA4kcTKC2MyMz0SoyXZz/lFcXc3A==", + "dev": true, + "dependencies": { + "chalk": "^4.1.0", + "execa": "^5.0.0", + "strong-log-transformer": "^2.1.0" + }, + "engines": { + "node": "^14.15.0 || >=16.0.0" + } + }, + "node_modules/@lerna/clean": { + "version": "5.6.2", + "resolved": "https://registry.npmjs.org/@lerna/clean/-/clean-5.6.2.tgz", + "integrity": "sha512-A7j8r0Hk2pGyLUyaCmx4keNHen1L/KdcOjb4nR6X8GtTJR5AeA47a8rRKOCz9wwdyMPlo2Dau7d3RV9viv7a5g==", + "dev": true, + "dependencies": { + "@lerna/command": "5.6.2", + "@lerna/filter-options": "5.6.2", + "@lerna/prompt": "5.6.2", + "@lerna/pulse-till-done": "5.6.2", + "@lerna/rimraf-dir": "5.6.2", + "p-map": "^4.0.0", + "p-map-series": "^2.1.0", + "p-waterfall": "^2.1.1" + }, + "engines": { + "node": "^14.15.0 || >=16.0.0" + } + }, + "node_modules/@lerna/cli": { + "version": "5.6.2", + "resolved": "https://registry.npmjs.org/@lerna/cli/-/cli-5.6.2.tgz", + "integrity": "sha512-w0NRIEqDOmYKlA5t0iyqx0hbY7zcozvApmfvwF0lhkuhf3k6LRAFSamtimGQWicC779a7J2NXw4ASuBV47Fs1Q==", + "dev": true, + "dependencies": { + "@lerna/global-options": "5.6.2", + "dedent": "^0.7.0", + "npmlog": "^6.0.2", + "yargs": "^16.2.0" + }, + "engines": { + "node": "^14.15.0 || >=16.0.0" + } + }, + "node_modules/@lerna/collect-uncommitted": { + "version": "5.6.2", + "resolved": "https://registry.npmjs.org/@lerna/collect-uncommitted/-/collect-uncommitted-5.6.2.tgz", + "integrity": "sha512-i0jhxpypyOsW2PpPwIw4xg6EPh7/N3YuiI6P2yL7PynZ8nOv8DkIdoyMkhUP4gALjBfckH8Bj94eIaKMviqW4w==", + "dev": true, + "dependencies": { + "@lerna/child-process": "5.6.2", + "chalk": "^4.1.0", + "npmlog": "^6.0.2" + }, + "engines": { + "node": "^14.15.0 || >=16.0.0" + } + }, + "node_modules/@lerna/collect-updates": { + "version": "5.6.2", + "resolved": "https://registry.npmjs.org/@lerna/collect-updates/-/collect-updates-5.6.2.tgz", + "integrity": "sha512-DdTK13X6PIsh9HINiMniFeiivAizR/1FBB+hDVe6tOhsXFBfjHMw1xZhXlE+mYIoFmDm1UFK7zvQSexoaxRqFA==", + "dev": true, + "dependencies": { + "@lerna/child-process": "5.6.2", + "@lerna/describe-ref": "5.6.2", + "minimatch": "^3.0.4", + "npmlog": "^6.0.2", + "slash": "^3.0.0" + }, + "engines": { + "node": "^14.15.0 || >=16.0.0" + } + }, + "node_modules/@lerna/command": { + "version": "5.6.2", + "resolved": "https://registry.npmjs.org/@lerna/command/-/command-5.6.2.tgz", + "integrity": "sha512-eLVGI9TmxcaGt1M7TXGhhBZoeWOtOedMiH7NuCGHtL6TMJ9k+SCExyx+KpNmE6ImyNOzws6EvYLPLjftiqmoaA==", + "dev": true, + "dependencies": { + "@lerna/child-process": "5.6.2", + "@lerna/package-graph": "5.6.2", + "@lerna/project": "5.6.2", + "@lerna/validation-error": "5.6.2", + "@lerna/write-log-file": "5.6.2", + "clone-deep": "^4.0.1", + "dedent": "^0.7.0", + "execa": "^5.0.0", + "is-ci": "^2.0.0", + "npmlog": "^6.0.2" + }, + "engines": { + "node": "^14.15.0 || >=16.0.0" + } + }, + "node_modules/@lerna/conventional-commits": { + "version": "5.6.2", + "resolved": "https://registry.npmjs.org/@lerna/conventional-commits/-/conventional-commits-5.6.2.tgz", + "integrity": "sha512-fPrJpYJhxCgY2uyOCTcAAC6+T6lUAtpEGxLbjWHWTb13oKKEygp9THoFpe6SbAD0fYMb3jeZCZCqNofM62rmuA==", + "dev": true, + "dependencies": { + "@lerna/validation-error": "5.6.2", + "conventional-changelog-angular": "^5.0.12", + "conventional-changelog-core": "^4.2.4", + "conventional-recommended-bump": "^6.1.0", + "fs-extra": "^9.1.0", + "get-stream": "^6.0.0", + "npm-package-arg": "8.1.1", + "npmlog": "^6.0.2", + "pify": "^5.0.0", + "semver": "^7.3.4" + }, + "engines": { + "node": "^14.15.0 || >=16.0.0" + } + }, + "node_modules/@lerna/create": { + "version": "5.6.2", + "resolved": "https://registry.npmjs.org/@lerna/create/-/create-5.6.2.tgz", + "integrity": "sha512-+Y5cMUxMNXjTTU9IHpgRYIwKo39w+blui1P+s+qYlZUSCUAew0xNpOBG8iN0Nc5X9op4U094oIdHxv7Dyz6tWQ==", + "dev": true, + "dependencies": { + "@lerna/child-process": "5.6.2", + "@lerna/command": "5.6.2", + "@lerna/npm-conf": "5.6.2", + "@lerna/validation-error": "5.6.2", + "dedent": "^0.7.0", + "fs-extra": "^9.1.0", + "init-package-json": "^3.0.2", + "npm-package-arg": "8.1.1", + "p-reduce": "^2.1.0", + "pacote": "^13.6.1", + "pify": "^5.0.0", + "semver": "^7.3.4", + "slash": "^3.0.0", + "validate-npm-package-license": "^3.0.4", + "validate-npm-package-name": "^4.0.0", + "yargs-parser": "20.2.4" + }, + "engines": { + "node": "^14.15.0 || >=16.0.0" + } + }, + "node_modules/@lerna/create-symlink": { + "version": "5.6.2", + "resolved": "https://registry.npmjs.org/@lerna/create-symlink/-/create-symlink-5.6.2.tgz", + "integrity": "sha512-0WIs3P6ohPVh2+t5axrLZDE5Dt7fe3Kv0Auj0sBiBd6MmKZ2oS76apIl0Bspdbv8jX8+TRKGv6ib0280D0dtEw==", + "dev": true, + "dependencies": { + "cmd-shim": "^5.0.0", + "fs-extra": "^9.1.0", + "npmlog": "^6.0.2" + }, + "engines": { + "node": "^14.15.0 || >=16.0.0" + } + }, + "node_modules/@lerna/create/node_modules/yargs-parser": { + "version": "20.2.4", + "resolved": "https://registry.npmjs.org/yargs-parser/-/yargs-parser-20.2.4.tgz", + "integrity": "sha512-WOkpgNhPTlE73h4VFAFsOnomJVaovO8VqLDzy5saChRBFQFBoMYirowyW+Q9HB4HFF4Z7VZTiG3iSzJJA29yRA==", + "dev": true, + "engines": { + "node": ">=10" + } + }, + "node_modules/@lerna/describe-ref": { + "version": "5.6.2", + "resolved": "https://registry.npmjs.org/@lerna/describe-ref/-/describe-ref-5.6.2.tgz", + "integrity": "sha512-UqU0N77aT1W8duYGir7R+Sk3jsY/c4lhcCEcnayMpFScMbAp0ETGsW04cYsHK29sgg+ZCc5zEwebBqabWhMhnA==", + "dev": true, + "dependencies": { + "@lerna/child-process": "5.6.2", + "npmlog": "^6.0.2" + }, + "engines": { + "node": "^14.15.0 || >=16.0.0" + } + }, + "node_modules/@lerna/diff": { + "version": "5.6.2", + "resolved": "https://registry.npmjs.org/@lerna/diff/-/diff-5.6.2.tgz", + "integrity": "sha512-aHKzKvUvUI8vOcshC2Za/bdz+plM3r/ycqUrPqaERzp+kc1pYHyPeXezydVdEmgmmwmyKI5hx4+2QNnzOnun2A==", + "dev": true, + "dependencies": { + "@lerna/child-process": "5.6.2", + "@lerna/command": "5.6.2", + "@lerna/validation-error": "5.6.2", + "npmlog": "^6.0.2" + }, + "engines": { + "node": "^14.15.0 || >=16.0.0" + } + }, + "node_modules/@lerna/exec": { + "version": "5.6.2", + "resolved": "https://registry.npmjs.org/@lerna/exec/-/exec-5.6.2.tgz", + "integrity": "sha512-meZozok5stK7S0oAVn+kdbTmU+kHj9GTXjW7V8kgwG9ld+JJMTH3nKK1L3mEKyk9TFu9vFWyEOF7HNK6yEOoVg==", + "dev": true, + "dependencies": { + "@lerna/child-process": "5.6.2", + "@lerna/command": "5.6.2", + "@lerna/filter-options": "5.6.2", + "@lerna/profiler": "5.6.2", + "@lerna/run-topologically": "5.6.2", + "@lerna/validation-error": "5.6.2", + "p-map": "^4.0.0" + }, + "engines": { + "node": "^14.15.0 || >=16.0.0" + } + }, + "node_modules/@lerna/filter-options": { + "version": "5.6.2", + "resolved": "https://registry.npmjs.org/@lerna/filter-options/-/filter-options-5.6.2.tgz", + "integrity": "sha512-4Z0HIhPak2TabTsUqEBQaQeOqgqEt0qyskvsY0oviYvqP/nrJfJBZh4H93jIiNQF59LJCn5Ce3KJJrLExxjlzw==", + "dev": true, + "dependencies": { + "@lerna/collect-updates": "5.6.2", + "@lerna/filter-packages": "5.6.2", + "dedent": "^0.7.0", + "npmlog": "^6.0.2" + }, + "engines": { + "node": "^14.15.0 || >=16.0.0" + } + }, + "node_modules/@lerna/filter-packages": { + "version": "5.6.2", + "resolved": "https://registry.npmjs.org/@lerna/filter-packages/-/filter-packages-5.6.2.tgz", + "integrity": "sha512-el9V2lTEG0Bbz+Omo45hATkRVnChCTJhcTpth19cMJ6mQ4M5H4IgbWCJdFMBi/RpTnOhz9BhJxDbj95kuIvvzw==", + "dev": true, + "dependencies": { + "@lerna/validation-error": "5.6.2", + "multimatch": "^5.0.0", + "npmlog": "^6.0.2" + }, + "engines": { + "node": "^14.15.0 || >=16.0.0" + } + }, + "node_modules/@lerna/get-npm-exec-opts": { + "version": "5.6.2", + "resolved": "https://registry.npmjs.org/@lerna/get-npm-exec-opts/-/get-npm-exec-opts-5.6.2.tgz", + "integrity": "sha512-0RbSDJ+QC9D5UWZJh3DN7mBIU1NhBmdHOE289oHSkjDY+uEjdzMPkEUy+wZ8fCzMLFnnNQkAEqNaOAzZ7dmFLA==", + "dev": true, + "dependencies": { + "npmlog": "^6.0.2" + }, + "engines": { + "node": "^14.15.0 || >=16.0.0" + } + }, + "node_modules/@lerna/get-packed": { + "version": "5.6.2", + "resolved": "https://registry.npmjs.org/@lerna/get-packed/-/get-packed-5.6.2.tgz", + "integrity": "sha512-pp5nNDmtrtd21aKHjwwOY5CS7XNIHxINzGa+Jholn1jMDYUtdskpN++ZqYbATGpW831++NJuiuBVyqAWi9xbXg==", + "dev": true, + "dependencies": { + "fs-extra": "^9.1.0", + "ssri": "^9.0.1", + "tar": "^6.1.0" + }, + "engines": { + "node": "^14.15.0 || >=16.0.0" + } + }, + "node_modules/@lerna/github-client": { + "version": "5.6.2", + "resolved": "https://registry.npmjs.org/@lerna/github-client/-/github-client-5.6.2.tgz", + "integrity": "sha512-pjALazZoRZtKqfwLBwmW3HPptVhQm54PvA8s3qhCQ+3JkqrZiIFwkkxNZxs3jwzr+aaSOzfhSzCndg0urb0GXA==", + "dev": true, + "dependencies": { + "@lerna/child-process": "5.6.2", + "@octokit/plugin-enterprise-rest": "^6.0.1", + "@octokit/rest": "^19.0.3", + "git-url-parse": "^13.1.0", + "npmlog": "^6.0.2" + }, + "engines": { + "node": "^14.15.0 || >=16.0.0" + } + }, + "node_modules/@lerna/gitlab-client": { + "version": "5.6.2", + "resolved": "https://registry.npmjs.org/@lerna/gitlab-client/-/gitlab-client-5.6.2.tgz", + "integrity": "sha512-TInJmbrsmYIwUyrRxytjO82KjJbRwm67F7LoZs1shAq6rMvNqi4NxSY9j+hT/939alFmEq1zssoy/caeLXHRfQ==", + "dev": true, + "dependencies": { + "node-fetch": "^2.6.1", + "npmlog": "^6.0.2" + }, + "engines": { + "node": "^14.15.0 || >=16.0.0" + } + }, + "node_modules/@lerna/global-options": { + "version": "5.6.2", + "resolved": "https://registry.npmjs.org/@lerna/global-options/-/global-options-5.6.2.tgz", + "integrity": "sha512-kaKELURXTlczthNJskdOvh6GGMyt24qat0xMoJZ8plYMdofJfhz24h1OFcvB/EwCUwP/XV1+ohE5P+vdktbrEg==", + "dev": true, + "engines": { + "node": "^14.15.0 || >=16.0.0" + } + }, + "node_modules/@lerna/has-npm-version": { + "version": "5.6.2", + "resolved": "https://registry.npmjs.org/@lerna/has-npm-version/-/has-npm-version-5.6.2.tgz", + "integrity": "sha512-kXCnSzffmTWsaK0ol30coyCfO8WH26HFbmJjRBzKv7VGkuAIcB6gX2gqRRgNLLlvI+Yrp+JSlpVNVnu15SEH2g==", + "dev": true, + "dependencies": { + "@lerna/child-process": "5.6.2", + "semver": "^7.3.4" + }, + "engines": { + "node": "^14.15.0 || >=16.0.0" + } + }, + "node_modules/@lerna/import": { + "version": "5.6.2", + "resolved": "https://registry.npmjs.org/@lerna/import/-/import-5.6.2.tgz", + "integrity": "sha512-xQUE49mtcP0z3KUdXBsyvp8rGDz6phuYUoQbhcFRJ7WPcQKzMvtm0XYrER6c2YWEX7QOuDac6tU82P8zTrTBaA==", + "dev": true, + "dependencies": { + "@lerna/child-process": "5.6.2", + "@lerna/command": "5.6.2", + "@lerna/prompt": "5.6.2", + "@lerna/pulse-till-done": "5.6.2", + "@lerna/validation-error": "5.6.2", + "dedent": "^0.7.0", + "fs-extra": "^9.1.0", + "p-map-series": "^2.1.0" + }, + "engines": { + "node": "^14.15.0 || >=16.0.0" + } + }, + "node_modules/@lerna/info": { + "version": "5.6.2", + "resolved": "https://registry.npmjs.org/@lerna/info/-/info-5.6.2.tgz", + "integrity": "sha512-MPjY5Olj+fiZHgfEdwXUFRKamdEuLr9Ob/qut8JsB/oQSQ4ALdQfnrOcMT8lJIcC2R67EA5yav2lHPBIkezm8A==", + "dev": true, + "dependencies": { + "@lerna/command": "5.6.2", + "@lerna/output": "5.6.2", + "envinfo": "^7.7.4" + }, + "engines": { + "node": "^14.15.0 || >=16.0.0" + } + }, + "node_modules/@lerna/init": { + "version": "5.6.2", + "resolved": "https://registry.npmjs.org/@lerna/init/-/init-5.6.2.tgz", + "integrity": "sha512-ahU3/lgF+J8kdJAQysihFJROHthkIDXfHmvhw7AYnzf94HjxGNXj7nz6i3At1/dM/1nQhR+4/uNR1/OU4tTYYQ==", + "dev": true, + "dependencies": { + "@lerna/child-process": "5.6.2", + "@lerna/command": "5.6.2", + "@lerna/project": "5.6.2", + "fs-extra": "^9.1.0", + "p-map": "^4.0.0", + "write-json-file": "^4.3.0" + }, + "engines": { + "node": "^14.15.0 || >=16.0.0" + } + }, + "node_modules/@lerna/link": { + "version": "5.6.2", + "resolved": "https://registry.npmjs.org/@lerna/link/-/link-5.6.2.tgz", + "integrity": "sha512-hXxQ4R3z6rUF1v2x62oIzLyeHL96u7ZBhxqYMJrm763D1VMSDcHKF9CjJfc6J9vH5Z2ZbL6CQg50Hw5mUpJbjg==", + "dev": true, + "dependencies": { + "@lerna/command": "5.6.2", + "@lerna/package-graph": "5.6.2", + "@lerna/symlink-dependencies": "5.6.2", + "@lerna/validation-error": "5.6.2", + "p-map": "^4.0.0", + "slash": "^3.0.0" + }, + "engines": { + "node": "^14.15.0 || >=16.0.0" + } + }, + "node_modules/@lerna/list": { + "version": "5.6.2", + "resolved": "https://registry.npmjs.org/@lerna/list/-/list-5.6.2.tgz", + "integrity": "sha512-WjE5O2tQ3TcS+8LqXUaxi0YdldhxUhNihT5+Gg4vzGdIlrPDioO50Zjo9d8jOU7i3LMIk6EzCma0sZr2CVfEGg==", + "dev": true, + "dependencies": { + "@lerna/command": "5.6.2", + "@lerna/filter-options": "5.6.2", + "@lerna/listable": "5.6.2", + "@lerna/output": "5.6.2" + }, + "engines": { + "node": "^14.15.0 || >=16.0.0" + } + }, + "node_modules/@lerna/listable": { + "version": "5.6.2", + "resolved": "https://registry.npmjs.org/@lerna/listable/-/listable-5.6.2.tgz", + "integrity": "sha512-8Yp49BwkY/5XqVru38Zko+6Wj/sgbwzJfIGEPy3Qu575r1NA/b9eI1gX22aMsEeXUeGOybR7nWT5ewnPQHjqvA==", + "dev": true, + "dependencies": { + "@lerna/query-graph": "5.6.2", + "chalk": "^4.1.0", + "columnify": "^1.6.0" + }, + "engines": { + "node": "^14.15.0 || >=16.0.0" + } + }, + "node_modules/@lerna/log-packed": { + "version": "5.6.2", + "resolved": "https://registry.npmjs.org/@lerna/log-packed/-/log-packed-5.6.2.tgz", + "integrity": "sha512-O9GODG7tMtWk+2fufn2MOkIDBYMRoKBhYMHshO5Aw/VIsH76DIxpX1koMzWfUngM/C70R4uNAKcVWineX4qzIw==", + "dev": true, + "dependencies": { + "byte-size": "^7.0.0", + "columnify": "^1.6.0", + "has-unicode": "^2.0.1", + "npmlog": "^6.0.2" + }, + "engines": { + "node": "^14.15.0 || >=16.0.0" + } + }, + "node_modules/@lerna/npm-conf": { + "version": "5.6.2", + "resolved": "https://registry.npmjs.org/@lerna/npm-conf/-/npm-conf-5.6.2.tgz", + "integrity": "sha512-gWDPhw1wjXYXphk/PAghTLexO5T6abVFhXb+KOMCeem366mY0F5bM88PiorL73aErTNUoR8n+V4X29NTZzDZpQ==", + "dev": true, + "dependencies": { + "config-chain": "^1.1.12", + "pify": "^5.0.0" + }, + "engines": { + "node": "^14.15.0 || >=16.0.0" + } + }, + "node_modules/@lerna/npm-dist-tag": { + "version": "5.6.2", + "resolved": "https://registry.npmjs.org/@lerna/npm-dist-tag/-/npm-dist-tag-5.6.2.tgz", + "integrity": "sha512-t2RmxV6Eog4acXkUI+EzWuYVbeVVY139pANIWS9qtdajfgp4GVXZi1S8mAIb70yeHdNpCp1mhK0xpCrFH9LvGQ==", + "dev": true, + "dependencies": { + "@lerna/otplease": "5.6.2", + "npm-package-arg": "8.1.1", + "npm-registry-fetch": "^13.3.0", + "npmlog": "^6.0.2" + }, + "engines": { + "node": "^14.15.0 || >=16.0.0" + } + }, + "node_modules/@lerna/npm-install": { + "version": "5.6.2", + "resolved": "https://registry.npmjs.org/@lerna/npm-install/-/npm-install-5.6.2.tgz", + "integrity": "sha512-AT226zdEo+uGENd37jwYgdALKJAIJK4pNOfmXWZWzVb9oMOr8I2YSjPYvSYUNG7gOo2YJQU8x5Zd7OShv2924Q==", + "dev": true, + "dependencies": { + "@lerna/child-process": "5.6.2", + "@lerna/get-npm-exec-opts": "5.6.2", + "fs-extra": "^9.1.0", + "npm-package-arg": "8.1.1", + "npmlog": "^6.0.2", + "signal-exit": "^3.0.3", + "write-pkg": "^4.0.0" + }, + "engines": { + "node": "^14.15.0 || >=16.0.0" + } + }, + "node_modules/@lerna/npm-publish": { + "version": "5.6.2", + "resolved": "https://registry.npmjs.org/@lerna/npm-publish/-/npm-publish-5.6.2.tgz", + "integrity": "sha512-ldSyewCfv9fAeC5xNjL0HKGSUxcC048EJoe/B+KRUmd+IPidvZxMEzRu08lSC/q3V9YeUv9ZvRnxATXOM8CffA==", + "dev": true, + "dependencies": { + "@lerna/otplease": "5.6.2", + "@lerna/run-lifecycle": "5.6.2", + "fs-extra": "^9.1.0", + "libnpmpublish": "^6.0.4", + "npm-package-arg": "8.1.1", + "npmlog": "^6.0.2", + "pify": "^5.0.0", + "read-package-json": "^5.0.1" + }, + "engines": { + "node": "^14.15.0 || >=16.0.0" + } + }, + "node_modules/@lerna/npm-run-script": { + "version": "5.6.2", + "resolved": "https://registry.npmjs.org/@lerna/npm-run-script/-/npm-run-script-5.6.2.tgz", + "integrity": "sha512-MOQoWNcAyJivM8SYp0zELM7vg/Dj07j4YMdxZkey+S1UO0T4/vKBxb575o16hH4WeNzC3Pd7WBlb7C8dLOfNwQ==", + "dev": true, + "dependencies": { + "@lerna/child-process": "5.6.2", + "@lerna/get-npm-exec-opts": "5.6.2", + "npmlog": "^6.0.2" + }, + "engines": { + "node": "^14.15.0 || >=16.0.0" + } + }, + "node_modules/@lerna/otplease": { + "version": "5.6.2", + "resolved": "https://registry.npmjs.org/@lerna/otplease/-/otplease-5.6.2.tgz", + "integrity": "sha512-dGS4lzkEQVTMAgji82jp8RK6UK32wlzrBAO4P4iiVHCUTuwNLsY9oeBXvVXSMrosJnl6Hbe0NOvi43mqSucGoA==", + "dev": true, + "dependencies": { + "@lerna/prompt": "5.6.2" + }, + "engines": { + "node": "^14.15.0 || >=16.0.0" + } + }, + "node_modules/@lerna/output": { + "version": "5.6.2", + "resolved": "https://registry.npmjs.org/@lerna/output/-/output-5.6.2.tgz", + "integrity": "sha512-++d+bfOQwY66yo7q1XuAvRcqtRHCG45e/awP5xQomTZ6R1rhWiZ3whWdc9Z6lF7+UtBB9toSYYffKU/xc3L0yQ==", + "dev": true, + "dependencies": { + "npmlog": "^6.0.2" + }, + "engines": { + "node": "^14.15.0 || >=16.0.0" + } + }, + "node_modules/@lerna/pack-directory": { + "version": "5.6.2", + "resolved": "https://registry.npmjs.org/@lerna/pack-directory/-/pack-directory-5.6.2.tgz", + "integrity": "sha512-w5Jk5fo+HkN4Le7WMOudTcmAymcf0xPd302TqAQncjXpk0cb8tZbj+5bbNHsGb58GRjOIm5icQbHXooQUxbHhA==", + "dev": true, + "dependencies": { + "@lerna/get-packed": "5.6.2", + "@lerna/package": "5.6.2", + "@lerna/run-lifecycle": "5.6.2", + "@lerna/temp-write": "5.6.2", + "npm-packlist": "^5.1.1", + "npmlog": "^6.0.2", + "tar": "^6.1.0" + }, + "engines": { + "node": "^14.15.0 || >=16.0.0" + } + }, + "node_modules/@lerna/package": { + "version": "5.6.2", + "resolved": "https://registry.npmjs.org/@lerna/package/-/package-5.6.2.tgz", + "integrity": "sha512-LaOC8moyM5J9WnRiWZkedjOninSclBOJyPqhif6mHb2kCFX6jAroNYzE8KM4cphu8CunHuhI6Ixzswtv+Dultw==", + "dev": true, + "dependencies": { + "load-json-file": "^6.2.0", + "npm-package-arg": "8.1.1", + "write-pkg": "^4.0.0" + }, + "engines": { + "node": "^14.15.0 || >=16.0.0" + } + }, + "node_modules/@lerna/package-graph": { + "version": "5.6.2", + "resolved": "https://registry.npmjs.org/@lerna/package-graph/-/package-graph-5.6.2.tgz", + "integrity": "sha512-TmL61qBBvA3Tc4qICDirZzdFFwWOA6qicIXUruLiE2PblRowRmCO1bKrrP6XbDOspzwrkPef6N2F2/5gHQAnkQ==", + "dev": true, + "dependencies": { + "@lerna/prerelease-id-from-version": "5.6.2", + "@lerna/validation-error": "5.6.2", + "npm-package-arg": "8.1.1", + "npmlog": "^6.0.2", + "semver": "^7.3.4" + }, + "engines": { + "node": "^14.15.0 || >=16.0.0" + } + }, + "node_modules/@lerna/prerelease-id-from-version": { + "version": "5.6.2", + "resolved": "https://registry.npmjs.org/@lerna/prerelease-id-from-version/-/prerelease-id-from-version-5.6.2.tgz", + "integrity": "sha512-7gIm9fecWFVNy2kpj/KbH11bRcpyANAwpsft3X5m6J7y7A6FTUscCbEvl3ZNdpQKHNuvnHgCtkm3A5PMSCEgkA==", + "dev": true, + "dependencies": { + "semver": "^7.3.4" + }, + "engines": { + "node": "^14.15.0 || >=16.0.0" + } + }, + "node_modules/@lerna/profiler": { + "version": "5.6.2", + "resolved": "https://registry.npmjs.org/@lerna/profiler/-/profiler-5.6.2.tgz", + "integrity": "sha512-okwkagP5zyRIOYTceu/9/esW7UZFt7lyL6q6ZgpSG3TYC5Ay+FXLtS6Xiha/FQdVdumFqKULDWTGovzUlxcwaw==", + "dev": true, + "dependencies": { + "fs-extra": "^9.1.0", + "npmlog": "^6.0.2", + "upath": "^2.0.1" + }, + "engines": { + "node": "^14.15.0 || >=16.0.0" + } + }, + "node_modules/@lerna/project": { + "version": "5.6.2", + "resolved": "https://registry.npmjs.org/@lerna/project/-/project-5.6.2.tgz", + "integrity": "sha512-kPIMcIy/0DVWM91FPMMFmXyAnCuuLm3NdhnA8NusE//VuY9wC6QC/3OwuCY39b2dbko/fPZheqKeAZkkMH6sGg==", + "dev": true, + "dependencies": { + "@lerna/package": "5.6.2", + "@lerna/validation-error": "5.6.2", + "cosmiconfig": "^7.0.0", + "dedent": "^0.7.0", + "dot-prop": "^6.0.1", + "glob-parent": "^5.1.1", + "globby": "^11.0.2", + "js-yaml": "^4.1.0", + "load-json-file": "^6.2.0", + "npmlog": "^6.0.2", + "p-map": "^4.0.0", + "resolve-from": "^5.0.0", + "write-json-file": "^4.3.0" + }, + "engines": { + "node": "^14.15.0 || >=16.0.0" + } + }, + "node_modules/@lerna/project/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/@lerna/project/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/@lerna/prompt": { + "version": "5.6.2", + "resolved": "https://registry.npmjs.org/@lerna/prompt/-/prompt-5.6.2.tgz", + "integrity": "sha512-4hTNmVYADEr0GJTMegWV+GW6n+dzKx1vN9v2ISqyle283Myv930WxuyO0PeYGqTrkneJsyPreCMovuEGCvZ0iQ==", + "dev": true, + "dependencies": { + "inquirer": "^8.2.4", + "npmlog": "^6.0.2" + }, + "engines": { + "node": "^14.15.0 || >=16.0.0" + } + }, + "node_modules/@lerna/publish": { + "version": "5.6.2", + "resolved": "https://registry.npmjs.org/@lerna/publish/-/publish-5.6.2.tgz", + "integrity": "sha512-QaW0GjMJMuWlRNjeDCjmY/vjriGSWgkLS23yu8VKNtV5U3dt5yIKA3DNGV3HgZACuu45kQxzMDsfLzgzbGNtYA==", + "dev": true, + "dependencies": { + "@lerna/check-working-tree": "5.6.2", + "@lerna/child-process": "5.6.2", + "@lerna/collect-updates": "5.6.2", + "@lerna/command": "5.6.2", + "@lerna/describe-ref": "5.6.2", + "@lerna/log-packed": "5.6.2", + "@lerna/npm-conf": "5.6.2", + "@lerna/npm-dist-tag": "5.6.2", + "@lerna/npm-publish": "5.6.2", + "@lerna/otplease": "5.6.2", + "@lerna/output": "5.6.2", + "@lerna/pack-directory": "5.6.2", + "@lerna/prerelease-id-from-version": "5.6.2", + "@lerna/prompt": "5.6.2", + "@lerna/pulse-till-done": "5.6.2", + "@lerna/run-lifecycle": "5.6.2", + "@lerna/run-topologically": "5.6.2", + "@lerna/validation-error": "5.6.2", + "@lerna/version": "5.6.2", + "fs-extra": "^9.1.0", + "libnpmaccess": "^6.0.3", + "npm-package-arg": "8.1.1", + "npm-registry-fetch": "^13.3.0", + "npmlog": "^6.0.2", + "p-map": "^4.0.0", + "p-pipe": "^3.1.0", + "pacote": "^13.6.1", + "semver": "^7.3.4" + }, + "engines": { + "node": "^14.15.0 || >=16.0.0" + } + }, + "node_modules/@lerna/pulse-till-done": { + "version": "5.6.2", + "resolved": "https://registry.npmjs.org/@lerna/pulse-till-done/-/pulse-till-done-5.6.2.tgz", + "integrity": "sha512-eA/X1RCxU5YGMNZmbgPi+Kyfx1Q3bn4P9jo/LZy+/NRRr1po3ASXP2GJZ1auBh/9A2ELDvvKTOXCVHqczKC6rA==", + "dev": true, + "dependencies": { + "npmlog": "^6.0.2" + }, + "engines": { + "node": "^14.15.0 || >=16.0.0" + } + }, + "node_modules/@lerna/query-graph": { + "version": "5.6.2", + "resolved": "https://registry.npmjs.org/@lerna/query-graph/-/query-graph-5.6.2.tgz", + "integrity": "sha512-KRngr96yBP8XYDi9/U62fnGO+ZXqm04Qk6a2HtoTr/ha8QvO1s7Tgm0xs/G7qWXDQHZgunWIbmK/LhxM7eFQrw==", + "dev": true, + "dependencies": { + "@lerna/package-graph": "5.6.2" + }, + "engines": { + "node": "^14.15.0 || >=16.0.0" + } + }, + "node_modules/@lerna/resolve-symlink": { + "version": "5.6.2", + "resolved": "https://registry.npmjs.org/@lerna/resolve-symlink/-/resolve-symlink-5.6.2.tgz", + "integrity": "sha512-PDQy+7M8JEFtwIVHJgWvSxHkxJf9zXCENkvIWDB+SsoDPhw9+caewt46bTeP5iGm9pOMu3oZukaWo/TvF7sNjg==", + "dev": true, + "dependencies": { + "fs-extra": "^9.1.0", + "npmlog": "^6.0.2", + "read-cmd-shim": "^3.0.0" + }, + "engines": { + "node": "^14.15.0 || >=16.0.0" + } + }, + "node_modules/@lerna/rimraf-dir": { + "version": "5.6.2", + "resolved": "https://registry.npmjs.org/@lerna/rimraf-dir/-/rimraf-dir-5.6.2.tgz", + "integrity": "sha512-jgEfzz7uBUiQKteq3G8MtJiA2D2VoKmZSSY3VSiW/tPOSXYxxSHxEsClQdCeNa6+sYrDNDT8fP6MJ3lPLjDeLA==", + "dev": true, + "dependencies": { + "@lerna/child-process": "5.6.2", + "npmlog": "^6.0.2", + "path-exists": "^4.0.0", + "rimraf": "^3.0.2" + }, + "engines": { + "node": "^14.15.0 || >=16.0.0" + } + }, + "node_modules/@lerna/run": { + "version": "5.6.2", + "resolved": "https://registry.npmjs.org/@lerna/run/-/run-5.6.2.tgz", + "integrity": "sha512-c2kJxdFrNg5KOkrhmgwKKUOsfSrGNlFCe26EttufOJ3xfY0VnXlEw9rHOkTgwtu7969rfCdyaVP1qckMrF1Dgw==", + "dev": true, + "dependencies": { + "@lerna/command": "5.6.2", + "@lerna/filter-options": "5.6.2", + "@lerna/npm-run-script": "5.6.2", + "@lerna/output": "5.6.2", + "@lerna/profiler": "5.6.2", + "@lerna/run-topologically": "5.6.2", + "@lerna/timer": "5.6.2", + "@lerna/validation-error": "5.6.2", + "fs-extra": "^9.1.0", + "p-map": "^4.0.0" + }, + "engines": { + "node": "^14.15.0 || >=16.0.0" + } + }, + "node_modules/@lerna/run-lifecycle": { + "version": "5.6.2", + "resolved": "https://registry.npmjs.org/@lerna/run-lifecycle/-/run-lifecycle-5.6.2.tgz", + "integrity": "sha512-u9gGgq/50Fm8dvfcc/TSHOCAQvzLD7poVanDMhHYWOAqRDnellJEEmA1K/Yka4vZmySrzluahkry9G6jcREt+g==", + "dev": true, + "dependencies": { + "@lerna/npm-conf": "5.6.2", + "@npmcli/run-script": "^4.1.7", + "npmlog": "^6.0.2", + "p-queue": "^6.6.2" + }, + "engines": { + "node": "^14.15.0 || >=16.0.0" + } + }, + "node_modules/@lerna/run-topologically": { + "version": "5.6.2", + "resolved": "https://registry.npmjs.org/@lerna/run-topologically/-/run-topologically-5.6.2.tgz", + "integrity": "sha512-QQ/jGOIsVvUg3izShWsd67RlWYh9UOH2yw97Ol1zySX9+JspCMVQrn9eKq1Pk8twQOFhT87LpT/aaxbTBgREPw==", + "dev": true, + "dependencies": { + "@lerna/query-graph": "5.6.2", + "p-queue": "^6.6.2" + }, + "engines": { + "node": "^14.15.0 || >=16.0.0" + } + }, + "node_modules/@lerna/symlink-binary": { + "version": "5.6.2", + "resolved": "https://registry.npmjs.org/@lerna/symlink-binary/-/symlink-binary-5.6.2.tgz", + "integrity": "sha512-Cth+miwYyO81WAmrQbPBrLHuF+F0UUc0el5kRXLH6j5zzaRS3kMM68r40M7MmfH8m3GPi7691UARoWFEotW5jw==", + "dev": true, + "dependencies": { + "@lerna/create-symlink": "5.6.2", + "@lerna/package": "5.6.2", + "fs-extra": "^9.1.0", + "p-map": "^4.0.0" + }, + "engines": { + "node": "^14.15.0 || >=16.0.0" + } + }, + "node_modules/@lerna/symlink-dependencies": { + "version": "5.6.2", + "resolved": "https://registry.npmjs.org/@lerna/symlink-dependencies/-/symlink-dependencies-5.6.2.tgz", + "integrity": "sha512-dUVNQLEcjVOIQiT9OlSAKt0ykjyJPy8l9i4NJDe2/0XYaUjo8PWsxJ0vrutz27jzi2aZUy07ASmowQZEmnLHAw==", + "dev": true, + "dependencies": { + "@lerna/create-symlink": "5.6.2", + "@lerna/resolve-symlink": "5.6.2", + "@lerna/symlink-binary": "5.6.2", + "fs-extra": "^9.1.0", + "p-map": "^4.0.0", + "p-map-series": "^2.1.0" + }, + "engines": { + "node": "^14.15.0 || >=16.0.0" + } + }, + "node_modules/@lerna/temp-write": { + "version": "5.6.2", + "resolved": "https://registry.npmjs.org/@lerna/temp-write/-/temp-write-5.6.2.tgz", + "integrity": "sha512-S5ZNVTurSwWBmc9kh5alfSjmO3+BnRT6shYtOlmVIUYqWeYVYA5C1Htj322bbU4CSNCMFK6NQl4qGKL17HMuig==", + "dev": true, + "dependencies": { + "graceful-fs": "^4.1.15", + "is-stream": "^2.0.0", + "make-dir": "^3.0.0", + "temp-dir": "^1.0.0", + "uuid": "^8.3.2" + } + }, + "node_modules/@lerna/temp-write/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/@lerna/timer": { + "version": "5.6.2", + "resolved": "https://registry.npmjs.org/@lerna/timer/-/timer-5.6.2.tgz", + "integrity": "sha512-AjMOiLc2B+5Nzdd9hNORetAdZ/WK8YNGX/+2ypzM68TMAPfIT5C40hMlSva9Yg4RsBz22REopXgM5s2zQd5ZQA==", + "dev": true, + "engines": { + "node": "^14.15.0 || >=16.0.0" + } + }, + "node_modules/@lerna/validation-error": { + "version": "5.6.2", + "resolved": "https://registry.npmjs.org/@lerna/validation-error/-/validation-error-5.6.2.tgz", + "integrity": "sha512-4WlDUHaa+RSJNyJRtX3gVIAPVzjZD2tle8AJ0ZYBfdZnZmG0VlB2pD1FIbOQPK8sY2h5m0cHLRvfLoLncqHvdQ==", + "dev": true, + "dependencies": { + "npmlog": "^6.0.2" + }, + "engines": { + "node": "^14.15.0 || >=16.0.0" + } + }, + "node_modules/@lerna/version": { + "version": "5.6.2", + "resolved": "https://registry.npmjs.org/@lerna/version/-/version-5.6.2.tgz", + "integrity": "sha512-odNSR2rTbHW++xMZSQKu/F6Syrd/sUvwDLPaMKktoOSPKmycHt/eWcuQQyACdtc43Iqeu4uQd7PCLsniqOVFrw==", + "dev": true, + "dependencies": { + "@lerna/check-working-tree": "5.6.2", + "@lerna/child-process": "5.6.2", + "@lerna/collect-updates": "5.6.2", + "@lerna/command": "5.6.2", + "@lerna/conventional-commits": "5.6.2", + "@lerna/github-client": "5.6.2", + "@lerna/gitlab-client": "5.6.2", + "@lerna/output": "5.6.2", + "@lerna/prerelease-id-from-version": "5.6.2", + "@lerna/prompt": "5.6.2", + "@lerna/run-lifecycle": "5.6.2", + "@lerna/run-topologically": "5.6.2", + "@lerna/temp-write": "5.6.2", + "@lerna/validation-error": "5.6.2", + "@nrwl/devkit": ">=14.8.1 < 16", + "chalk": "^4.1.0", + "dedent": "^0.7.0", + "load-json-file": "^6.2.0", + "minimatch": "^3.0.4", + "npmlog": "^6.0.2", + "p-map": "^4.0.0", + "p-pipe": "^3.1.0", + "p-reduce": "^2.1.0", + "p-waterfall": "^2.1.1", + "semver": "^7.3.4", + "slash": "^3.0.0", + "write-json-file": "^4.3.0" + }, + "engines": { + "node": "^14.15.0 || >=16.0.0" + } + }, + "node_modules/@lerna/write-log-file": { + "version": "5.6.2", + "resolved": "https://registry.npmjs.org/@lerna/write-log-file/-/write-log-file-5.6.2.tgz", + "integrity": "sha512-J09l18QnWQ3sXIRwuJkjXY3+KwPR2uO5NgbZGE3GXJK1V/LzOBRMvjGAIbuQHXw25uqe7vpLUpB8drtnFrubCQ==", + "dev": true, + "dependencies": { + "npmlog": "^6.0.2", + "write-file-atomic": "^4.0.1" + }, + "engines": { + "node": "^14.15.0 || >=16.0.0" + } + }, + "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/@npmcli/arborist": { + "version": "5.3.0", + "resolved": "https://registry.npmjs.org/@npmcli/arborist/-/arborist-5.3.0.tgz", + "integrity": "sha512-+rZ9zgL1lnbl8Xbb1NQdMjveOMwj4lIYfcDtyJHHi5x4X8jtR6m8SXooJMZy5vmFVZ8w7A2Bnd/oX9eTuU8w5A==", + "dev": true, + "dependencies": { + "@isaacs/string-locale-compare": "^1.1.0", + "@npmcli/installed-package-contents": "^1.0.7", + "@npmcli/map-workspaces": "^2.0.3", + "@npmcli/metavuln-calculator": "^3.0.1", + "@npmcli/move-file": "^2.0.0", + "@npmcli/name-from-folder": "^1.0.1", + "@npmcli/node-gyp": "^2.0.0", + "@npmcli/package-json": "^2.0.0", + "@npmcli/run-script": "^4.1.3", + "bin-links": "^3.0.0", + "cacache": "^16.0.6", + "common-ancestor-path": "^1.0.1", + "json-parse-even-better-errors": "^2.3.1", + "json-stringify-nice": "^1.1.4", + "mkdirp": "^1.0.4", + "mkdirp-infer-owner": "^2.0.0", + "nopt": "^5.0.0", + "npm-install-checks": "^5.0.0", + "npm-package-arg": "^9.0.0", + "npm-pick-manifest": "^7.0.0", + "npm-registry-fetch": "^13.0.0", + "npmlog": "^6.0.2", + "pacote": "^13.6.1", + "parse-conflict-json": "^2.0.1", + "proc-log": "^2.0.0", + "promise-all-reject-late": "^1.0.0", + "promise-call-limit": "^1.0.1", + "read-package-json-fast": "^2.0.2", + "readdir-scoped-modules": "^1.1.0", + "rimraf": "^3.0.2", + "semver": "^7.3.7", + "ssri": "^9.0.0", + "treeverse": "^2.0.0", + "walk-up-path": "^1.0.0" + }, + "bin": { + "arborist": "bin/index.js" + }, + "engines": { + "node": "^12.13.0 || ^14.15.0 || >=16.0.0" + } + }, + "node_modules/@npmcli/arborist/node_modules/hosted-git-info": { + "version": "5.1.0", + "resolved": "https://registry.npmjs.org/hosted-git-info/-/hosted-git-info-5.1.0.tgz", + "integrity": "sha512-Ek+QmMEqZF8XrbFdwoDjSbm7rT23pCgEMOJmz6GPk/s4yH//RQfNPArhIxbguNxROq/+5lNBwCDHMhA903Kx1Q==", + "dev": true, + "dependencies": { + "lru-cache": "^7.5.1" + }, + "engines": { + "node": "^12.13.0 || ^14.15.0 || >=16.0.0" + } + }, + "node_modules/@npmcli/arborist/node_modules/npm-package-arg": { + "version": "9.1.2", + "resolved": "https://registry.npmjs.org/npm-package-arg/-/npm-package-arg-9.1.2.tgz", + "integrity": "sha512-pzd9rLEx4TfNJkovvlBSLGhq31gGu2QDexFPWT19yCDh0JgnRhlBLNo5759N0AJmBk+kQ9Y/hXoLnlgFD+ukmg==", + "dev": true, + "dependencies": { + "hosted-git-info": "^5.0.0", + "proc-log": "^2.0.1", + "semver": "^7.3.5", + "validate-npm-package-name": "^4.0.0" + }, + "engines": { + "node": "^12.13.0 || ^14.15.0 || >=16.0.0" + } + }, + "node_modules/@npmcli/fs": { + "version": "2.1.2", + "resolved": "https://registry.npmjs.org/@npmcli/fs/-/fs-2.1.2.tgz", + "integrity": "sha512-yOJKRvohFOaLqipNtwYB9WugyZKhC/DZC4VYPmpaCzDBrA8YpK3qHZ8/HGscMnE4GqbkLNuVcCnxkeQEdGt6LQ==", + "dev": true, + "dependencies": { + "@gar/promisify": "^1.1.3", + "semver": "^7.3.5" + }, + "engines": { + "node": "^12.13.0 || ^14.15.0 || >=16.0.0" + } + }, + "node_modules/@npmcli/git": { + "version": "3.0.2", + "resolved": "https://registry.npmjs.org/@npmcli/git/-/git-3.0.2.tgz", + "integrity": "sha512-CAcd08y3DWBJqJDpfuVL0uijlq5oaXaOJEKHKc4wqrjd00gkvTZB+nFuLn+doOOKddaQS9JfqtNoFCO2LCvA3w==", + "dev": true, + "dependencies": { + "@npmcli/promise-spawn": "^3.0.0", + "lru-cache": "^7.4.4", + "mkdirp": "^1.0.4", + "npm-pick-manifest": "^7.0.0", + "proc-log": "^2.0.0", + "promise-inflight": "^1.0.1", + "promise-retry": "^2.0.1", + "semver": "^7.3.5", + "which": "^2.0.2" + }, + "engines": { + "node": "^12.13.0 || ^14.15.0 || >=16.0.0" + } + }, + "node_modules/@npmcli/installed-package-contents": { + "version": "1.0.7", + "resolved": "https://registry.npmjs.org/@npmcli/installed-package-contents/-/installed-package-contents-1.0.7.tgz", + "integrity": "sha512-9rufe0wnJusCQoLpV9ZPKIVP55itrM5BxOXs10DmdbRfgWtHy1LDyskbwRnBghuB0PrF7pNPOqREVtpz4HqzKw==", + "dev": true, + "dependencies": { + "npm-bundled": "^1.1.1", + "npm-normalize-package-bin": "^1.0.1" + }, + "bin": { + "installed-package-contents": "index.js" + }, + "engines": { + "node": ">= 10" + } + }, + "node_modules/@npmcli/map-workspaces": { + "version": "2.0.4", + "resolved": "https://registry.npmjs.org/@npmcli/map-workspaces/-/map-workspaces-2.0.4.tgz", + "integrity": "sha512-bMo0aAfwhVwqoVM5UzX1DJnlvVvzDCHae821jv48L1EsrYwfOZChlqWYXEtto/+BkBXetPbEWgau++/brh4oVg==", + "dev": true, + "dependencies": { + "@npmcli/name-from-folder": "^1.0.1", + "glob": "^8.0.1", + "minimatch": "^5.0.1", + "read-package-json-fast": "^2.0.3" + }, + "engines": { + "node": "^12.13.0 || ^14.15.0 || >=16.0.0" + } + }, + "node_modules/@npmcli/map-workspaces/node_modules/brace-expansion": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/brace-expansion/-/brace-expansion-2.0.1.tgz", + "integrity": "sha512-XnAIvQ8eM+kC6aULx6wuQiwVsnzsi9d3WxzV3FpWTGA19F621kwdbsAcFKXgKUHZWsy+mY6iL1sHTxWEFCytDA==", + "dev": true, + "dependencies": { + "balanced-match": "^1.0.0" + } + }, + "node_modules/@npmcli/map-workspaces/node_modules/minimatch": { + "version": "5.1.0", + "resolved": "https://registry.npmjs.org/minimatch/-/minimatch-5.1.0.tgz", + "integrity": "sha512-9TPBGGak4nHfGZsPBohm9AWg6NoT7QTCehS3BIJABslyZbzxfV78QM2Y6+i741OPZIafFAaiiEMh5OyIrJPgtg==", + "dev": true, + "dependencies": { + "brace-expansion": "^2.0.1" + }, + "engines": { + "node": ">=10" + } + }, + "node_modules/@npmcli/metavuln-calculator": { + "version": "3.1.1", + "resolved": "https://registry.npmjs.org/@npmcli/metavuln-calculator/-/metavuln-calculator-3.1.1.tgz", + "integrity": "sha512-n69ygIaqAedecLeVH3KnO39M6ZHiJ2dEv5A7DGvcqCB8q17BGUgW8QaanIkbWUo2aYGZqJaOORTLAlIvKjNDKA==", + "dev": true, + "dependencies": { + "cacache": "^16.0.0", + "json-parse-even-better-errors": "^2.3.1", + "pacote": "^13.0.3", + "semver": "^7.3.5" + }, + "engines": { + "node": "^12.13.0 || ^14.15.0 || >=16.0.0" + } + }, + "node_modules/@npmcli/move-file": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/@npmcli/move-file/-/move-file-2.0.1.tgz", + "integrity": "sha512-mJd2Z5TjYWq/ttPLLGqArdtnC74J6bOzg4rMDnN+p1xTacZ2yPRCk2y0oSWQtygLR9YVQXgOcONrwtnk3JupxQ==", + "dev": true, + "dependencies": { + "mkdirp": "^1.0.4", + "rimraf": "^3.0.2" + }, + "engines": { + "node": "^12.13.0 || ^14.15.0 || >=16.0.0" + } + }, + "node_modules/@npmcli/name-from-folder": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/@npmcli/name-from-folder/-/name-from-folder-1.0.1.tgz", + "integrity": "sha512-qq3oEfcLFwNfEYOQ8HLimRGKlD8WSeGEdtUa7hmzpR8Sa7haL1KVQrvgO6wqMjhWFFVjgtrh1gIxDz+P8sjUaA==", + "dev": true + }, + "node_modules/@npmcli/node-gyp": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/@npmcli/node-gyp/-/node-gyp-2.0.0.tgz", + "integrity": "sha512-doNI35wIe3bBaEgrlPfdJPaCpUR89pJWep4Hq3aRdh6gKazIVWfs0jHttvSSoq47ZXgC7h73kDsUl8AoIQUB+A==", + "dev": true, + "engines": { + "node": "^12.13.0 || ^14.15.0 || >=16.0.0" + } + }, + "node_modules/@npmcli/package-json": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/@npmcli/package-json/-/package-json-2.0.0.tgz", + "integrity": "sha512-42jnZ6yl16GzjWSH7vtrmWyJDGVa/LXPdpN2rcUWolFjc9ON2N3uz0qdBbQACfmhuJZ2lbKYtmK5qx68ZPLHMA==", + "dev": true, + "dependencies": { + "json-parse-even-better-errors": "^2.3.1" + }, + "engines": { + "node": "^12.13.0 || ^14.15.0 || >=16.0.0" + } + }, + "node_modules/@npmcli/promise-spawn": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/@npmcli/promise-spawn/-/promise-spawn-3.0.0.tgz", + "integrity": "sha512-s9SgS+p3a9Eohe68cSI3fi+hpcZUmXq5P7w0kMlAsWVtR7XbK3ptkZqKT2cK1zLDObJ3sR+8P59sJE0w/KTL1g==", + "dev": true, + "dependencies": { + "infer-owner": "^1.0.4" + }, + "engines": { + "node": "^12.13.0 || ^14.15.0 || >=16.0.0" + } + }, + "node_modules/@npmcli/run-script": { + "version": "4.2.1", + "resolved": "https://registry.npmjs.org/@npmcli/run-script/-/run-script-4.2.1.tgz", + "integrity": "sha512-7dqywvVudPSrRCW5nTHpHgeWnbBtz8cFkOuKrecm6ih+oO9ciydhWt6OF7HlqupRRmB8Q/gECVdB9LMfToJbRg==", + "dev": true, + "dependencies": { + "@npmcli/node-gyp": "^2.0.0", + "@npmcli/promise-spawn": "^3.0.0", + "node-gyp": "^9.0.0", + "read-package-json-fast": "^2.0.3", + "which": "^2.0.2" + }, + "engines": { + "node": "^12.13.0 || ^14.15.0 || >=16.0.0" + } + }, + "node_modules/@nrwl/cli": { + "version": "14.8.4", + "resolved": "https://registry.npmjs.org/@nrwl/cli/-/cli-14.8.4.tgz", + "integrity": "sha512-JBoMw1IUFbtahDWolv3iBWJyO3ZXHOsqUt2AvWSrKfteOCjhSfG9GdQYGlnV9ZpWAx4bDf4f7Xz5z6+DJuaONA==", + "dev": true, + "dependencies": { + "nx": "14.8.4" + } + }, + "node_modules/@nrwl/devkit": { + "version": "14.8.4", + "resolved": "https://registry.npmjs.org/@nrwl/devkit/-/devkit-14.8.4.tgz", + "integrity": "sha512-GmHZ8SVE0aL4iRfkYRzzE5I09rl6MgHpLDkuGAYQOPLOm4REjZ5jFjoODS2M7AydrJ34JxAq9eAFXGFr4cKauA==", + "dev": true, + "dependencies": { + "@phenomnomnominal/tsquery": "4.1.1", + "ejs": "^3.1.7", + "ignore": "^5.0.4", + "tslib": "^2.3.0" + }, + "peerDependencies": { + "nx": ">= 13.10 <= 15" + } + }, + "node_modules/@nrwl/tao": { + "version": "14.8.4", + "resolved": "https://registry.npmjs.org/@nrwl/tao/-/tao-14.8.4.tgz", + "integrity": "sha512-wEDBELOYzfvp96xCnoWoMr4UA/e3cUri7kAXDGK3hrGGcCUplJ+notHiKJoZXmB3yHME2PMJca4dHcG4zVgA0w==", + "dev": true, + "dependencies": { + "nx": "14.8.4" + }, + "bin": { + "tao": "index.js" + } + }, + "node_modules/@octokit/auth-token": { + "version": "3.0.1", + "resolved": "https://registry.npmjs.org/@octokit/auth-token/-/auth-token-3.0.1.tgz", + "integrity": "sha512-/USkK4cioY209wXRpund6HZzHo9GmjakpV9ycOkpMcMxMk7QVcVFVyCMtzvXYiHsB2crgDgrtNYSELYFBXhhaA==", + "dev": true, + "dependencies": { + "@octokit/types": "^7.0.0" + }, + "engines": { + "node": ">= 14" + } + }, + "node_modules/@octokit/core": { + "version": "4.0.5", + "resolved": "https://registry.npmjs.org/@octokit/core/-/core-4.0.5.tgz", + "integrity": "sha512-4R3HeHTYVHCfzSAi0C6pbGXV8UDI5Rk+k3G7kLVNckswN9mvpOzW9oENfjfH3nEmzg8y3AmKmzs8Sg6pLCeOCA==", + "dev": true, + "dependencies": { + "@octokit/auth-token": "^3.0.0", + "@octokit/graphql": "^5.0.0", + "@octokit/request": "^6.0.0", + "@octokit/request-error": "^3.0.0", + "@octokit/types": "^7.0.0", + "before-after-hook": "^2.2.0", + "universal-user-agent": "^6.0.0" + }, + "engines": { + "node": ">= 14" + } + }, + "node_modules/@octokit/endpoint": { + "version": "7.0.2", + "resolved": "https://registry.npmjs.org/@octokit/endpoint/-/endpoint-7.0.2.tgz", + "integrity": "sha512-8/AUACfE9vpRpehE6ZLfEtzkibe5nfsSwFZVMsG8qabqRt1M81qZYUFRZa1B8w8lP6cdfDJfRq9HWS+MbmR7tw==", + "dev": true, + "dependencies": { + "@octokit/types": "^7.0.0", + "is-plain-object": "^5.0.0", + "universal-user-agent": "^6.0.0" + }, + "engines": { + "node": ">= 14" + } + }, + "node_modules/@octokit/graphql": { + "version": "5.0.1", + "resolved": "https://registry.npmjs.org/@octokit/graphql/-/graphql-5.0.1.tgz", + "integrity": "sha512-sxmnewSwAixkP1TrLdE6yRG53eEhHhDTYUykUwdV9x8f91WcbhunIHk9x1PZLALdBZKRPUO2HRcm4kezZ79HoA==", + "dev": true, + "dependencies": { + "@octokit/request": "^6.0.0", + "@octokit/types": "^7.0.0", + "universal-user-agent": "^6.0.0" + }, + "engines": { + "node": ">= 14" + } + }, + "node_modules/@octokit/openapi-types": { + "version": "13.13.1", + "resolved": "https://registry.npmjs.org/@octokit/openapi-types/-/openapi-types-13.13.1.tgz", + "integrity": "sha512-4EuKSk3N95UBWFau3Bz9b3pheQ8jQYbKmBL5+GSuY8YDPDwu03J4BjI+66yNi8aaX/3h1qDpb0mbBkLdr+cfGQ==", + "dev": true + }, + "node_modules/@octokit/plugin-enterprise-rest": { + "version": "6.0.1", + "resolved": "https://registry.npmjs.org/@octokit/plugin-enterprise-rest/-/plugin-enterprise-rest-6.0.1.tgz", + "integrity": "sha512-93uGjlhUD+iNg1iWhUENAtJata6w5nE+V4urXOAlIXdco6xNZtUSfYY8dzp3Udy74aqO/B5UZL80x/YMa5PKRw==", + "dev": true + }, + "node_modules/@octokit/plugin-paginate-rest": { + "version": "4.3.1", + "resolved": "https://registry.npmjs.org/@octokit/plugin-paginate-rest/-/plugin-paginate-rest-4.3.1.tgz", + "integrity": "sha512-h8KKxESmSFTcXX409CAxlaOYscEDvN2KGQRsLCGT1NSqRW+D6EXLVQ8vuHhFznS9MuH9QYw1GfsUN30bg8hjVA==", + "dev": true, + "dependencies": { + "@octokit/types": "^7.5.0" + }, + "engines": { + "node": ">= 14" + }, + "peerDependencies": { + "@octokit/core": ">=4" + } + }, + "node_modules/@octokit/plugin-request-log": { + "version": "1.0.4", + "resolved": "https://registry.npmjs.org/@octokit/plugin-request-log/-/plugin-request-log-1.0.4.tgz", + "integrity": "sha512-mLUsMkgP7K/cnFEw07kWqXGF5LKrOkD+lhCrKvPHXWDywAwuDUeDwWBpc69XK3pNX0uKiVt8g5z96PJ6z9xCFA==", + "dev": true, + "peerDependencies": { + "@octokit/core": ">=3" + } + }, + "node_modules/@octokit/plugin-rest-endpoint-methods": { + "version": "6.6.2", + "resolved": "https://registry.npmjs.org/@octokit/plugin-rest-endpoint-methods/-/plugin-rest-endpoint-methods-6.6.2.tgz", + "integrity": "sha512-n9dL5KMpz9qVFSNdcVWC8ZPbl68QbTk7+CMPXCXqaMZOLn1n1YuoSFFCy84Ge0fx333fUqpnBHv8BFjwGtUQkA==", + "dev": true, + "dependencies": { + "@octokit/types": "^7.5.0", + "deprecation": "^2.3.1" + }, + "engines": { + "node": ">= 14" + }, + "peerDependencies": { + "@octokit/core": ">=3" + } + }, + "node_modules/@octokit/request": { + "version": "6.2.1", + "resolved": "https://registry.npmjs.org/@octokit/request/-/request-6.2.1.tgz", + "integrity": "sha512-gYKRCia3cpajRzDSU+3pt1q2OcuC6PK8PmFIyxZDWCzRXRSIBH8jXjFJ8ZceoygBIm0KsEUg4x1+XcYBz7dHPQ==", + "dev": true, + "dependencies": { + "@octokit/endpoint": "^7.0.0", + "@octokit/request-error": "^3.0.0", + "@octokit/types": "^7.0.0", + "is-plain-object": "^5.0.0", + "node-fetch": "^2.6.7", + "universal-user-agent": "^6.0.0" + }, + "engines": { + "node": ">= 14" + } + }, + "node_modules/@octokit/request-error": { + "version": "3.0.1", + "resolved": "https://registry.npmjs.org/@octokit/request-error/-/request-error-3.0.1.tgz", + "integrity": "sha512-ym4Bp0HTP7F3VFssV88WD1ZyCIRoE8H35pXSKwLeMizcdZAYc/t6N9X9Yr9n6t3aG9IH75XDnZ6UeZph0vHMWQ==", + "dev": true, + "dependencies": { + "@octokit/types": "^7.0.0", + "deprecation": "^2.0.0", + "once": "^1.4.0" + }, + "engines": { + "node": ">= 14" + } + }, + "node_modules/@octokit/rest": { + "version": "19.0.4", + "resolved": "https://registry.npmjs.org/@octokit/rest/-/rest-19.0.4.tgz", + "integrity": "sha512-LwG668+6lE8zlSYOfwPj4FxWdv/qFXYBpv79TWIQEpBLKA9D/IMcWsF/U9RGpA3YqMVDiTxpgVpEW3zTFfPFTA==", + "dev": true, + "dependencies": { + "@octokit/core": "^4.0.0", + "@octokit/plugin-paginate-rest": "^4.0.0", + "@octokit/plugin-request-log": "^1.0.4", + "@octokit/plugin-rest-endpoint-methods": "^6.0.0" + }, + "engines": { + "node": ">= 14" + } + }, + "node_modules/@octokit/types": { + "version": "7.5.1", + "resolved": "https://registry.npmjs.org/@octokit/types/-/types-7.5.1.tgz", + "integrity": "sha512-Zk4OUMLCSpXNI8KZZn47lVLJSsgMyCimsWWQI5hyjZg7hdYm0kjotaIkbG0Pp8SfU2CofMBzonboTqvzn3FrJA==", + "dev": true, + "dependencies": { + "@octokit/openapi-types": "^13.11.0" + } + }, + "node_modules/@parcel/watcher": { + "version": "2.0.4", + "resolved": "https://registry.npmjs.org/@parcel/watcher/-/watcher-2.0.4.tgz", + "integrity": "sha512-cTDi+FUDBIUOBKEtj+nhiJ71AZVlkAsQFuGQTun5tV9mwQBQgZvhCzG+URPQc8myeN32yRVZEfVAPCs1RW+Jvg==", + "dev": true, + "hasInstallScript": true, + "dependencies": { + "node-addon-api": "^3.2.1", + "node-gyp-build": "^4.3.0" + }, + "engines": { + "node": ">= 10.0.0" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/parcel" + } + }, + "node_modules/@phenomnomnominal/tsquery": { + "version": "4.1.1", + "resolved": "https://registry.npmjs.org/@phenomnomnominal/tsquery/-/tsquery-4.1.1.tgz", + "integrity": "sha512-jjMmK1tnZbm1Jq5a7fBliM4gQwjxMU7TFoRNwIyzwlO+eHPRCFv/Nv+H/Gi1jc3WR7QURG8D5d0Tn12YGrUqBQ==", + "dev": true, + "dependencies": { + "esquery": "^1.0.1" + }, + "peerDependencies": { + "typescript": "^3 || ^4" + } + }, + "node_modules/@pnpm/network.ca-file": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/@pnpm/network.ca-file/-/network.ca-file-1.0.1.tgz", + "integrity": "sha512-gkINruT2KUhZLTaiHxwCOh1O4NVnFT0wLjWFBHmTz9vpKag/C/noIMJXBxFe4F0mYpUVX2puLwAieLYFg2NvoA==", + "dev": true, + "dependencies": { + "graceful-fs": "4.2.10" + }, + "engines": { + "node": ">=12.22.0" + } + }, + "node_modules/@pnpm/npm-conf": { + "version": "1.0.5", + "resolved": "https://registry.npmjs.org/@pnpm/npm-conf/-/npm-conf-1.0.5.tgz", + "integrity": "sha512-hD8ml183638O3R6/Txrh0L8VzGOrFXgRtRDG4qQC4tONdZ5Z1M+tlUUDUvrjYdmK6G+JTBTeaCLMna11cXzi8A==", + "dev": true, + "dependencies": { + "@pnpm/network.ca-file": "^1.0.1", + "config-chain": "^1.1.11" + }, + "engines": { + "node": ">=12" + } + }, + "node_modules/@sindresorhus/is": { + "version": "5.3.0", + "resolved": "https://registry.npmjs.org/@sindresorhus/is/-/is-5.3.0.tgz", + "integrity": "sha512-CX6t4SYQ37lzxicAqsBtxA3OseeoVrh9cSJ5PFYam0GksYlupRfy1A+Q4aYD3zvcfECLc0zO2u+ZnR2UYKvCrw==", + "dev": true, + "engines": { + "node": ">=14.16" + }, + "funding": { + "url": "https://github.com/sindresorhus/is?sponsor=1" + } + }, + "node_modules/@szmarczak/http-timer": { + "version": "5.0.1", + "resolved": "https://registry.npmjs.org/@szmarczak/http-timer/-/http-timer-5.0.1.tgz", + "integrity": "sha512-+PmQX0PiAYPMeVYe237LJAYvOMYW1j2rH5YROyS3b4CTVJum34HfRvKvAzozHAQG0TnHNdUfY9nCeUyRAs//cw==", + "dev": true, + "dependencies": { + "defer-to-connect": "^2.0.1" + }, + "engines": { + "node": ">=14.16" + } + }, + "node_modules/@tootallnate/once": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/@tootallnate/once/-/once-2.0.0.tgz", + "integrity": "sha512-XCuKFP5PS55gnMVu3dty8KPatLqUoy/ZYzDzAGCQ8JNFCkLXzmI7vNHCR+XpbZaMWQK/vQubr7PkYq8g470J/A==", + "dev": true, + "engines": { + "node": ">= 10" + } + }, + "node_modules/@types/http-cache-semantics": { + "version": "4.0.1", + "resolved": "https://registry.npmjs.org/@types/http-cache-semantics/-/http-cache-semantics-4.0.1.tgz", + "integrity": "sha512-SZs7ekbP8CN0txVG2xVRH6EgKmEm31BOxA07vkFaETzZz1xh+cbt8BcI0slpymvwhx5dlFnQG2rTlPVQn+iRPQ==", + "dev": true + }, + "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/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 + }, + "node_modules/@types/minimatch": { + "version": "3.0.5", + "resolved": "https://registry.npmjs.org/@types/minimatch/-/minimatch-3.0.5.tgz", + "integrity": "sha512-Klz949h02Gz2uZCMGwDUSDS1YBlTdDDgbWHi+81l29tQALUtvz4rAYi5uoVhE5Lagoq6DeqAUlbrHvW/mXDgdQ==", + "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/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", + "integrity": "sha512-//oorEZjL6sbPcKUaCdIGlIUeH26mgzimjBB77G6XRgnDl/L5wOnpyBGRe/Mmf5CVW3PwEBE1NjiMZ/ssFh4wA==", + "dev": true + }, + "node_modules/@typescript-eslint/eslint-plugin": { + "version": "5.40.0", + "resolved": "https://registry.npmjs.org/@typescript-eslint/eslint-plugin/-/eslint-plugin-5.40.0.tgz", + "integrity": "sha512-FIBZgS3DVJgqPwJzvZTuH4HNsZhHMa9SjxTKAZTlMsPw/UzpEjcf9f4dfgDJEHjK+HboUJo123Eshl6niwEm/Q==", + "dev": true, + "dependencies": { + "@typescript-eslint/scope-manager": "5.40.0", + "@typescript-eslint/type-utils": "5.40.0", + "@typescript-eslint/utils": "5.40.0", + "debug": "^4.3.4", + "ignore": "^5.2.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.40.0", + "resolved": "https://registry.npmjs.org/@typescript-eslint/parser/-/parser-5.40.0.tgz", + "integrity": "sha512-Ah5gqyX2ySkiuYeOIDg7ap51/b63QgWZA7w6AHtFrag7aH0lRQPbLzUjk0c9o5/KZ6JRkTTDKShL4AUrQa6/hw==", + "dev": true, + "dependencies": { + "@typescript-eslint/scope-manager": "5.40.0", + "@typescript-eslint/types": "5.40.0", + "@typescript-eslint/typescript-estree": "5.40.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.40.0", + "resolved": "https://registry.npmjs.org/@typescript-eslint/scope-manager/-/scope-manager-5.40.0.tgz", + "integrity": "sha512-d3nPmjUeZtEWRvyReMI4I1MwPGC63E8pDoHy0BnrYjnJgilBD3hv7XOiETKLY/zTwI7kCnBDf2vWTRUVpYw0Uw==", + "dev": true, + "dependencies": { + "@typescript-eslint/types": "5.40.0", + "@typescript-eslint/visitor-keys": "5.40.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.40.0", + "resolved": "https://registry.npmjs.org/@typescript-eslint/type-utils/-/type-utils-5.40.0.tgz", + "integrity": "sha512-nfuSdKEZY2TpnPz5covjJqav+g5qeBqwSHKBvz7Vm1SAfy93SwKk/JeSTymruDGItTwNijSsno5LhOHRS1pcfw==", + "dev": true, + "dependencies": { + "@typescript-eslint/typescript-estree": "5.40.0", + "@typescript-eslint/utils": "5.40.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.40.0", + "resolved": "https://registry.npmjs.org/@typescript-eslint/types/-/types-5.40.0.tgz", + "integrity": "sha512-V1KdQRTXsYpf1Y1fXCeZ+uhjW48Niiw0VGt4V8yzuaDTU8Z1Xl7yQDyQNqyAFcVhpYXIVCEuxSIWTsLDpHgTbw==", + "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.40.0", + "resolved": "https://registry.npmjs.org/@typescript-eslint/typescript-estree/-/typescript-estree-5.40.0.tgz", + "integrity": "sha512-b0GYlDj8TLTOqwX7EGbw2gL5EXS2CPEWhF9nGJiGmEcmlpNBjyHsTwbqpyIEPVpl6br4UcBOYlcI2FJVtJkYhg==", + "dev": true, + "dependencies": { + "@typescript-eslint/types": "5.40.0", + "@typescript-eslint/visitor-keys": "5.40.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.40.0", + "resolved": "https://registry.npmjs.org/@typescript-eslint/utils/-/utils-5.40.0.tgz", + "integrity": "sha512-MO0y3T5BQ5+tkkuYZJBjePewsY+cQnfkYeRqS6tPh28niiIwPnQ1t59CSRcs1ZwJJNOdWw7rv9pF8aP58IMihA==", + "dev": true, + "dependencies": { + "@types/json-schema": "^7.0.9", + "@typescript-eslint/scope-manager": "5.40.0", + "@typescript-eslint/types": "5.40.0", + "@typescript-eslint/typescript-estree": "5.40.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.40.0", + "resolved": "https://registry.npmjs.org/@typescript-eslint/visitor-keys/-/visitor-keys-5.40.0.tgz", + "integrity": "sha512-ijJ+6yig+x9XplEpG2K6FUdJeQGGj/15U3S56W9IqXKJqleuD7zJ2AX/miLezwxpd7ZxDAqO87zWufKg+RPZyQ==", + "dev": true, + "dependencies": { + "@typescript-eslint/types": "5.40.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/@yarnpkg/lockfile": { + "version": "1.1.0", + "resolved": "https://registry.npmjs.org/@yarnpkg/lockfile/-/lockfile-1.1.0.tgz", + "integrity": "sha512-GpSwvyXOcOOlV70vbnzjj4fW5xW/FdUF6nQEt1ENy7m4ZCczi1+/buVUPAqmGfqznsORNFzUMjctTIp8a9tuCQ==", + "dev": true + }, + "node_modules/@yarnpkg/parsers": { + "version": "3.0.0-rc.25", + "resolved": "https://registry.npmjs.org/@yarnpkg/parsers/-/parsers-3.0.0-rc.25.tgz", + "integrity": "sha512-uotaIJwVQeV/DcGA9G2EVuVFHnEEdxDy3yRLeh9VHS6Lx7nZETaWzJPU1bgAwnAa3gplol2NIQhlsr2eqgq9qA==", + "dev": true, + "dependencies": { + "js-yaml": "^3.10.0", + "tslib": "^2.4.0" + }, + "engines": { + "node": ">=14.15.0" + } + }, + "node_modules/@yarnpkg/parsers/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/@yarnpkg/parsers/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/@zkochan/js-yaml": { + "version": "0.0.6", + "resolved": "https://registry.npmjs.org/@zkochan/js-yaml/-/js-yaml-0.0.6.tgz", + "integrity": "sha512-nzvgl3VfhcELQ8LyVrYOru+UtAy1nrygk2+AGbTm8a5YcO6o8lSjAT+pfg3vJWxIoZKOUhrK6UU7xW/+00kQrg==", + "dev": true, + "dependencies": { + "argparse": "^2.0.1" + }, + "bin": { + "js-yaml": "bin/js-yaml.js" + } + }, + "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==", + "dev": true + }, + "node_modules/acorn": { + "version": "8.8.0", + "resolved": "https://registry.npmjs.org/acorn/-/acorn-8.8.0.tgz", + "integrity": "sha512-QOxyigPVrpZ2GXT+PFyZTl6TtOFc5egxHIP9IlQ+RbupQuX4RkT/Bee4/kQuC02Xkzg84JcT7oLYtDIQxp+v7w==", + "dev": true, + "bin": { + "acorn": "bin/acorn" + }, + "engines": { + "node": ">=0.4.0" + } + }, + "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/add-stream": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/add-stream/-/add-stream-1.0.0.tgz", + "integrity": "sha512-qQLMr+8o0WC4FZGQTcJiKBVC59JylcPSrTtk6usvmIDFUOCKegapy1VHQwRbFMOFyb/inzUVqHs+eMYKDM1YeQ==", + "dev": true + }, + "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==", + "dev": true, + "dependencies": { + "debug": "4" + }, + "engines": { + "node": ">= 6.0.0" + } + }, + "node_modules/agentkeepalive": { + "version": "4.2.1", + "resolved": "https://registry.npmjs.org/agentkeepalive/-/agentkeepalive-4.2.1.tgz", + "integrity": "sha512-Zn4cw2NEqd+9fiSVWMscnjyQ1a8Yfoc5oBajLeo5w+YBHgDUcEBY2hS4YpTz6iN5f/2zQiktcuM6tS8x1p9dpA==", + "dev": true, + "dependencies": { + "debug": "^4.1.0", + "depd": "^1.1.2", + "humanize-ms": "^1.2.1" + }, + "engines": { + "node": ">= 8.0.0" + } + }, + "node_modules/aggregate-error": { + "version": "3.1.0", + "resolved": "https://registry.npmjs.org/aggregate-error/-/aggregate-error-3.1.0.tgz", + "integrity": "sha512-4I7Td01quW/RpocfNayFdFVk1qSuoh0E7JrbRJ16nH01HhKFQ88INq9Sd+nd72zqRySlr9BmDA8xlEJ6vJMrYA==", + "dev": true, + "dependencies": { + "clean-stack": "^2.0.0", + "indent-string": "^4.0.0" + }, + "engines": { + "node": ">=8" + } + }, + "node_modules/ansi-align": { + "version": "3.0.1", + "resolved": "https://registry.npmjs.org/ansi-align/-/ansi-align-3.0.1.tgz", + "integrity": "sha512-IOfwwBF5iczOjp/WeY4YxyjqAFMQoZufdQWDd19SEExbVLNXqvpzSJ/M7Za4/sCPmQ0+GRquoA7bGcINcxew6w==", + "dev": true, + "dependencies": { + "string-width": "^4.1.0" + } + }, + "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==", + "dev": true, + "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.2", + "resolved": "https://registry.npmjs.org/anymatch/-/anymatch-3.1.2.tgz", + "integrity": "sha512-P43ePfOAIupkguHUycrc4qJ9kz8ZiuOUijaETwX7THt0Y/GNK7v0aa8rY816xWjZ7rJdA5XdMcpVFTKMq+RvWg==", + "dev": true, + "dependencies": { + "normalize-path": "^3.0.0", + "picomatch": "^2.0.4" + }, + "engines": { + "node": ">= 8" + } + }, + "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==", + "dev": true + }, + "node_modules/are-we-there-yet": { + "version": "3.0.1", + "resolved": "https://registry.npmjs.org/are-we-there-yet/-/are-we-there-yet-3.0.1.tgz", + "integrity": "sha512-QZW4EDmGwlYur0Yyf/b2uGucHQMa8aFUP7eu9ddR73vvhFyt4V0Vl3QHPcTNJ8l6qYOBdxgXdnBXQrHilfRQBg==", + "dev": true, + "dependencies": { + "delegates": "^1.0.0", + "readable-stream": "^3.6.0" + }, + "engines": { + "node": "^12.13.0 || ^14.15.0 || >=16.0.0" + } + }, + "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-differ": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/array-differ/-/array-differ-3.0.0.tgz", + "integrity": "sha512-THtfYS6KtME/yIAhKjZ2ul7XI96lQGHRputJQHO80LAWQnuGP4iCIN8vdMRboGbIEYBwU33q8Tch1os2+X0kMg==", + "dev": true, + "engines": { + "node": ">=8" + } + }, + "node_modules/array-ify": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/array-ify/-/array-ify-1.0.0.tgz", + "integrity": "sha512-c5AMf34bKdvPhQ7tBGhqkgKNUzMr4WUs+WDtC2ZUGOUncbxKMTvqxYctiseW3+L4bA8ec+GcZ6/A/FW4m8ukng==", + "dev": true + }, + "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/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/asap": { + "version": "2.0.6", + "resolved": "https://registry.npmjs.org/asap/-/asap-2.0.6.tgz", + "integrity": "sha512-BSHWgDSAiKs50o2Re8ppvp3seVHXSRM44cdSsT9FfNEUUZLOGWVCsiWaRPWM1Znn+mqZ1OfVZ3z3DWEzSp7hRA==", + "dev": true + }, + "node_modules/async": { + "version": "3.2.4", + "resolved": "https://registry.npmjs.org/async/-/async-3.2.4.tgz", + "integrity": "sha512-iAB+JbDEGXhyIUavoDl9WP/Jj106Kz9DEn1DPgYw5ruDn0e3Wgi3sKFm55sASdGBNOQB8F59d9qQ7deqrHA8wQ==", + "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/at-least-node": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/at-least-node/-/at-least-node-1.0.0.tgz", + "integrity": "sha512-+q/t7Ekv1EDY2l6Gda6LLiX14rU9TV20Wa3ofeQmwPFZbOMo9DXrLbOjFaaclkXKWidIaopwAObQDqwWtGUjqg==", + "dev": true, + "engines": { + "node": ">= 4.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/before-after-hook": { + "version": "2.2.3", + "resolved": "https://registry.npmjs.org/before-after-hook/-/before-after-hook-2.2.3.tgz", + "integrity": "sha512-NzUnlZexiaH/46WDhANlyR2bXRopNg4F/zuSA3OpZnllCUgRaOF2znDioDWrmbNVsuZk6l9pMquQB38cfBZwkQ==", + "dev": true + }, + "node_modules/bin-links": { + "version": "3.0.3", + "resolved": "https://registry.npmjs.org/bin-links/-/bin-links-3.0.3.tgz", + "integrity": "sha512-zKdnMPWEdh4F5INR07/eBrodC7QrF5JKvqskjz/ZZRXg5YSAZIbn8zGhbhUrElzHBZ2fvEQdOU59RHcTG3GiwA==", + "dev": true, + "dependencies": { + "cmd-shim": "^5.0.0", + "mkdirp-infer-owner": "^2.0.0", + "npm-normalize-package-bin": "^2.0.0", + "read-cmd-shim": "^3.0.0", + "rimraf": "^3.0.0", + "write-file-atomic": "^4.0.0" + }, + "engines": { + "node": "^12.13.0 || ^14.15.0 || >=16.0.0" + } + }, + "node_modules/bin-links/node_modules/npm-normalize-package-bin": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/npm-normalize-package-bin/-/npm-normalize-package-bin-2.0.0.tgz", + "integrity": "sha512-awzfKUO7v0FscrSpRoogyNm0sajikhBWpU0QMrW09AMi9n1PoKU6WaIqUzuJSQnpciZZmJ/jMZ2Egfmb/9LiWQ==", + "dev": true, + "engines": { + "node": "^12.13.0 || ^14.15.0 || >=16.0.0" + } + }, + "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/boxen": { + "version": "7.0.0", + "resolved": "https://registry.npmjs.org/boxen/-/boxen-7.0.0.tgz", + "integrity": "sha512-j//dBVuyacJbvW+tvZ9HuH03fZ46QcaKvvhZickZqtB271DxJ7SNRSNxrV/dZX0085m7hISRZWbzWlJvx/rHSg==", + "dev": true, + "dependencies": { + "ansi-align": "^3.0.1", + "camelcase": "^7.0.0", + "chalk": "^5.0.1", + "cli-boxes": "^3.0.0", + "string-width": "^5.1.2", + "type-fest": "^2.13.0", + "widest-line": "^4.0.1", + "wrap-ansi": "^8.0.1" + }, + "engines": { + "node": ">=14.16" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" + } + }, + "node_modules/boxen/node_modules/ansi-regex": { + "version": "6.0.1", + "resolved": "https://registry.npmjs.org/ansi-regex/-/ansi-regex-6.0.1.tgz", + "integrity": "sha512-n5M855fKb2SsfMIiFFoVrABHJC8QtHwVx+mHWP3QcEqBHYienj5dHSgjbxtC0WEZXYt4wcD6zrQElDPhFuZgfA==", + "dev": true, + "engines": { + "node": ">=12" + }, + "funding": { + "url": "https://github.com/chalk/ansi-regex?sponsor=1" + } + }, + "node_modules/boxen/node_modules/ansi-styles": { + "version": "6.2.0", + "resolved": "https://registry.npmjs.org/ansi-styles/-/ansi-styles-6.2.0.tgz", + "integrity": "sha512-3MWBO/XxbkDtc/qpECaUwDM0DQ++ujBjdjs0ElZvChUoPv/P7GOnl3x+R2RF2My5UJHEW5R87q556MiR8U3PLw==", + "dev": true, + "engines": { + "node": ">=12" + }, + "funding": { + "url": "https://github.com/chalk/ansi-styles?sponsor=1" + } + }, + "node_modules/boxen/node_modules/camelcase": { + "version": "7.0.0", + "resolved": "https://registry.npmjs.org/camelcase/-/camelcase-7.0.0.tgz", + "integrity": "sha512-JToIvOmz6nhGsUhAYScbo2d6Py5wojjNfoxoc2mEVLUdJ70gJK2gnd+ABY1Tc3sVMyK7QDPtN0T/XdlCQWITyQ==", + "dev": true, + "engines": { + "node": ">=14.16" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" + } + }, + "node_modules/boxen/node_modules/chalk": { + "version": "5.1.0", + "resolved": "https://registry.npmjs.org/chalk/-/chalk-5.1.0.tgz", + "integrity": "sha512-56zD4khRTBoIyzUYAFgDDaPhUMN/fC/rySe6aZGqbj/VWiU2eI3l6ZLOtYGFZAV5v02mwPjtpzlrOveJiz5eZQ==", + "dev": true, + "engines": { + "node": "^12.17.0 || ^14.13 || >=16.0.0" + }, + "funding": { + "url": "https://github.com/chalk/chalk?sponsor=1" + } + }, + "node_modules/boxen/node_modules/emoji-regex": { + "version": "9.2.2", + "resolved": "https://registry.npmjs.org/emoji-regex/-/emoji-regex-9.2.2.tgz", + "integrity": "sha512-L18DaJsXSUk2+42pv8mLs5jJT2hqFkFE4j21wOmgbUqsZ2hL72NsUU785g9RXgo3s0ZNgVl42TiHp3ZtOv/Vyg==", + "dev": true + }, + "node_modules/boxen/node_modules/string-width": { + "version": "5.1.2", + "resolved": "https://registry.npmjs.org/string-width/-/string-width-5.1.2.tgz", + "integrity": "sha512-HnLOCR3vjcY8beoNLtcjZ5/nxn2afmME6lhrDrebokqMap+XbeW8n9TXpPDOqdGK5qcI3oT0GKTW6wC7EMiVqA==", + "dev": true, + "dependencies": { + "eastasianwidth": "^0.2.0", + "emoji-regex": "^9.2.2", + "strip-ansi": "^7.0.1" + }, + "engines": { + "node": ">=12" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" + } + }, + "node_modules/boxen/node_modules/strip-ansi": { + "version": "7.0.1", + "resolved": "https://registry.npmjs.org/strip-ansi/-/strip-ansi-7.0.1.tgz", + "integrity": "sha512-cXNxvT8dFNRVfhVME3JAe98mkXDYN2O1l7jmcwMnOslDeESg1rF/OZMtK0nRAhiari1unG5cD4jG3rapUAkLbw==", + "dev": true, + "dependencies": { + "ansi-regex": "^6.0.1" + }, + "engines": { + "node": ">=12" + }, + "funding": { + "url": "https://github.com/chalk/strip-ansi?sponsor=1" + } + }, + "node_modules/boxen/node_modules/type-fest": { + "version": "2.19.0", + "resolved": "https://registry.npmjs.org/type-fest/-/type-fest-2.19.0.tgz", + "integrity": "sha512-RAH822pAdBgcNMAfWnCBU3CFZcfZ/i1eZjwFU/dsLKumyuuP3niueg2UAukXYF0E2AAoc82ZSSf9J0WQBinzHA==", + "dev": true, + "engines": { + "node": ">=12.20" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" + } + }, + "node_modules/boxen/node_modules/wrap-ansi": { + "version": "8.0.1", + "resolved": "https://registry.npmjs.org/wrap-ansi/-/wrap-ansi-8.0.1.tgz", + "integrity": "sha512-QFF+ufAqhoYHvoHdajT/Po7KoXVBPXS2bgjIam5isfWJPfIOnQZ50JtUiVvCv/sjgacf3yRrt2ZKUZ/V4itN4g==", + "dev": true, + "dependencies": { + "ansi-styles": "^6.1.0", + "string-width": "^5.0.1", + "strip-ansi": "^7.0.1" + }, + "engines": { + "node": ">=12" + }, + "funding": { + "url": "https://github.com/chalk/wrap-ansi?sponsor=1" + } + }, + "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/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==", + "dev": true + }, + "node_modules/builtins": { + "version": "5.0.1", + "resolved": "https://registry.npmjs.org/builtins/-/builtins-5.0.1.tgz", + "integrity": "sha512-qwVpFEHNfhYJIzNRBvd2C1kyo6jz3ZSMPyyuR47OPdiKWlbYnZNyDWuyR175qDnAJLiCo5fBBqPb3RiXgWlkOQ==", + "dev": true, + "dependencies": { + "semver": "^7.0.0" + } + }, + "node_modules/byte-size": { + "version": "7.0.1", + "resolved": "https://registry.npmjs.org/byte-size/-/byte-size-7.0.1.tgz", + "integrity": "sha512-crQdqyCwhokxwV1UyDzLZanhkugAgft7vt0qbbdt60C6Zf3CAiGmtUCylbtYwrU6loOUw3euGrNtW1J651ot1A==", + "dev": true, + "engines": { + "node": ">=10" + } + }, + "node_modules/c8": { + "version": "7.12.0", + "resolved": "https://registry.npmjs.org/c8/-/c8-7.12.0.tgz", + "integrity": "sha512-CtgQrHOkyxr5koX1wEUmN/5cfDa2ckbHRA4Gy5LAL0zaCFtVWJS5++n+w4/sr2GWGerBxgTjpKeDclk/Qk6W/A==", + "dev": true, + "dependencies": { + "@bcoe/v8-coverage": "^0.2.3", + "@istanbuljs/schema": "^0.1.3", + "find-up": "^5.0.0", + "foreground-child": "^2.0.0", + "istanbul-lib-coverage": "^3.2.0", + "istanbul-lib-report": "^3.0.0", + "istanbul-reports": "^3.1.4", + "rimraf": "^3.0.2", + "test-exclude": "^6.0.0", + "v8-to-istanbul": "^9.0.0", + "yargs": "^16.2.0", + "yargs-parser": "^20.2.9" + }, + "bin": { + "c8": "bin/c8.js" + }, + "engines": { + "node": ">=10.12.0" + } + }, + "node_modules/cacache": { + "version": "16.1.3", + "resolved": "https://registry.npmjs.org/cacache/-/cacache-16.1.3.tgz", + "integrity": "sha512-/+Emcj9DAXxX4cwlLmRI9c166RuL3w30zp4R7Joiv2cQTtTtA+jeuCAjH3ZlGnYS3tKENSrKhAzVVP9GVyzeYQ==", + "dev": true, + "dependencies": { + "@npmcli/fs": "^2.1.0", + "@npmcli/move-file": "^2.0.0", + "chownr": "^2.0.0", + "fs-minipass": "^2.1.0", + "glob": "^8.0.1", + "infer-owner": "^1.0.4", + "lru-cache": "^7.7.1", + "minipass": "^3.1.6", + "minipass-collect": "^1.0.2", + "minipass-flush": "^1.0.5", + "minipass-pipeline": "^1.2.4", + "mkdirp": "^1.0.4", + "p-map": "^4.0.0", + "promise-inflight": "^1.0.1", + "rimraf": "^3.0.2", + "ssri": "^9.0.0", + "tar": "^6.1.11", + "unique-filename": "^2.0.0" + }, + "engines": { + "node": "^12.13.0 || ^14.15.0 || >=16.0.0" + } + }, + "node_modules/cacheable-lookup": { + "version": "7.0.0", + "resolved": "https://registry.npmjs.org/cacheable-lookup/-/cacheable-lookup-7.0.0.tgz", + "integrity": "sha512-+qJyx4xiKra8mZrcwhjMRMUhD5NR1R8esPkzIYxX96JiecFoxAXFuz/GpR3+ev4PE1WamHip78wV0vcmPQtp8w==", + "dev": true, + "engines": { + "node": ">=14.16" + } + }, + "node_modules/cacheable-request": { + "version": "10.2.1", + "resolved": "https://registry.npmjs.org/cacheable-request/-/cacheable-request-10.2.1.tgz", + "integrity": "sha512-3tLJyBjGuXw1s5gpKFSG3iS4kaKT4id04dZi98wzHQp/8cqZNweBnrF9J+rrlvrf4M53OdtDGNctNHFias8BEA==", + "dev": true, + "dependencies": { + "@types/http-cache-semantics": "^4.0.1", + "get-stream": "^6.0.1", + "http-cache-semantics": "^4.1.0", + "keyv": "^4.5.0", + "mimic-response": "^4.0.0", + "normalize-url": "^7.1.0", + "responselike": "^3.0.0" + }, + "engines": { + "node": ">=14.16" + } + }, + "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/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/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/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/chokidar/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/chownr": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/chownr/-/chownr-2.0.0.tgz", + "integrity": "sha512-bIomtDF5KGpdogkLd9VspvFzk9KfpyyGlS8YFVZl7TGPBHL5snIOnxeshwVgPteQ9b4Eydl+pVbIyE1DcvCWgQ==", + "dev": true, + "engines": { + "node": ">=10" + } + }, + "node_modules/ci-info": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/ci-info/-/ci-info-2.0.0.tgz", + "integrity": "sha512-5tK7EtrZ0N+OLFMthtqOj4fI2Jeb88C4CAZPu25LDVUgXJ0A3Js4PMGqrn0JU1W0Mh1/Z8wZzYPxqUrXeBboCQ==", + "dev": true + }, + "node_modules/clean-stack": { + "version": "2.2.0", + "resolved": "https://registry.npmjs.org/clean-stack/-/clean-stack-2.2.0.tgz", + "integrity": "sha512-4diC9HaTE+KRAMWhDhrGOECgWZxoevMc5TlkObMqNSsVU62PYzXZ/SMTjzyGAFF1YusgxGcSWTEXBhp0CPwQ1A==", + "dev": true, + "engines": { + "node": ">=6" + } + }, + "node_modules/cli-boxes": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/cli-boxes/-/cli-boxes-3.0.0.tgz", + "integrity": "sha512-/lzGpEWL/8PfI0BmBOPRwp0c/wFNX1RdUML3jK/RcSBA9T8mZDdQpqYBKtCFTOfQbwPqWEOpjqW+Fnayc0969g==", + "dev": true, + "engines": { + "node": ">=10" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" + } + }, + "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.6.1", + "resolved": "https://registry.npmjs.org/cli-spinners/-/cli-spinners-2.6.1.tgz", + "integrity": "sha512-x/5fWmGMnbKQAaNwN+UZlV79qBLM9JFnJuJ03gIi5whrob0xV0ofNVHy9DhwGdsMJQc2OKv0oGmLzvaqvAVv+g==", + "dev": true, + "engines": { + "node": ">=6" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" + } + }, + "node_modules/cli-table": { + "version": "0.3.11", + "resolved": "https://registry.npmjs.org/cli-table/-/cli-table-0.3.11.tgz", + "integrity": "sha512-IqLQi4lO0nIB4tcdTpN4LCB9FI3uqrJZK7RC515EnhZ6qBaglkIgICb1wjeAqpdoOabm1+SuQtkXIPdYC93jhQ==", + "dev": true, + "dependencies": { + "colors": "1.0.3" + }, + "engines": { + "node": ">= 0.2.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": "7.0.4", + "resolved": "https://registry.npmjs.org/cliui/-/cliui-7.0.4.tgz", + "integrity": "sha512-OcRE68cOsVMXp1Yvonl/fzkQOyjLSu/8bhPDfQt0e0/Eb283TKP20Fs2MqoPsr9SwA595rRCA+QMzYc9nBP+JQ==", + "dev": true, + "dependencies": { + "string-width": "^4.2.0", + "strip-ansi": "^6.0.0", + "wrap-ansi": "^7.0.0" + } + }, + "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/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/clone-deep/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/cmd-shim": { + "version": "5.0.0", + "resolved": "https://registry.npmjs.org/cmd-shim/-/cmd-shim-5.0.0.tgz", + "integrity": "sha512-qkCtZ59BidfEwHltnJwkyVZn+XQojdAySM1D1gSeh11Z4pW1Kpolkyo53L5noc0nrxmIvyFwTmJRo4xs7FFLPw==", + "dev": true, + "dependencies": { + "mkdirp-infer-owner": "^2.0.0" + }, + "engines": { + "node": "^12.13.0 || ^14.15.0 || >=16.0.0" + } + }, + "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/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/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==", + "dev": true, + "bin": { + "color-support": "bin.js" + } + }, + "node_modules/colors": { + "version": "1.0.3", + "resolved": "https://registry.npmjs.org/colors/-/colors-1.0.3.tgz", + "integrity": "sha512-pFGrxThWcWQ2MsAz6RtgeWe4NK2kUE1WfsrvvlctdII745EW9I0yflqhe7++M5LEc7bV2c/9/5zc8sFcpL0Drw==", + "dev": true, + "engines": { + "node": ">=0.1.90" + } + }, + "node_modules/columnify": { + "version": "1.6.0", + "resolved": "https://registry.npmjs.org/columnify/-/columnify-1.6.0.tgz", + "integrity": "sha512-lomjuFZKfM6MSAnV9aCZC9sc0qGbmZdfygNv+nCpqVkSKdCxCklLtd16O0EILGkImHw9ZpHkAnHaB+8Zxq5W6Q==", + "dev": true, + "dependencies": { + "strip-ansi": "^6.0.1", + "wcwidth": "^1.0.0" + }, + "engines": { + "node": ">=8.0.0" + } + }, + "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": "9.4.1", + "resolved": "https://registry.npmjs.org/commander/-/commander-9.4.1.tgz", + "integrity": "sha512-5EEkTNyHNGFPD2H+c/dXXfQZYa/scCKasxWcXJaWnNJ99pnQN9Vnmqow+p+PlFPE63Q6mThaZws1T+HxfpgtPw==", + "dev": true, + "engines": { + "node": "^12.20.0 || >=14" + } + }, + "node_modules/common-ancestor-path": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/common-ancestor-path/-/common-ancestor-path-1.0.1.tgz", + "integrity": "sha512-L3sHRo1pXXEqX8VU28kfgUY+YGsk09hPqZiZmLacNib6XNTCM8ubYeT7ryXQw8asB1sKgcU5lkB7ONug08aB8w==", + "dev": true + }, + "node_modules/compare-func": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/compare-func/-/compare-func-2.0.0.tgz", + "integrity": "sha512-zHig5N+tPWARooBnb0Zx1MFcdfpyJrfTJ3Y5L+IFvUm8rM74hHz66z0gw0x4tijh5CorKkKUCnW82R2vmpeCRA==", + "dev": true, + "dependencies": { + "array-ify": "^1.0.0", + "dot-prop": "^5.1.0" + } + }, + "node_modules/compare-func/node_modules/dot-prop": { + "version": "5.3.0", + "resolved": "https://registry.npmjs.org/dot-prop/-/dot-prop-5.3.0.tgz", + "integrity": "sha512-QM8q3zDe58hqUqjraQOmzZ1LIH9SWQJTlEKCH4kJ2oQvLZk7RbQXvtDM2XEq3fwkV9CCvvH4LA0AV+ogFsBM2Q==", + "dev": true, + "dependencies": { + "is-obj": "^2.0.0" + }, + "engines": { + "node": ">=8" + } + }, + "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": "2.0.0", + "resolved": "https://registry.npmjs.org/concat-stream/-/concat-stream-2.0.0.tgz", + "integrity": "sha512-MWufYdFw53ccGjCA+Ol7XJYpAlW6/prSMzuPOTRnJGcGzuhLn4Scrz7qf6o8bROZ514ltazcIFJZevcfbo0x7A==", + "dev": true, + "engines": [ + "node >= 6.0" + ], + "dependencies": { + "buffer-from": "^1.0.0", + "inherits": "^2.0.3", + "readable-stream": "^3.0.2", + "typedarray": "^0.0.6" + } + }, + "node_modules/config-chain": { + "version": "1.1.13", + "resolved": "https://registry.npmjs.org/config-chain/-/config-chain-1.1.13.tgz", + "integrity": "sha512-qj+f8APARXHrM0hraqXYb2/bOVSV4PvJQlNZ/DVj0QrmNM2q2euizkeuVckQ57J+W0mRH6Hvi+k50M4Jul2VRQ==", + "dev": true, + "dependencies": { + "ini": "^1.3.4", + "proto-list": "~1.2.1" + } + }, + "node_modules/configstore": { + "version": "6.0.0", + "resolved": "https://registry.npmjs.org/configstore/-/configstore-6.0.0.tgz", + "integrity": "sha512-cD31W1v3GqUlQvbBCGcXmd2Nj9SvLDOP1oQ0YFuLETufzSPaKp11rYBsSOm7rCsW3OnIRAFM3OxRhceaXNYHkA==", + "dev": true, + "dependencies": { + "dot-prop": "^6.0.1", + "graceful-fs": "^4.2.6", + "unique-string": "^3.0.0", + "write-file-atomic": "^3.0.3", + "xdg-basedir": "^5.0.1" + }, + "engines": { + "node": ">=12" + }, + "funding": { + "url": "https://github.com/yeoman/configstore?sponsor=1" + } + }, + "node_modules/configstore/node_modules/write-file-atomic": { + "version": "3.0.3", + "resolved": "https://registry.npmjs.org/write-file-atomic/-/write-file-atomic-3.0.3.tgz", + "integrity": "sha512-AvHcyZ5JnSfq3ioSyjrBkH9yW4m7Ayk8/9My/DD9onKeu/94fwrMocemO2QAJFAlnnDN+ZDS+ZjAR5ua1/PV/Q==", + "dev": true, + "dependencies": { + "imurmurhash": "^0.1.4", + "is-typedarray": "^1.0.0", + "signal-exit": "^3.0.2", + "typedarray-to-buffer": "^3.1.5" + } + }, + "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==", + "dev": true + }, + "node_modules/conventional-changelog-angular": { + "version": "5.0.13", + "resolved": "https://registry.npmjs.org/conventional-changelog-angular/-/conventional-changelog-angular-5.0.13.tgz", + "integrity": "sha512-i/gipMxs7s8L/QeuavPF2hLnJgH6pEZAttySB6aiQLWcX3puWDL3ACVmvBhJGxnAy52Qc15ua26BufY6KpmrVA==", + "dev": true, + "dependencies": { + "compare-func": "^2.0.0", + "q": "^1.5.1" + }, + "engines": { + "node": ">=10" + } + }, + "node_modules/conventional-changelog-core": { + "version": "4.2.4", + "resolved": "https://registry.npmjs.org/conventional-changelog-core/-/conventional-changelog-core-4.2.4.tgz", + "integrity": "sha512-gDVS+zVJHE2v4SLc6B0sLsPiloR0ygU7HaDW14aNJE1v4SlqJPILPl/aJC7YdtRE4CybBf8gDwObBvKha8Xlyg==", + "dev": true, + "dependencies": { + "add-stream": "^1.0.0", + "conventional-changelog-writer": "^5.0.0", + "conventional-commits-parser": "^3.2.0", + "dateformat": "^3.0.0", + "get-pkg-repo": "^4.0.0", + "git-raw-commits": "^2.0.8", + "git-remote-origin-url": "^2.0.0", + "git-semver-tags": "^4.1.1", + "lodash": "^4.17.15", + "normalize-package-data": "^3.0.0", + "q": "^1.5.1", + "read-pkg": "^3.0.0", + "read-pkg-up": "^3.0.0", + "through2": "^4.0.0" + }, + "engines": { + "node": ">=10" + } + }, + "node_modules/conventional-changelog-preset-loader": { + "version": "2.3.4", + "resolved": "https://registry.npmjs.org/conventional-changelog-preset-loader/-/conventional-changelog-preset-loader-2.3.4.tgz", + "integrity": "sha512-GEKRWkrSAZeTq5+YjUZOYxdHq+ci4dNwHvpaBC3+ENalzFWuCWa9EZXSuZBpkr72sMdKB+1fyDV4takK1Lf58g==", + "dev": true, + "engines": { + "node": ">=10" + } + }, + "node_modules/conventional-changelog-writer": { + "version": "5.0.1", + "resolved": "https://registry.npmjs.org/conventional-changelog-writer/-/conventional-changelog-writer-5.0.1.tgz", + "integrity": "sha512-5WsuKUfxW7suLblAbFnxAcrvf6r+0b7GvNaWUwUIk0bXMnENP/PEieGKVUQrjPqwPT4o3EPAASBXiY6iHooLOQ==", + "dev": true, + "dependencies": { + "conventional-commits-filter": "^2.0.7", + "dateformat": "^3.0.0", + "handlebars": "^4.7.7", + "json-stringify-safe": "^5.0.1", + "lodash": "^4.17.15", + "meow": "^8.0.0", + "semver": "^6.0.0", + "split": "^1.0.0", + "through2": "^4.0.0" + }, + "bin": { + "conventional-changelog-writer": "cli.js" + }, + "engines": { + "node": ">=10" + } + }, + "node_modules/conventional-changelog-writer/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/conventional-commits-filter": { + "version": "2.0.7", + "resolved": "https://registry.npmjs.org/conventional-commits-filter/-/conventional-commits-filter-2.0.7.tgz", + "integrity": "sha512-ASS9SamOP4TbCClsRHxIHXRfcGCnIoQqkvAzCSbZzTFLfcTqJVugB0agRgsEELsqaeWgsXv513eS116wnlSSPA==", + "dev": true, + "dependencies": { + "lodash.ismatch": "^4.4.0", + "modify-values": "^1.0.0" + }, + "engines": { + "node": ">=10" + } + }, + "node_modules/conventional-commits-parser": { + "version": "3.2.4", + "resolved": "https://registry.npmjs.org/conventional-commits-parser/-/conventional-commits-parser-3.2.4.tgz", + "integrity": "sha512-nK7sAtfi+QXbxHCYfhpZsfRtaitZLIA6889kFIouLvz6repszQDgxBu7wf2WbU+Dco7sAnNCJYERCwt54WPC2Q==", + "dev": true, + "dependencies": { + "is-text-path": "^1.0.1", + "JSONStream": "^1.0.4", + "lodash": "^4.17.15", + "meow": "^8.0.0", + "split2": "^3.0.0", + "through2": "^4.0.0" + }, + "bin": { + "conventional-commits-parser": "cli.js" + }, + "engines": { + "node": ">=10" + } + }, + "node_modules/conventional-recommended-bump": { + "version": "6.1.0", + "resolved": "https://registry.npmjs.org/conventional-recommended-bump/-/conventional-recommended-bump-6.1.0.tgz", + "integrity": "sha512-uiApbSiNGM/kkdL9GTOLAqC4hbptObFo4wW2QRyHsKciGAfQuLU1ShZ1BIVI/+K2BE/W1AWYQMCXAsv4dyKPaw==", + "dev": true, + "dependencies": { + "concat-stream": "^2.0.0", + "conventional-changelog-preset-loader": "^2.3.4", + "conventional-commits-filter": "^2.0.7", + "conventional-commits-parser": "^3.2.0", + "git-raw-commits": "^2.0.8", + "git-semver-tags": "^4.1.1", + "meow": "^8.0.0", + "q": "^1.5.1" + }, + "bin": { + "conventional-recommended-bump": "cli.js" + }, + "engines": { + "node": ">=10" + } + }, + "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/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.0.1", + "resolved": "https://registry.npmjs.org/cosmiconfig/-/cosmiconfig-7.0.1.tgz", + "integrity": "sha512-a1YWNUV2HwGimB7dU2s1wUMurNKjpx60HxBB6xUM8Re+2s1g1IIfJvFR0/iCF+XHdE0GMTKTuLR32UQff4TEyQ==", + "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/crypto-random-string": { + "version": "4.0.0", + "resolved": "https://registry.npmjs.org/crypto-random-string/-/crypto-random-string-4.0.0.tgz", + "integrity": "sha512-x8dy3RnvYdlUcPOjkEHqozhiwzKNSq7GcPuXFbnyMOCHxX8V3OgIg/pYuabl2sbUPfIJaeAQB7PMOK8DFIdoRA==", + "dev": true, + "dependencies": { + "type-fest": "^1.0.1" + }, + "engines": { + "node": ">=12" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" + } + }, + "node_modules/crypto-random-string/node_modules/type-fest": { + "version": "1.4.0", + "resolved": "https://registry.npmjs.org/type-fest/-/type-fest-1.4.0.tgz", + "integrity": "sha512-yGSza74xk0UG8k+pLh5oeoYirvIiWo5t0/o3zHHAO2tRDiZcxWP7fywNlXhqb6/r6sWvwi+RsyQMWhVLe4BVuA==", + "dev": true, + "engines": { + "node": ">=10" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" + } + }, + "node_modules/dargs": { + "version": "7.0.0", + "resolved": "https://registry.npmjs.org/dargs/-/dargs-7.0.0.tgz", + "integrity": "sha512-2iy1EkLdlBzQGvbweYRFxmFath8+K7+AKB0TlhHWkNuH+TmovaMH/Wp7V7R4u7f4SnX3OgLsU9t1NI9ioDnUpg==", + "dev": true, + "engines": { + "node": ">=8" + } + }, + "node_modules/dateformat": { + "version": "3.0.3", + "resolved": "https://registry.npmjs.org/dateformat/-/dateformat-3.0.3.tgz", + "integrity": "sha512-jyCETtSl3VMZMWeRo7iY1FL19ges1t55hMo5yaam4Jrsm5EPL89UQkoQRyiI+Yf4k8r2ZpdngkV8hr1lIdjb3Q==", + "dev": true, + "engines": { + "node": "*" + } + }, + "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/debuglog": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/debuglog/-/debuglog-1.0.1.tgz", + "integrity": "sha512-syBZ+rnAK3EgMsH2aYEOLUW7mZSY9Gb+0wUMCFsZvcmiz+HigA0LOcq/HoQqVuGG+EKykunc7QG2bzrponfaSw==", + "dev": true, + "engines": { + "node": "*" + } + }, + "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.0", + "resolved": "https://registry.npmjs.org/decamelize-keys/-/decamelize-keys-1.1.0.tgz", + "integrity": "sha512-ocLWuYzRPoS9bfiSdDd3cxvrzovVMZnRDVEzAs+hWIVXGDbHxWMECij2OBuyB/An0FFW/nLuq6Kv1i/YC5Qfzg==", + "dev": true, + "dependencies": { + "decamelize": "^1.1.0", + "map-obj": "^1.0.0" + }, + "engines": { + "node": ">=0.10.0" + } + }, + "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/decompress-response": { + "version": "6.0.0", + "resolved": "https://registry.npmjs.org/decompress-response/-/decompress-response-6.0.0.tgz", + "integrity": "sha512-aW35yZM6Bb/4oJlZncMH2LCoZtJXTRxES17vE3hoRiowU2kWHaJKFkSBDnDR+cm9J+9QhXmREyIfv0pji9ejCQ==", + "dev": true, + "dependencies": { + "mimic-response": "^3.1.0" + }, + "engines": { + "node": ">=10" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" + } + }, + "node_modules/decompress-response/node_modules/mimic-response": { + "version": "3.1.0", + "resolved": "https://registry.npmjs.org/mimic-response/-/mimic-response-3.1.0.tgz", + "integrity": "sha512-z0yWI+4FDrrweS8Zmt4Ej5HdJmky15+L2e6Wgn3+iK5fWzb6T3fhNFq2+MeTRb064c6Wr4N/wv0DzQTjNzHNGQ==", + "dev": true, + "engines": { + "node": ">=10" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" + } + }, + "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-extend": { + "version": "0.6.0", + "resolved": "https://registry.npmjs.org/deep-extend/-/deep-extend-0.6.0.tgz", + "integrity": "sha512-LOHxIOaPYdHlJRtCQfDIVZtfw/ufM8+rVj649RIHzcm/vGwQRXFt6OPqIFWsm2XEMrNIEtWR64sY1LEKD2vAOA==", + "dev": true, + "engines": { + "node": ">=4.0.0" + } + }, + "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/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/defer-to-connect": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/defer-to-connect/-/defer-to-connect-2.0.1.tgz", + "integrity": "sha512-4tvttepXG1VaYGrRibk5EwJd1t4udunSOVMdLSAL6mId1ix438oPwPZMALY41FCijukO1L0twNcGsdzS7dHgDg==", + "dev": true, + "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/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/delegates": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/delegates/-/delegates-1.0.0.tgz", + "integrity": "sha512-bd2L678uiWATM6m5Z1VzNCErI3jiGzt6HGY8OVICs40JQq/HALfbyNJmp0UDakEY4pMMaN0Ly5om/B1VI/+xfQ==", + "dev": true + }, + "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/deprecation": { + "version": "2.3.1", + "resolved": "https://registry.npmjs.org/deprecation/-/deprecation-2.3.1.tgz", + "integrity": "sha512-xmHIy4F3scKVwMsQ4WnVaS8bHOx0DmVwRywosKhaILI0ywMDWPtBSku2HNxRvF7jtwDRsoEwYQSfbxj8b7RlJQ==", + "dev": true + }, + "node_modules/detect-indent": { + "version": "6.1.0", + "resolved": "https://registry.npmjs.org/detect-indent/-/detect-indent-6.1.0.tgz", + "integrity": "sha512-reYkTUJAZb9gUuZ2RvVCNhVHdg62RHnJ7WJl8ftMi4diZ6NWlciOzQN88pUhSELEwflJht4oQDv0F0BMlwaYtA==", + "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/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/dot-prop": { + "version": "6.0.1", + "resolved": "https://registry.npmjs.org/dot-prop/-/dot-prop-6.0.1.tgz", + "integrity": "sha512-tE7ztYzXHIeyvc7N+hR3oi7FIbf/NIjVP9hmAt3yMXzrQ072/fpjGLx2GxNxGxUl5V73MEqYzioOMoVhGMJ5cA==", + "dev": true, + "dependencies": { + "is-obj": "^2.0.0" + }, + "engines": { + "node": ">=10" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" + } + }, + "node_modules/dotenv": { + "version": "10.0.0", + "resolved": "https://registry.npmjs.org/dotenv/-/dotenv-10.0.0.tgz", + "integrity": "sha512-rlBi9d8jpv9Sf1klPjNfFAuWDjKLwTIJJ/VxtoTwIR6hnZxcEOQCZg2oIL3MWBYw5GpUDKOEnND7LXTbIpQ03Q==", + "dev": true, + "engines": { + "node": ">=10" + } + }, + "node_modules/duplexer": { + "version": "0.1.2", + "resolved": "https://registry.npmjs.org/duplexer/-/duplexer-0.1.2.tgz", + "integrity": "sha512-jtD6YG370ZCIi/9GTaJKQxWTZD045+4R4hTk/x1UyoqadyJ9x9CgSi1RlVDQF8U2sxLLSnFkCaMihqljHIWgMg==", + "dev": true + }, + "node_modules/eastasianwidth": { + "version": "0.2.0", + "resolved": "https://registry.npmjs.org/eastasianwidth/-/eastasianwidth-0.2.0.tgz", + "integrity": "sha512-I88TYZWc9XiYHRQ4/3c5rjjfgkjhLyW2luGIheGERbNQ6OY7yTybanSpDXZa8y7VUP9YmDcYa+eyq4ca7iLqWA==", + "dev": true + }, + "node_modules/ejs": { + "version": "3.1.8", + "resolved": "https://registry.npmjs.org/ejs/-/ejs-3.1.8.tgz", + "integrity": "sha512-/sXZeMlhS0ArkfX2Aw780gJzXSMPnKjtspYZv+f3NiKLlubezAHDU5+9xz6gd3/NhG3txQCo6xlglmTS+oTGEQ==", + "dev": true, + "dependencies": { + "jake": "^10.8.5" + }, + "bin": { + "ejs": "bin/cli.js" + }, + "engines": { + "node": ">=0.10.0" + } + }, + "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/encoding": { + "version": "0.1.13", + "resolved": "https://registry.npmjs.org/encoding/-/encoding-0.1.13.tgz", + "integrity": "sha512-ETBauow1T35Y/WZMkio9jiM0Z5xjHHmJ4XmjZOq1l/dXz3lr2sRn87nJy20RupqSh1F2m3HHPSp8ShIPQJrJ3A==", + "dev": true, + "optional": true, + "dependencies": { + "iconv-lite": "^0.6.2" + } + }, + "node_modules/encoding/node_modules/iconv-lite": { + "version": "0.6.3", + "resolved": "https://registry.npmjs.org/iconv-lite/-/iconv-lite-0.6.3.tgz", + "integrity": "sha512-4fCk79wshMdzMp2rH06qWrJE4iolqLhCUH+OiuIgU++RB0+94NlDL81atO7GX55uUKueo0txHNtvEyI6D7WdMw==", + "dev": true, + "optional": true, + "dependencies": { + "safer-buffer": ">= 2.1.2 < 3.0.0" + }, + "engines": { + "node": ">=0.10.0" + } + }, + "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/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/env-paths": { + "version": "2.2.1", + "resolved": "https://registry.npmjs.org/env-paths/-/env-paths-2.2.1.tgz", + "integrity": "sha512-+h1lkLKhZMTYjog1VEpJNG7NZJWcuc2DDk/qsqSTRRCOXiLjeQ1d1/udrUGhqMxUgAlwKNZ0cf2uqan5GLuS2A==", + "dev": true, + "engines": { + "node": ">=6" + } + }, + "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/err-code": { + "version": "2.0.3", + "resolved": "https://registry.npmjs.org/err-code/-/err-code-2.0.3.tgz", + "integrity": "sha512-2bmlRpNKBxT/CRmPOlyISQpNj+qSeYvcym/uT0Jx2bMOlKLtSy1ZmLuVxSEKKyor/N5yhvp/ZiG1oE3DEYMSFA==", + "dev": true + }, + "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/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-goat": { + "version": "4.0.0", + "resolved": "https://registry.npmjs.org/escape-goat/-/escape-goat-4.0.0.tgz", + "integrity": "sha512-2Sd4ShcWxbx6OY1IHyla/CVNwvg7XwZVoXZHcSu9w9SReNP1EzzD5T8NWKIR38fIqEns9kDWKUQTXXAmlDrdPg==", + "dev": true, + "engines": { + "node": ">=12" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" + } + }, + "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.25.0", + "resolved": "https://registry.npmjs.org/eslint/-/eslint-8.25.0.tgz", + "integrity": "sha512-DVlJOZ4Pn50zcKW5bYH7GQK/9MsoQG2d5eDH0ebEkE8PbgzTTmtt/VTH9GGJ4BfeZCpBLqFfvsjX35UacUL83A==", + "dev": true, + "dependencies": { + "@eslint/eslintrc": "^1.3.3", + "@humanwhocodes/config-array": "^0.10.5", + "@humanwhocodes/module-importer": "^1.0.1", + "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.1", + "globals": "^13.15.0", + "globby": "^11.1.0", + "grapheme-splitter": "^1.0.4", + "ignore": "^5.2.0", + "import-fresh": "^3.0.0", + "imurmurhash": "^0.1.4", + "is-glob": "^4.0.0", + "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-prettier": { + "version": "8.5.0", + "resolved": "https://registry.npmjs.org/eslint-config-prettier/-/eslint-config-prettier-8.5.0.tgz", + "integrity": "sha512-obmWKLUNCnhtQRKc+tmnYuQl0pFU1ibYJQ5BGhTVB08bHe9wC8qUeG7c08dj9XX+AuPj1YSGSQIHl1pnDHZR0Q==", + "dev": true, + "bin": { + "eslint-config-prettier": "bin/cli.js" + }, + "peerDependencies": { + "eslint": ">=7.0.0" + } + }, + "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, + "dependencies": { + "prettier-linter-helpers": "^1.0.0" + }, + "engines": { + "node": ">=12.0.0" + }, + "peerDependencies": { + "eslint": ">=7.28.0", + "prettier": ">=2.0.0" + }, + "peerDependenciesMeta": { + "eslint-config-prettier": { + "optional": true + } + } + }, + "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/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": { + "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/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.0", + "resolved": "https://registry.npmjs.org/espree/-/espree-9.4.0.tgz", + "integrity": "sha512-DQmnRpLj7f6TgN/NYb0MTzJXL+vJF9h3pHy4JhCIs3zwcgez8xmGg3sXHcEO97BrmO2OSvCwMdfdlyl+E9KjOw==", + "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/eventemitter3": { + "version": "4.0.7", + "resolved": "https://registry.npmjs.org/eventemitter3/-/eventemitter3-4.0.7.tgz", + "integrity": "sha512-8guHBZCwKnFhYdHr2ysuRWErTwhoN2X8XELRlrRwpmfeY2jjuUN4taQMsULKUVo1K4DvZl+0pgfyoysHxvmvEw==", + "dev": true + }, + "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/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-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", + "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-glob/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/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-memoize": { + "version": "2.5.2", + "resolved": "https://registry.npmjs.org/fast-memoize/-/fast-memoize-2.5.2.tgz", + "integrity": "sha512-Ue0LwpDYErFbmNnZSF0UH6eImUwDmogUO1jyE+JbN2gsQz/jICm1Ve7t9QT0rNSsfJt+Hs4/S3GnsDVjL4HVrw==", + "dev": true + }, + "node_modules/fastq": { + "version": "1.13.0", + "resolved": "https://registry.npmjs.org/fastq/-/fastq-1.13.0.tgz", + "integrity": "sha512-YpkpUnK8od0o1hmeSc7UUs/eB/vIPWJYjKck2QKIzAf71Vm1AAQ3EbuZB3g2JIy+pg+ERD0vqI79KyZiB2e2Nw==", + "dev": true, + "dependencies": { + "reusify": "^1.0.4" + } + }, + "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/filelist": { + "version": "1.0.4", + "resolved": "https://registry.npmjs.org/filelist/-/filelist-1.0.4.tgz", + "integrity": "sha512-w1cEuf3S+DrLCQL7ET6kz+gmlJdbq9J7yXCSjK/OZCPA+qEN1WyF4ZAf0YYJa4/shHJra2t/d/r8SV4Ji+x+8Q==", + "dev": true, + "dependencies": { + "minimatch": "^5.0.1" + } + }, + "node_modules/filelist/node_modules/brace-expansion": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/brace-expansion/-/brace-expansion-2.0.1.tgz", + "integrity": "sha512-XnAIvQ8eM+kC6aULx6wuQiwVsnzsi9d3WxzV3FpWTGA19F621kwdbsAcFKXgKUHZWsy+mY6iL1sHTxWEFCytDA==", + "dev": true, + "dependencies": { + "balanced-match": "^1.0.0" + } + }, + "node_modules/filelist/node_modules/minimatch": { + "version": "5.1.0", + "resolved": "https://registry.npmjs.org/minimatch/-/minimatch-5.1.0.tgz", + "integrity": "sha512-9TPBGGak4nHfGZsPBohm9AWg6NoT7QTCehS3BIJABslyZbzxfV78QM2Y6+i741OPZIafFAaiiEMh5OyIrJPgtg==", + "dev": true, + "dependencies": { + "brace-expansion": "^2.0.1" + }, + "engines": { + "node": ">=10" + } + }, + "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/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": { + "version": "5.0.2", + "resolved": "https://registry.npmjs.org/flat/-/flat-5.0.2.tgz", + "integrity": "sha512-b6suED+5/3rTpUBdG1gupIl8MPFCAMA0QXwmljLhvCUKcUvdE4gWky9zpuGCcXHOsz4J9wPGNWq6OKpmIzz3hQ==", + "dev": true, + "bin": { + "flat": "cli.js" + } + }, + "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/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", + "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/foreground-child": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/foreground-child/-/foreground-child-2.0.0.tgz", + "integrity": "sha512-dCIq9FpEcyQyXKCkyzmlPTFNgrCzPudOe+mhvJU5zAtlBnGVy2yKxtfsxK2tQBThwq225jcvBjpw1Gr40uzZCA==", + "dev": true, + "dependencies": { + "cross-spawn": "^7.0.0", + "signal-exit": "^3.0.2" + }, + "engines": { + "node": ">=8.0.0" + } + }, + "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/form-data-encoder": { + "version": "2.1.3", + "resolved": "https://registry.npmjs.org/form-data-encoder/-/form-data-encoder-2.1.3.tgz", + "integrity": "sha512-KqU0nnPMgIJcCOFTNJFEA8epcseEaoox4XZffTgy8jlI6pL/5EFyR54NRG7CnCJN0biY7q52DO3MH6/sJ/TKlQ==", + "dev": true, + "engines": { + "node": ">= 14.17" + } + }, + "node_modules/fp-and-or": { + "version": "0.1.3", + "resolved": "https://registry.npmjs.org/fp-and-or/-/fp-and-or-0.1.3.tgz", + "integrity": "sha512-wJaE62fLaB3jCYvY2ZHjZvmKK2iiLiiehX38rz5QZxtdN8fVPJDeZUiVvJrHStdTc+23LHlyZuSEKgFc0pxi2g==", + "dev": true, + "engines": { + "node": ">=10" + } + }, + "node_modules/fs-constants": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/fs-constants/-/fs-constants-1.0.0.tgz", + "integrity": "sha512-y6OAwoSIf7FyjMIv94u+b5rdheZEjzR63GTyZJm5qh4Bi+2YgwLCcI/fPFZkL5PSixOt6ZNKm+w+Hfp/Bciwow==", + "dev": true + }, + "node_modules/fs-extra": { + "version": "9.1.0", + "resolved": "https://registry.npmjs.org/fs-extra/-/fs-extra-9.1.0.tgz", + "integrity": "sha512-hcg3ZmepS30/7BSFqRvoo3DOMQu7IjqxO5nCDt+zM9XWjb33Wg7ziNT+Qvqbuc3+gWpzO02JubVyk2G4Zvo1OQ==", + "dev": true, + "dependencies": { + "at-least-node": "^1.0.0", + "graceful-fs": "^4.2.0", + "jsonfile": "^6.0.1", + "universalify": "^2.0.0" + }, + "engines": { + "node": ">=10" + } + }, + "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==", + "dev": true, + "dependencies": { + "minipass": "^3.0.0" + }, + "engines": { + "node": ">= 8" + } + }, + "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/gauge": { + "version": "4.0.4", + "resolved": "https://registry.npmjs.org/gauge/-/gauge-4.0.4.tgz", + "integrity": "sha512-f9m+BEN5jkg6a0fZjleidjN51VE1X+mPFQ2DJ0uv1V39oCLCbsGe6yjbBnp7eK7z/+GAon99a3nHuqbuuthyPg==", + "dev": true, + "dependencies": { + "aproba": "^1.0.3 || ^2.0.0", + "color-support": "^1.1.3", + "console-control-strings": "^1.1.0", + "has-unicode": "^2.0.1", + "signal-exit": "^3.0.7", + "string-width": "^4.2.3", + "strip-ansi": "^6.0.1", + "wide-align": "^1.1.5" + }, + "engines": { + "node": "^12.13.0 || ^14.15.0 || >=16.0.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-pkg-repo": { + "version": "4.2.1", + "resolved": "https://registry.npmjs.org/get-pkg-repo/-/get-pkg-repo-4.2.1.tgz", + "integrity": "sha512-2+QbHjFRfGB74v/pYWjd5OhU3TDIC2Gv/YKUTk/tCvAz0pkn/Mz6P3uByuBimLOcPvN2jYdScl3xGFSrx0jEcA==", + "dev": true, + "dependencies": { + "@hutson/parse-repository-url": "^3.0.0", + "hosted-git-info": "^4.0.0", + "through2": "^2.0.0", + "yargs": "^16.2.0" + }, + "bin": { + "get-pkg-repo": "src/cli.js" + }, + "engines": { + "node": ">=6.9.0" + } + }, + "node_modules/get-pkg-repo/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/get-pkg-repo/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/get-pkg-repo/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/get-pkg-repo/node_modules/through2": { + "version": "2.0.5", + "resolved": "https://registry.npmjs.org/through2/-/through2-2.0.5.tgz", + "integrity": "sha512-/mrRod8xqpA+IHSLyGCQ2s8SPHiCDEeQJSep1jqLYeEUClOFG2Qsh+4FU6G9VeqpZnGW/Su8LQGc4YKni5rYSQ==", + "dev": true, + "dependencies": { + "readable-stream": "~2.3.6", + "xtend": "~4.0.1" + } + }, + "node_modules/get-port": { + "version": "5.1.1", + "resolved": "https://registry.npmjs.org/get-port/-/get-port-5.1.1.tgz", + "integrity": "sha512-g/Q1aTSDOxFpchXC4i8ZWvxA1lnPqx/JHqcpIw0/LX9T8x/GBbi6YnlN5nhaKIFkT8oFsscUKgDJYxfwfS6QsQ==", + "dev": true, + "engines": { + "node": ">=8" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" + } + }, + "node_modules/get-stdin": { + "version": "8.0.0", + "resolved": "https://registry.npmjs.org/get-stdin/-/get-stdin-8.0.0.tgz", + "integrity": "sha512-sY22aA6xchAzprjyqmSEQv4UbAAzRN0L2dQB0NlN5acTTK9Don6nhoc3eAbUnpZiCANAMfd/+40kVdKfFygohg==", + "dev": true, + "engines": { + "node": ">=10" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" + } + }, + "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/git-raw-commits": { + "version": "2.0.11", + "resolved": "https://registry.npmjs.org/git-raw-commits/-/git-raw-commits-2.0.11.tgz", + "integrity": "sha512-VnctFhw+xfj8Va1xtfEqCUD2XDrbAPSJx+hSrE5K7fGdjZruW7XV+QOrN7LF/RJyvspRiD2I0asWsxFp0ya26A==", + "dev": true, + "dependencies": { + "dargs": "^7.0.0", + "lodash": "^4.17.15", + "meow": "^8.0.0", + "split2": "^3.0.0", + "through2": "^4.0.0" + }, + "bin": { + "git-raw-commits": "cli.js" + }, + "engines": { + "node": ">=10" + } + }, + "node_modules/git-remote-origin-url": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/git-remote-origin-url/-/git-remote-origin-url-2.0.0.tgz", + "integrity": "sha512-eU+GGrZgccNJcsDH5LkXR3PB9M958hxc7sbA8DFJjrv9j4L2P/eZfKhM+QD6wyzpiv+b1BpK0XrYCxkovtjSLw==", + "dev": true, + "dependencies": { + "gitconfiglocal": "^1.0.0", + "pify": "^2.3.0" + }, + "engines": { + "node": ">=4" + } + }, + "node_modules/git-remote-origin-url/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/git-semver-tags": { + "version": "4.1.1", + "resolved": "https://registry.npmjs.org/git-semver-tags/-/git-semver-tags-4.1.1.tgz", + "integrity": "sha512-OWyMt5zBe7xFs8vglMmhM9lRQzCWL3WjHtxNNfJTMngGym7pC1kh8sP6jevfydJ6LP3ZvGxfb6ABYgPUM0mtsA==", + "dev": true, + "dependencies": { + "meow": "^8.0.0", + "semver": "^6.0.0" + }, + "bin": { + "git-semver-tags": "cli.js" + }, + "engines": { + "node": ">=10" + } + }, + "node_modules/git-semver-tags/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/git-up": { + "version": "7.0.0", + "resolved": "https://registry.npmjs.org/git-up/-/git-up-7.0.0.tgz", + "integrity": "sha512-ONdIrbBCFusq1Oy0sC71F5azx8bVkvtZtMJAsv+a6lz5YAmbNnLD6HAB4gptHZVLPR8S2/kVN6Gab7lryq5+lQ==", + "dev": true, + "dependencies": { + "is-ssh": "^1.4.0", + "parse-url": "^8.1.0" + } + }, + "node_modules/git-url-parse": { + "version": "13.1.0", + "resolved": "https://registry.npmjs.org/git-url-parse/-/git-url-parse-13.1.0.tgz", + "integrity": "sha512-5FvPJP/70WkIprlUZ33bm4UAaFdjcLkJLpWft1BeZKqwR0uhhNGoKwlUaPtVb4LxCSQ++erHapRak9kWGj+FCA==", + "dev": true, + "dependencies": { + "git-up": "^7.0.0" + } + }, + "node_modules/gitconfiglocal": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/gitconfiglocal/-/gitconfiglocal-1.0.0.tgz", + "integrity": "sha512-spLUXeTAVHxDtKsJc8FkFVgFtMdEN9qPGpL23VfSHx4fP4+Ds097IXLvymbnDH8FnmxX5Nr9bPw3A+AQ6mWEaQ==", + "dev": true, + "dependencies": { + "ini": "^1.3.2" + } + }, + "node_modules/glob": { + "version": "8.0.3", + "resolved": "https://registry.npmjs.org/glob/-/glob-8.0.3.tgz", + "integrity": "sha512-ull455NHSHI/Y1FqGaaYFaLGkNMMJbavMrEGFXG/PGrg6y7sutWHUHrz6gy6WEBH6akM1M414dWKCNs+IhKdiQ==", + "dev": true, + "dependencies": { + "fs.realpath": "^1.0.0", + "inflight": "^1.0.4", + "inherits": "2", + "minimatch": "^5.0.1", + "once": "^1.3.0" + }, + "engines": { + "node": ">=12" + }, + "funding": { + "url": "https://github.com/sponsors/isaacs" + } + }, + "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/glob/node_modules/brace-expansion": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/brace-expansion/-/brace-expansion-2.0.1.tgz", + "integrity": "sha512-XnAIvQ8eM+kC6aULx6wuQiwVsnzsi9d3WxzV3FpWTGA19F621kwdbsAcFKXgKUHZWsy+mY6iL1sHTxWEFCytDA==", + "dev": true, + "dependencies": { + "balanced-match": "^1.0.0" + } + }, + "node_modules/glob/node_modules/minimatch": { + "version": "5.1.0", + "resolved": "https://registry.npmjs.org/minimatch/-/minimatch-5.1.0.tgz", + "integrity": "sha512-9TPBGGak4nHfGZsPBohm9AWg6NoT7QTCehS3BIJABslyZbzxfV78QM2Y6+i741OPZIafFAaiiEMh5OyIrJPgtg==", + "dev": true, + "dependencies": { + "brace-expansion": "^2.0.1" + }, + "engines": { + "node": ">=10" + } + }, + "node_modules/global-dirs": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/global-dirs/-/global-dirs-3.0.0.tgz", + "integrity": "sha512-v8ho2DS5RiCjftj1nD9NmnfaOzTdud7RRnVd9kFNOjqZbISlx5DQ+OrTkywgd0dIt7oFCvKetZSHoHcP3sDdiA==", + "dev": true, + "dependencies": { + "ini": "2.0.0" + }, + "engines": { + "node": ">=10" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" + } + }, + "node_modules/global-dirs/node_modules/ini": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/ini/-/ini-2.0.0.tgz", + "integrity": "sha512-7PnF4oN3CvZF23ADhA5wRaYEQpJ8qygSkbtTXWBeXWXmEVRXK+1ITciHWwHhsjv1TmW0MgacIv6hEi5pX5NQdA==", + "dev": true, + "engines": { + "node": ">=10" + } + }, + "node_modules/globals": { + "version": "13.17.0", + "resolved": "https://registry.npmjs.org/globals/-/globals-13.17.0.tgz", + "integrity": "sha512-1C+6nQRb1GwGMKm2dH/E7enFAMxGTmGI7/dEdhy/DNelv85w9B72t3uc5frtMNXIbzrarJJ/lTCjcaZwbLJmyw==", + "dev": true, + "dependencies": { + "type-fest": "^0.20.2" + }, + "engines": { + "node": ">=8" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" + } + }, + "node_modules/globals/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/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/got": { + "version": "12.5.1", + "resolved": "https://registry.npmjs.org/got/-/got-12.5.1.tgz", + "integrity": "sha512-sD16AK8cCyUoPtKr/NMvLTFFa+T3i3S+zoiuvhq0HP2YiqBZA9AtlBjAdsQBsLBK7slPuvmfE0OxhGi7N5dD4w==", + "dev": true, + "dependencies": { + "@sindresorhus/is": "^5.2.0", + "@szmarczak/http-timer": "^5.0.1", + "cacheable-lookup": "^7.0.0", + "cacheable-request": "^10.2.1", + "decompress-response": "^6.0.0", + "form-data-encoder": "^2.1.2", + "get-stream": "^6.0.1", + "http2-wrapper": "^2.1.10", + "lowercase-keys": "^3.0.0", + "p-cancelable": "^3.0.0", + "responselike": "^3.0.0" + }, + "engines": { + "node": ">=14.16" + }, + "funding": { + "url": "https://github.com/sindresorhus/got?sponsor=1" + } + }, + "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/handlebars": { + "version": "4.7.7", + "resolved": "https://registry.npmjs.org/handlebars/-/handlebars-4.7.7.tgz", + "integrity": "sha512-aAcXm5OAfE/8IXkcZvCepKU3VzW1/39Fb5ZuqMtgI/hT8X2YgoMvBY5dLhq/cpOvw7Lk1nK/UF71aLG/ZnVYRA==", + "dev": true, + "dependencies": { + "minimist": "^1.2.5", + "neo-async": "^2.6.0", + "source-map": "^0.6.1", + "wordwrap": "^1.0.0" + }, + "bin": { + "handlebars": "bin/handlebars" + }, + "engines": { + "node": ">=0.4.7" + }, + "optionalDependencies": { + "uglify-js": "^3.1.4" + } + }, + "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", + "integrity": "sha512-f2dvO0VU6Oej7RkWJGrehjbzMAjFp5/VKPp5tTpWIV4JHHZK1/BxbFRtf/siA2SWTe09caDmVtYYzWEIbBS4zw==", + "dev": true, + "dependencies": { + "function-bind": "^1.1.1" + }, + "engines": { + "node": ">= 0.4.0" + } + }, + "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/has-unicode": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/has-unicode/-/has-unicode-2.0.1.tgz", + "integrity": "sha512-8Rf9Y83NBReMnx0gFzA8JImQACstCYWUplepDa9xprwwtmgEZUF0h/i5xSA625zB/I37EtrswSST6OXxwaaIJQ==", + "dev": true + }, + "node_modules/has-yarn": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/has-yarn/-/has-yarn-3.0.0.tgz", + "integrity": "sha512-IrsVwUHhEULx3R8f/aA8AHuEzAorplsab/v8HBzEiIukwq5i/EC+xmOW+HfP1OaDP+2JkgT1yILHN2O3UFIbcA==", + "dev": true, + "engines": { + "node": "^12.20.0 || ^14.13.1 || >=16.0.0" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" + } + }, + "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/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-cache-semantics": { + "version": "4.1.0", + "resolved": "https://registry.npmjs.org/http-cache-semantics/-/http-cache-semantics-4.1.0.tgz", + "integrity": "sha512-carPklcUh7ROWRK7Cv27RPtdhYhUsela/ue5/jKzjegVvXDqM2ILE9Q2BGn9JZJh1g87cp56su/FgQSzcWS8cQ==", + "dev": true + }, + "node_modules/http-proxy-agent": { + "version": "5.0.0", + "resolved": "https://registry.npmjs.org/http-proxy-agent/-/http-proxy-agent-5.0.0.tgz", + "integrity": "sha512-n2hY8YdoRE1i7r6M0w9DIw5GgZN0G25P8zLCRQ8rjXtTU3vsNFBI/vWK/UIeE6g5MUUz6avwAPXmL6Fy9D/90w==", + "dev": true, + "dependencies": { + "@tootallnate/once": "2", + "agent-base": "6", + "debug": "4" + }, + "engines": { + "node": ">= 6" + } + }, + "node_modules/http2-wrapper": { + "version": "2.1.11", + "resolved": "https://registry.npmjs.org/http2-wrapper/-/http2-wrapper-2.1.11.tgz", + "integrity": "sha512-aNAk5JzLturWEUiuhAN73Jcbq96R7rTitAoXV54FYMatvihnpD2+6PUgU4ce3D/m5VDbw+F5CsyKSF176ptitQ==", + "dev": true, + "dependencies": { + "quick-lru": "^5.1.1", + "resolve-alpn": "^1.2.0" + }, + "engines": { + "node": ">=10.19.0" + } + }, + "node_modules/http2-wrapper/node_modules/quick-lru": { + "version": "5.1.1", + "resolved": "https://registry.npmjs.org/quick-lru/-/quick-lru-5.1.1.tgz", + "integrity": "sha512-WuyALRjWPDGtt/wzJiadO5AXY+8hZ80hVpe6MyivgraREW751X3SbhRvG3eLKOYN+8VEvqLcf3wdnt44Z4S4SA==", + "dev": true, + "engines": { + "node": ">=10" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" + } + }, + "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==", + "dev": true, + "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", + "integrity": "sha512-B4FFZ6q/T2jhhksgkbEW3HBvWIfDW85snkQgawt07S7J5QXTk6BkNV+0yAeZrM5QpMAdYlocGoljn0sJ/WQkFw==", + "dev": true, + "engines": { + "node": ">=10.17.0" + } + }, + "node_modules/humanize-ms": { + "version": "1.2.1", + "resolved": "https://registry.npmjs.org/humanize-ms/-/humanize-ms-1.2.1.tgz", + "integrity": "sha512-Fl70vYtsAFb/C06PTS9dZBo7ihau+Tu/DNCk/OyHhea07S+aeMWpFFkUaXRa8fI+ScZbEI8dfSxwY7gxZ9SAVQ==", + "dev": true, + "dependencies": { + "ms": "^2.0.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/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.0", + "resolved": "https://registry.npmjs.org/ignore/-/ignore-5.2.0.tgz", + "integrity": "sha512-CmxgYGiEPCLhfLnpPp1MoRmifwEIOgjcHXxOBjv7mY96c+eWScsOP9c112ZyLdWHi0FxHjI+4uVhKYp/gcdRmQ==", + "dev": true, + "engines": { + "node": ">= 4" + } + }, + "node_modules/ignore-walk": { + "version": "5.0.1", + "resolved": "https://registry.npmjs.org/ignore-walk/-/ignore-walk-5.0.1.tgz", + "integrity": "sha512-yemi4pMf51WKT7khInJqAvsIGzoqYXblnsz0ql8tM+yi1EKYTY1evX4NAbJrLL/Aanr2HyZeluqU+Oi7MGHokw==", + "dev": true, + "dependencies": { + "minimatch": "^5.0.1" + }, + "engines": { + "node": "^12.13.0 || ^14.15.0 || >=16.0.0" + } + }, + "node_modules/ignore-walk/node_modules/brace-expansion": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/brace-expansion/-/brace-expansion-2.0.1.tgz", + "integrity": "sha512-XnAIvQ8eM+kC6aULx6wuQiwVsnzsi9d3WxzV3FpWTGA19F621kwdbsAcFKXgKUHZWsy+mY6iL1sHTxWEFCytDA==", + "dev": true, + "dependencies": { + "balanced-match": "^1.0.0" + } + }, + "node_modules/ignore-walk/node_modules/minimatch": { + "version": "5.1.0", + "resolved": "https://registry.npmjs.org/minimatch/-/minimatch-5.1.0.tgz", + "integrity": "sha512-9TPBGGak4nHfGZsPBohm9AWg6NoT7QTCehS3BIJABslyZbzxfV78QM2Y6+i741OPZIafFAaiiEMh5OyIrJPgtg==", + "dev": true, + "dependencies": { + "brace-expansion": "^2.0.1" + }, + "engines": { + "node": ">=10" + } + }, + "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-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", + "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/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/infer-owner": { + "version": "1.0.4", + "resolved": "https://registry.npmjs.org/infer-owner/-/infer-owner-1.0.4.tgz", + "integrity": "sha512-IClj+Xz94+d7irH5qRyfJonOdfTzuDaifE6ZPWfx0N0+/ATZCbuTPq2prFl526urkQd90WyUKIh1DfBQ2hMz9A==", + "dev": true + }, + "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/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/init-package-json": { + "version": "3.0.2", + "resolved": "https://registry.npmjs.org/init-package-json/-/init-package-json-3.0.2.tgz", + "integrity": "sha512-YhlQPEjNFqlGdzrBfDNRLhvoSgX7iQRgSxgsNknRQ9ITXFT7UMfVMWhBTOh2Y+25lRnGrv5Xz8yZwQ3ACR6T3A==", + "dev": true, + "dependencies": { + "npm-package-arg": "^9.0.1", + "promzard": "^0.3.0", + "read": "^1.0.7", + "read-package-json": "^5.0.0", + "semver": "^7.3.5", + "validate-npm-package-license": "^3.0.4", + "validate-npm-package-name": "^4.0.0" + }, + "engines": { + "node": "^12.13.0 || ^14.15.0 || >=16.0.0" + } + }, + "node_modules/init-package-json/node_modules/hosted-git-info": { + "version": "5.1.0", + "resolved": "https://registry.npmjs.org/hosted-git-info/-/hosted-git-info-5.1.0.tgz", + "integrity": "sha512-Ek+QmMEqZF8XrbFdwoDjSbm7rT23pCgEMOJmz6GPk/s4yH//RQfNPArhIxbguNxROq/+5lNBwCDHMhA903Kx1Q==", + "dev": true, + "dependencies": { + "lru-cache": "^7.5.1" + }, + "engines": { + "node": "^12.13.0 || ^14.15.0 || >=16.0.0" + } + }, + "node_modules/init-package-json/node_modules/npm-package-arg": { + "version": "9.1.2", + "resolved": "https://registry.npmjs.org/npm-package-arg/-/npm-package-arg-9.1.2.tgz", + "integrity": "sha512-pzd9rLEx4TfNJkovvlBSLGhq31gGu2QDexFPWT19yCDh0JgnRhlBLNo5759N0AJmBk+kQ9Y/hXoLnlgFD+ukmg==", + "dev": true, + "dependencies": { + "hosted-git-info": "^5.0.0", + "proc-log": "^2.0.1", + "semver": "^7.3.5", + "validate-npm-package-name": "^4.0.0" + }, + "engines": { + "node": "^12.13.0 || ^14.15.0 || >=16.0.0" + } + }, + "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/ip": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/ip/-/ip-2.0.0.tgz", + "integrity": "sha512-WKa+XuLG1A1R0UWhl2+1XQSi+fZWMsYKffMZTTYsiZaUD8k2yDAj5atimTUD2TZkyCkNEeYE5NhFZmupOGtjYQ==", + "dev": true + }, + "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-ci": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/is-ci/-/is-ci-2.0.0.tgz", + "integrity": "sha512-YfJT7rkpQB0updsdHLGWrvhBJfcfzNNawYDNIyQXJz0IViGf75O8EBPKSdvw2rF+LGCsX4FZ8tcr3b19LcZq4w==", + "dev": true, + "dependencies": { + "ci-info": "^2.0.0" + }, + "bin": { + "is-ci": "bin.js" + } + }, + "node_modules/is-core-module": { + "version": "2.10.0", + "resolved": "https://registry.npmjs.org/is-core-module/-/is-core-module-2.10.0.tgz", + "integrity": "sha512-Erxj2n/LDAZ7H8WNJXd9tw38GYM3dv8rk8Zcs+jJuxYTW7sozH+SS8NtrSjVL1/vpLvWi1hxy96IzjJ3EHTJJg==", + "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-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", + "integrity": "sha512-xelSayHH36ZgE7ZWhli7pW34hNbNl8Ojv5KVmkJD4hBdD3th8Tfk9vYasLM+mXWOZhFkgZfxhLSnrwRr4elSSg==", + "dev": true, + "dependencies": { + "is-extglob": "^2.1.1" + }, + "engines": { + "node": ">=0.10.0" + } + }, + "node_modules/is-installed-globally": { + "version": "0.4.0", + "resolved": "https://registry.npmjs.org/is-installed-globally/-/is-installed-globally-0.4.0.tgz", + "integrity": "sha512-iwGqO3J21aaSkC7jWnHP/difazwS7SFeIqxv6wEtLU8Y5KlzFTjyqcSIT0d8s4+dDhKytsk9PJZ2BkS5eZwQRQ==", + "dev": true, + "dependencies": { + "global-dirs": "^3.0.0", + "is-path-inside": "^3.0.2" + }, + "engines": { + "node": ">=10" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" + } + }, + "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-lambda": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/is-lambda/-/is-lambda-1.0.1.tgz", + "integrity": "sha512-z7CMFGNrENq5iFB9Bqo64Xk6Y9sg+epq1myIcdHaGnbMTYOxvzsEtdYqQUylB7LxfkvgrrjP32T6Ywciio9UIQ==", + "dev": true + }, + "node_modules/is-npm": { + "version": "6.0.0", + "resolved": "https://registry.npmjs.org/is-npm/-/is-npm-6.0.0.tgz", + "integrity": "sha512-JEjxbSmtPSt1c8XTkVrlujcXdKV1/tvuQ7GwKcAlyiVLeYFQ2VHat8xfrDJsIkhCdF/tZ7CiIR3sy141c6+gPQ==", + "dev": true, + "engines": { + "node": "^12.20.0 || ^14.13.1 || >=16.0.0" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" + } + }, + "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-obj": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/is-obj/-/is-obj-2.0.0.tgz", + "integrity": "sha512-drqDG3cbczxxEJRoOXcOjtdp1J/lyp1mNn0xaznRs8+muBhgQcrnbspox5X5fOw0HnMnbfDzvnEMEtqDEJEo8w==", + "dev": true, + "engines": { + "node": ">=8" + } + }, + "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": ">=8" + } + }, + "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/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/is-ssh": { + "version": "1.4.0", + "resolved": "https://registry.npmjs.org/is-ssh/-/is-ssh-1.4.0.tgz", + "integrity": "sha512-x7+VxdxOdlV3CYpjvRLBv5Lo9OJerlYanjwFrPR9fuGPjCiNiCzFgAWpiLAohSbsnH4ZAys3SBh+hq5rJosxUQ==", + "dev": true, + "dependencies": { + "protocols": "^2.0.1" + } + }, + "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-text-path": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/is-text-path/-/is-text-path-1.0.1.tgz", + "integrity": "sha512-xFuJpne9oFz5qDaodwmmG08e3CawH/2ZV8Qqza1Ko7Sk8POWbkRdwIoAWVhqvq0XeUzANEhKo2n0IXUGBm7A/w==", + "dev": true, + "dependencies": { + "text-extensions": "^1.0.0" + }, + "engines": { + "node": ">=0.10.0" + } + }, + "node_modules/is-typedarray": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/is-typedarray/-/is-typedarray-1.0.0.tgz", + "integrity": "sha512-cyA56iCMHAh5CdzjJIa4aohJyeO1YbwLi3Jc35MmRU6poroFjIGZzUzupGiRPOjgHg9TLu43xbpwXk523fMxKA==", + "dev": true + }, + "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-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/is-yarn-global": { + "version": "0.4.0", + "resolved": "https://registry.npmjs.org/is-yarn-global/-/is-yarn-global-0.4.0.tgz", + "integrity": "sha512-HneQBCrXGBy15QnaDfcn6OLoU8AQPAa0Qn0IeJR/QCo4E8dNZaGGwxpCwWyEBQC5QvFonP8d6t60iGpAHVAfNA==", + "dev": true, + "engines": { + "node": ">=12" + } + }, + "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/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-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-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/jake": { + "version": "10.8.5", + "resolved": "https://registry.npmjs.org/jake/-/jake-10.8.5.tgz", + "integrity": "sha512-sVpxYeuAhWt0OTWITwT98oyV0GsXyMlXCF+3L1SuafBVUIr/uILGRB+NqwkzhgXKvoJpDIpQvqkUALgdmQsQxw==", + "dev": true, + "dependencies": { + "async": "^3.2.3", + "chalk": "^4.0.2", + "filelist": "^1.0.1", + "minimatch": "^3.0.4" + }, + "bin": { + "jake": "bin/cli.js" + }, + "engines": { + "node": ">=10" + } + }, + "node_modules/jju": { + "version": "1.4.0", + "resolved": "https://registry.npmjs.org/jju/-/jju-1.4.0.tgz", + "integrity": "sha512-8wb9Yw966OSxApiCt0K3yNJL8pnNeIv+OEq2YMidz4FKP6nonSRoOXc80iXY4JaN2FC11B9qsNmDsm+ZOfMROA==", + "dev": true + }, + "node_modules/js-sdsl": { + "version": "4.1.5", + "resolved": "https://registry.npmjs.org/js-sdsl/-/js-sdsl-4.1.5.tgz", + "integrity": "sha512-08bOAKweV2NUC1wqTtf3qZlnpOX/R2DU9ikpjOHs0H+ibQv3zpncVQg6um4uYtRtrwIX8M4Nh3ytK4HGlYAq7Q==", + "dev": true + }, + "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/json-buffer": { + "version": "3.0.1", + "resolved": "https://registry.npmjs.org/json-buffer/-/json-buffer-3.0.1.tgz", + "integrity": "sha512-4bV5BfR2mqfQTJm+V5tPPdf+ZpuhiIvTuAB5g8kcrXOZpTT/QwwVRWBywX1ozr6lEuPdbHxwaJlm9G6mI2sfSQ==", + "dev": true + }, + "node_modules/json-parse-better-errors": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/json-parse-better-errors/-/json-parse-better-errors-1.0.2.tgz", + "integrity": "sha512-mrqyZKfX5EhL7hvqcV6WG1yYjnjeuYDzDhhcAAUrq8Po85NBQBJP+ZDUT75qZQ98IkUoBqdkExkukOU7Ts2wrw==", + "dev": true + }, + "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-parse-helpfulerror": { + "version": "1.0.3", + "resolved": "https://registry.npmjs.org/json-parse-helpfulerror/-/json-parse-helpfulerror-1.0.3.tgz", + "integrity": "sha512-XgP0FGR77+QhUxjXkwOMkC94k3WtqEBfcnjWqhRd82qTat4SWKRE+9kUnynz/shm3I4ea2+qISvTIeGTNU7kJg==", + "dev": true, + "dependencies": { + "jju": "^1.1.0" + } + }, + "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/json-stringify-nice": { + "version": "1.1.4", + "resolved": "https://registry.npmjs.org/json-stringify-nice/-/json-stringify-nice-1.1.4.tgz", + "integrity": "sha512-5Z5RFW63yxReJ7vANgW6eZFGWaQvnPE3WNmZoOJrSkGju2etKA2L5rrOa1sm877TVTFt57A80BH1bArcmlLfPw==", + "dev": true, + "funding": { + "url": "https://github.com/sponsors/isaacs" + } + }, + "node_modules/json-stringify-safe": { + "version": "5.0.1", + "resolved": "https://registry.npmjs.org/json-stringify-safe/-/json-stringify-safe-5.0.1.tgz", + "integrity": "sha512-ZClg6AaYvamvYEE82d3Iyd3vSSIjQ+odgjaTzRuO3s7toCdFKczob2i0zCh7JE8kWn17yvAWhUVxvqGwUalsRA==", + "dev": true + }, + "node_modules/json5": { + "version": "2.2.1", + "resolved": "https://registry.npmjs.org/json5/-/json5-2.2.1.tgz", + "integrity": "sha512-1hqLFMSrGHRHxav9q9gNjJ5EXznIxGVO09xQRrwplcS8qs28pZ8s8hupZAmqDwZUmVZ2Qb2jnyPOWcDH8m8dlA==", + "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/jsonlines": { + "version": "0.1.1", + "resolved": "https://registry.npmjs.org/jsonlines/-/jsonlines-0.1.1.tgz", + "integrity": "sha512-ekDrAGso79Cvf+dtm+mL8OBI2bmAOt3gssYs833De/C9NmIpWDWyUO4zPgB5x2/OhY366dkhgfPMYfwZF7yOZA==", + "dev": true + }, + "node_modules/jsonparse": { + "version": "1.3.1", + "resolved": "https://registry.npmjs.org/jsonparse/-/jsonparse-1.3.1.tgz", + "integrity": "sha512-POQXvpdL69+CluYsillJ7SUhKvytYjW9vG/GKpnf+xP8UWgYEM/RaMzHHofbALDiKbbP1W8UEYmgGl39WkPZsg==", + "dev": true, + "engines": [ + "node >= 0.2.0" + ] + }, + "node_modules/JSONStream": { + "version": "1.3.5", + "resolved": "https://registry.npmjs.org/JSONStream/-/JSONStream-1.3.5.tgz", + "integrity": "sha512-E+iruNOY8VV9s4JEbe1aNEm6MiszPRr/UfcHMz0TQh1BXSxHK+ASV1R6W4HpjBhSeS+54PIsAMCBmwD06LLsqQ==", + "dev": true, + "dependencies": { + "jsonparse": "^1.2.0", + "through": ">=2.2.7 <3" + }, + "bin": { + "JSONStream": "bin.js" + }, + "engines": { + "node": "*" + } + }, + "node_modules/just-diff": { + "version": "5.1.1", + "resolved": "https://registry.npmjs.org/just-diff/-/just-diff-5.1.1.tgz", + "integrity": "sha512-u8HXJ3HlNrTzY7zrYYKjNEfBlyjqhdBkoyTVdjtn7p02RJD5NvR8rIClzeGA7t+UYP1/7eAkWNLU0+P3QrEqKQ==", + "dev": true + }, + "node_modules/just-diff-apply": { + "version": "5.4.1", + "resolved": "https://registry.npmjs.org/just-diff-apply/-/just-diff-apply-5.4.1.tgz", + "integrity": "sha512-AAV5Jw7tsniWwih8Ly3fXxEZ06y+6p5TwQMsw0dzZ/wPKilzyDgdAnL0Ug4NNIquPUOh1vfFWEHbmXUqM5+o8g==", + "dev": true + }, + "node_modules/keyv": { + "version": "4.5.0", + "resolved": "https://registry.npmjs.org/keyv/-/keyv-4.5.0.tgz", + "integrity": "sha512-2YvuMsA+jnFGtBareKqgANOEKe1mk3HKiXu2fRmAfyxG0MJAywNhi5ttWA3PMjl4NmpyjZNbFifR2vNjW1znfA==", + "dev": true, + "dependencies": { + "json-buffer": "3.0.1" + } + }, + "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/kleur": { + "version": "4.1.5", + "resolved": "https://registry.npmjs.org/kleur/-/kleur-4.1.5.tgz", + "integrity": "sha512-o+NO+8WrRiQEE4/7nwRJhN1HWpVmJm511pBHUxPLtp0BUISzlBplORYSmTclCnJvQq2tKu/sgl3xVpkc7ZWuQQ==", + "dev": true, + "engines": { + "node": ">=6" + } + }, + "node_modules/latest-version": { + "version": "7.0.0", + "resolved": "https://registry.npmjs.org/latest-version/-/latest-version-7.0.0.tgz", + "integrity": "sha512-KvNT4XqAMzdcL6ka6Tl3i2lYeFDgXNCuIX+xNx6ZMVR1dFq+idXd9FLKNMOIx0t9mJ9/HudyX4oZWXZQ0UJHeg==", + "dev": true, + "dependencies": { + "package-json": "^8.1.0" + }, + "engines": { + "node": ">=14.16" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" + } + }, + "node_modules/lerna": { + "version": "5.6.2", + "resolved": "https://registry.npmjs.org/lerna/-/lerna-5.6.2.tgz", + "integrity": "sha512-Y0yMPslvnBnTZi7Nrs/gDyYZYauNf61xWNCehISHIORxZmmpoluNkcWTfcyb47is5uJQCv5QJX5xKKubbs+a6w==", + "dev": true, + "dependencies": { + "@lerna/add": "5.6.2", + "@lerna/bootstrap": "5.6.2", + "@lerna/changed": "5.6.2", + "@lerna/clean": "5.6.2", + "@lerna/cli": "5.6.2", + "@lerna/command": "5.6.2", + "@lerna/create": "5.6.2", + "@lerna/diff": "5.6.2", + "@lerna/exec": "5.6.2", + "@lerna/import": "5.6.2", + "@lerna/info": "5.6.2", + "@lerna/init": "5.6.2", + "@lerna/link": "5.6.2", + "@lerna/list": "5.6.2", + "@lerna/publish": "5.6.2", + "@lerna/run": "5.6.2", + "@lerna/version": "5.6.2", + "@nrwl/devkit": ">=14.8.1 < 16", + "import-local": "^3.0.2", + "inquirer": "^8.2.4", + "npmlog": "^6.0.2", + "nx": ">=14.8.1 < 16", + "typescript": "^3 || ^4" + }, + "bin": { + "lerna": "cli.js" + }, + "engines": { + "node": "^14.15.0 || >=16.0.0" + } + }, + "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/libnpmaccess": { + "version": "6.0.4", + "resolved": "https://registry.npmjs.org/libnpmaccess/-/libnpmaccess-6.0.4.tgz", + "integrity": "sha512-qZ3wcfIyUoW0+qSFkMBovcTrSGJ3ZeyvpR7d5N9pEYv/kXs8sHP2wiqEIXBKLFrZlmM0kR0RJD7mtfLngtlLag==", + "dev": true, + "dependencies": { + "aproba": "^2.0.0", + "minipass": "^3.1.1", + "npm-package-arg": "^9.0.1", + "npm-registry-fetch": "^13.0.0" + }, + "engines": { + "node": "^12.13.0 || ^14.15.0 || >=16.0.0" + } + }, + "node_modules/libnpmaccess/node_modules/hosted-git-info": { + "version": "5.1.0", + "resolved": "https://registry.npmjs.org/hosted-git-info/-/hosted-git-info-5.1.0.tgz", + "integrity": "sha512-Ek+QmMEqZF8XrbFdwoDjSbm7rT23pCgEMOJmz6GPk/s4yH//RQfNPArhIxbguNxROq/+5lNBwCDHMhA903Kx1Q==", + "dev": true, + "dependencies": { + "lru-cache": "^7.5.1" + }, + "engines": { + "node": "^12.13.0 || ^14.15.0 || >=16.0.0" + } + }, + "node_modules/libnpmaccess/node_modules/npm-package-arg": { + "version": "9.1.2", + "resolved": "https://registry.npmjs.org/npm-package-arg/-/npm-package-arg-9.1.2.tgz", + "integrity": "sha512-pzd9rLEx4TfNJkovvlBSLGhq31gGu2QDexFPWT19yCDh0JgnRhlBLNo5759N0AJmBk+kQ9Y/hXoLnlgFD+ukmg==", + "dev": true, + "dependencies": { + "hosted-git-info": "^5.0.0", + "proc-log": "^2.0.1", + "semver": "^7.3.5", + "validate-npm-package-name": "^4.0.0" + }, + "engines": { + "node": "^12.13.0 || ^14.15.0 || >=16.0.0" + } + }, + "node_modules/libnpmpublish": { + "version": "6.0.5", + "resolved": "https://registry.npmjs.org/libnpmpublish/-/libnpmpublish-6.0.5.tgz", + "integrity": "sha512-LUR08JKSviZiqrYTDfywvtnsnxr+tOvBU0BF8H+9frt7HMvc6Qn6F8Ubm72g5hDTHbq8qupKfDvDAln2TVPvFg==", + "dev": true, + "dependencies": { + "normalize-package-data": "^4.0.0", + "npm-package-arg": "^9.0.1", + "npm-registry-fetch": "^13.0.0", + "semver": "^7.3.7", + "ssri": "^9.0.0" + }, + "engines": { + "node": "^12.13.0 || ^14.15.0 || >=16.0.0" + } + }, + "node_modules/libnpmpublish/node_modules/hosted-git-info": { + "version": "5.1.0", + "resolved": "https://registry.npmjs.org/hosted-git-info/-/hosted-git-info-5.1.0.tgz", + "integrity": "sha512-Ek+QmMEqZF8XrbFdwoDjSbm7rT23pCgEMOJmz6GPk/s4yH//RQfNPArhIxbguNxROq/+5lNBwCDHMhA903Kx1Q==", + "dev": true, + "dependencies": { + "lru-cache": "^7.5.1" + }, + "engines": { + "node": "^12.13.0 || ^14.15.0 || >=16.0.0" + } + }, + "node_modules/libnpmpublish/node_modules/normalize-package-data": { + "version": "4.0.1", + "resolved": "https://registry.npmjs.org/normalize-package-data/-/normalize-package-data-4.0.1.tgz", + "integrity": "sha512-EBk5QKKuocMJhB3BILuKhmaPjI8vNRSpIfO9woLC6NyHVkKKdVEdAO1mrT0ZfxNR1lKwCcTkuZfmGIFdizZ8Pg==", + "dev": true, + "dependencies": { + "hosted-git-info": "^5.0.0", + "is-core-module": "^2.8.1", + "semver": "^7.3.5", + "validate-npm-package-license": "^3.0.4" + }, + "engines": { + "node": "^12.13.0 || ^14.15.0 || >=16.0.0" + } + }, + "node_modules/libnpmpublish/node_modules/npm-package-arg": { + "version": "9.1.2", + "resolved": "https://registry.npmjs.org/npm-package-arg/-/npm-package-arg-9.1.2.tgz", + "integrity": "sha512-pzd9rLEx4TfNJkovvlBSLGhq31gGu2QDexFPWT19yCDh0JgnRhlBLNo5759N0AJmBk+kQ9Y/hXoLnlgFD+ukmg==", + "dev": true, + "dependencies": { + "hosted-git-info": "^5.0.0", + "proc-log": "^2.0.1", + "semver": "^7.3.5", + "validate-npm-package-name": "^4.0.0" + }, + "engines": { + "node": "^12.13.0 || ^14.15.0 || >=16.0.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/load-json-file": { + "version": "6.2.0", + "resolved": "https://registry.npmjs.org/load-json-file/-/load-json-file-6.2.0.tgz", + "integrity": "sha512-gUD/epcRms75Cw8RT1pUdHugZYM5ce64ucs2GEISABwkRsOQr0q2wm/MV2TKThycIe5e0ytRweW2RZxclogCdQ==", + "dev": true, + "dependencies": { + "graceful-fs": "^4.1.15", + "parse-json": "^5.0.0", + "strip-bom": "^4.0.0", + "type-fest": "^0.6.0" + }, + "engines": { + "node": ">=8" + } + }, + "node_modules/load-json-file/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/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", + "integrity": "sha512-v2kDEe57lecTulaDIuNTPy3Ry4gLGJ6Z1O3vE1krgXZNrsQ+LFTGHVxVjcXPs17LhbZVGedAJv8XZ1tvj5FvSg==", + "dev": true + }, + "node_modules/lodash.ismatch": { + "version": "4.4.0", + "resolved": "https://registry.npmjs.org/lodash.ismatch/-/lodash.ismatch-4.4.0.tgz", + "integrity": "sha512-fPMfXjGQEV9Xsq/8MTSgUf255gawYRbjwMyDbcvDhXgV7enSZA0hynz6vMPnpAb5iONEzBHBPsT+0zes5Z301g==", + "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/lowercase-keys": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/lowercase-keys/-/lowercase-keys-3.0.0.tgz", + "integrity": "sha512-ozCC6gdQ+glXOQsveKD0YsDy8DSQFjDTz4zyzEHNV5+JP5D62LmfDZ6o1cycFx9ouG940M5dE8C8CTewdj2YWQ==", + "dev": true, + "engines": { + "node": "^12.20.0 || ^14.13.1 || >=16.0.0" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" + } + }, + "node_modules/lru-cache": { + "version": "7.14.0", + "resolved": "https://registry.npmjs.org/lru-cache/-/lru-cache-7.14.0.tgz", + "integrity": "sha512-EIRtP1GrSJny0dqb50QXRUNBxHJhcpxHC++M5tD7RYbvLLn5KVWKsbyswSSqDuU15UFi3bgTQIY8nhDMeF6aDQ==", + "dev": true, + "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-fetch-happen": { + "version": "10.2.1", + "resolved": "https://registry.npmjs.org/make-fetch-happen/-/make-fetch-happen-10.2.1.tgz", + "integrity": "sha512-NgOPbRiaQM10DYXvN3/hhGVI2M5MtITFryzBGxHM5p4wnFxsVCbxkrBrDsk+EZ5OB4jEOT7AjDxtdF+KVEFT7w==", + "dev": true, + "dependencies": { + "agentkeepalive": "^4.2.1", + "cacache": "^16.1.0", + "http-cache-semantics": "^4.1.0", + "http-proxy-agent": "^5.0.0", + "https-proxy-agent": "^5.0.0", + "is-lambda": "^1.0.1", + "lru-cache": "^7.7.1", + "minipass": "^3.1.6", + "minipass-collect": "^1.0.2", + "minipass-fetch": "^2.0.3", + "minipass-flush": "^1.0.5", + "minipass-pipeline": "^1.2.4", + "negotiator": "^0.6.3", + "promise-retry": "^2.0.1", + "socks-proxy-agent": "^7.0.0", + "ssri": "^9.0.0" + }, + "engines": { + "node": "^12.13.0 || ^14.15.0 || >=16.0.0" + } + }, + "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/meow": { + "version": "8.1.2", + "resolved": "https://registry.npmjs.org/meow/-/meow-8.1.2.tgz", + "integrity": "sha512-r85E3NdZ+mpYk1C6RjPFEMSE+s1iZMuHtsHAqY0DT3jZczl0diWUZ8g6oU7h0M9cD2EL+PzaYghhCLzR0ZNn5Q==", + "dev": true, + "dependencies": { + "@types/minimist": "^1.2.0", + "camelcase-keys": "^6.2.2", + "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/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/meow/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/meow/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/meow/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/meow/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/meow/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/meow/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/meow/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/meow/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/meow/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/meow/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/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-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/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-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/mimic-response": { + "version": "4.0.0", + "resolved": "https://registry.npmjs.org/mimic-response/-/mimic-response-4.0.0.tgz", + "integrity": "sha512-e5ISH9xMYU0DzrT+jl8q2ze9D6eWBto+I8CNpe+VI+K2J/F/k3PdkdTdz4wvGVH4NTpo+NRYTVIuMQEMMcsLqg==", + "dev": true, + "engines": { + "node": "^12.20.0 || ^14.13.1 || >=16.0.0" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" + } + }, + "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/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==", + "dev": true, + "funding": { + "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/minipass": { + "version": "3.3.4", + "resolved": "https://registry.npmjs.org/minipass/-/minipass-3.3.4.tgz", + "integrity": "sha512-I9WPbWHCGu8W+6k1ZiGpPu0GkoKBeorkfKNuAFBNS1HNFJvke82sxvI5bzcCNpWPorkOO5QQ+zomzzwRxejXiw==", + "dev": true, + "dependencies": { + "yallist": "^4.0.0" + }, + "engines": { + "node": ">=8" + } + }, + "node_modules/minipass-collect": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/minipass-collect/-/minipass-collect-1.0.2.tgz", + "integrity": "sha512-6T6lH0H8OG9kITm/Jm6tdooIbogG9e0tLgpY6mphXSm/A9u8Nq1ryBG+Qspiub9LjWlBPsPS3tWQ/Botq4FdxA==", + "dev": true, + "dependencies": { + "minipass": "^3.0.0" + }, + "engines": { + "node": ">= 8" + } + }, + "node_modules/minipass-fetch": { + "version": "2.1.2", + "resolved": "https://registry.npmjs.org/minipass-fetch/-/minipass-fetch-2.1.2.tgz", + "integrity": "sha512-LT49Zi2/WMROHYoqGgdlQIZh8mLPZmOrN2NdJjMXxYe4nkN6FUyuPuOAOedNJDrx0IRGg9+4guZewtp8hE6TxA==", + "dev": true, + "dependencies": { + "minipass": "^3.1.6", + "minipass-sized": "^1.0.3", + "minizlib": "^2.1.2" + }, + "engines": { + "node": "^12.13.0 || ^14.15.0 || >=16.0.0" + }, + "optionalDependencies": { + "encoding": "^0.1.13" + } + }, + "node_modules/minipass-flush": { + "version": "1.0.5", + "resolved": "https://registry.npmjs.org/minipass-flush/-/minipass-flush-1.0.5.tgz", + "integrity": "sha512-JmQSYYpPUqX5Jyn1mXaRwOda1uQ8HP5KAT/oDSLCzt1BYRhQU0/hDtsB1ufZfEEzMZ9aAVmsBw8+FWsIXlClWw==", + "dev": true, + "dependencies": { + "minipass": "^3.0.0" + }, + "engines": { + "node": ">= 8" + } + }, + "node_modules/minipass-json-stream": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/minipass-json-stream/-/minipass-json-stream-1.0.1.tgz", + "integrity": "sha512-ODqY18UZt/I8k+b7rl2AENgbWE8IDYam+undIJONvigAz8KR5GWblsFTEfQs0WODsjbSXWlm+JHEv8Gr6Tfdbg==", + "dev": true, + "dependencies": { + "jsonparse": "^1.3.1", + "minipass": "^3.0.0" + } + }, + "node_modules/minipass-pipeline": { + "version": "1.2.4", + "resolved": "https://registry.npmjs.org/minipass-pipeline/-/minipass-pipeline-1.2.4.tgz", + "integrity": "sha512-xuIq7cIOt09RPRJ19gdi4b+RiNvDFYe5JH+ggNvBqGqpQXcru3PcRmOZuHBKWK1Txf9+cQ+HMVN4d6z46LZP7A==", + "dev": true, + "dependencies": { + "minipass": "^3.0.0" + }, + "engines": { + "node": ">=8" + } + }, + "node_modules/minipass-sized": { + "version": "1.0.3", + "resolved": "https://registry.npmjs.org/minipass-sized/-/minipass-sized-1.0.3.tgz", + "integrity": "sha512-MbkQQ2CTiBMlA2Dm/5cY+9SWFEN8pzzOXi6rlM5Xxq0Yqbda5ZQy9sU75a673FE9ZK0Zsbr6Y5iP6u9nktfg2g==", + "dev": true, + "dependencies": { + "minipass": "^3.0.0" + }, + "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==", + "dev": true, + "dependencies": { + "minipass": "^3.0.0", + "yallist": "^4.0.0" + }, + "engines": { + "node": ">= 8" + } + }, + "node_modules/mkdirp": { + "version": "1.0.4", + "resolved": "https://registry.npmjs.org/mkdirp/-/mkdirp-1.0.4.tgz", + "integrity": "sha512-vVqVZQyf3WLx2Shd0qJ9xuvqgAyKPLAiqITEtqW0oIUjzo3PePDd6fW9iFz30ef7Ysp/oiWqbhszeGWW2T6Gzw==", + "dev": true, + "bin": { + "mkdirp": "bin/cmd.js" + }, + "engines": { + "node": ">=10" + } + }, + "node_modules/mkdirp-infer-owner": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/mkdirp-infer-owner/-/mkdirp-infer-owner-2.0.0.tgz", + "integrity": "sha512-sdqtiFt3lkOaYvTXSRIUjkIdPTcxgv5+fgqYE/5qgwdw12cOrAuzzgzvVExIkH/ul1oeHN3bCLOWSG3XOqbKKw==", + "dev": true, + "dependencies": { + "chownr": "^2.0.0", + "infer-owner": "^1.0.4", + "mkdirp": "^1.0.3" + }, + "engines": { + "node": ">=10" + } + }, + "node_modules/modify-values": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/modify-values/-/modify-values-1.0.1.tgz", + "integrity": "sha512-xV2bxeN6F7oYjZWTe/YPAy6MN2M+sL4u/Rlm2AHCIVGfo2p1yGmBHQ6vHehl4bRTZBdHu3TSkWdYgkwpYzAGSw==", + "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", + "integrity": "sha512-sGkPx+VjMtmA6MX27oA4FBFELFCZZ4S4XqeGOXCv68tT+jb3vk/RyaKWP0PTKyWtmLSM0b+adUTEvbs1PEaH2w==", + "dev": true + }, + "node_modules/multimatch": { + "version": "5.0.0", + "resolved": "https://registry.npmjs.org/multimatch/-/multimatch-5.0.0.tgz", + "integrity": "sha512-ypMKuglUrZUD99Tk2bUQ+xNQj43lPEfAeX2o9cTteAmShXy2VHDJpuwu1o0xqoKCt9jLVAvwyFKdLTPXKAfJyA==", + "dev": true, + "dependencies": { + "@types/minimatch": "^3.0.3", + "array-differ": "^3.0.0", + "array-union": "^2.1.0", + "arrify": "^2.0.1", + "minimatch": "^3.0.4" + }, + "engines": { + "node": ">=10" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" + } + }, + "node_modules/multimatch/node_modules/arrify": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/arrify/-/arrify-2.0.1.tgz", + "integrity": "sha512-3duEwti880xqi4eAMN8AyR4a0ByT90zoYdLlevfrvU43vb0YZwZVfxOgxWrLXXXpyugL0hNZc9G6BiB5B3nUug==", + "dev": true, + "engines": { + "node": ">=8" + } + }, + "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/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/node-addon-api": { + "version": "3.2.1", + "resolved": "https://registry.npmjs.org/node-addon-api/-/node-addon-api-3.2.1.tgz", + "integrity": "sha512-mmcei9JghVNDYydghQmeDX8KoAm0FAiYyIcUt/N4nhyAipB17pllZQDOJD2fotxABnt4Mdz+dKTO7eftLg4d0A==", + "dev": true + }, + "node_modules/node-fetch": { + "version": "2.6.7", + "resolved": "https://registry.npmjs.org/node-fetch/-/node-fetch-2.6.7.tgz", + "integrity": "sha512-ZjMPFEfVx5j+y2yF35Kzx5sF7kDzxuDj6ziH4FFbOp87zKDZNx8yExJIb05OGF4Nlt9IHFIMBkRl41VdvcNdbQ==", + "dev": true, + "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-gyp": { + "version": "9.3.0", + "resolved": "https://registry.npmjs.org/node-gyp/-/node-gyp-9.3.0.tgz", + "integrity": "sha512-A6rJWfXFz7TQNjpldJ915WFb1LnhO4lIve3ANPbWreuEoLoKlFT3sxIepPBkLhM27crW8YmN+pjlgbasH6cH/Q==", + "dev": true, + "dependencies": { + "env-paths": "^2.2.0", + "glob": "^7.1.4", + "graceful-fs": "^4.2.6", + "make-fetch-happen": "^10.0.3", + "nopt": "^6.0.0", + "npmlog": "^6.0.0", + "rimraf": "^3.0.2", + "semver": "^7.3.5", + "tar": "^6.1.2", + "which": "^2.0.2" + }, + "bin": { + "node-gyp": "bin/node-gyp.js" + }, + "engines": { + "node": "^12.22 || ^14.13 || >=16" + } + }, + "node_modules/node-gyp-build": { + "version": "4.5.0", + "resolved": "https://registry.npmjs.org/node-gyp-build/-/node-gyp-build-4.5.0.tgz", + "integrity": "sha512-2iGbaQBV+ITgCz76ZEjmhUKAKVf7xfY1sRl4UiKQspfZMH2h06SyhNsnSVy50cwkFQDGLyif6m/6uFXHkOZ6rg==", + "dev": true, + "bin": { + "node-gyp-build": "bin.js", + "node-gyp-build-optional": "optional.js", + "node-gyp-build-test": "build-test.js" + } + }, + "node_modules/node-gyp/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/node-gyp/node_modules/nopt": { + "version": "6.0.0", + "resolved": "https://registry.npmjs.org/nopt/-/nopt-6.0.0.tgz", + "integrity": "sha512-ZwLpbTgdhuZUnZzjd7nb1ZV+4DoiC6/sfiVKok72ym/4Tlf+DFdlHYmT2JPmcNNWV6Pi3SDf1kT+A4r9RTuT9g==", + "dev": true, + "dependencies": { + "abbrev": "^1.0.0" + }, + "bin": { + "nopt": "bin/nopt.js" + }, + "engines": { + "node": "^12.13.0 || ^14.15.0 || >=16.0.0" + } + }, + "node_modules/nopt": { + "version": "5.0.0", + "resolved": "https://registry.npmjs.org/nopt/-/nopt-5.0.0.tgz", + "integrity": "sha512-Tbj67rffqceeLpcRXrT7vKAN8CwfPeIBgM7E6iBkmKLV7bEMwpGgYLGv0jACUsECaa/vuxP0IjEont6umdMgtQ==", + "dev": true, + "dependencies": { + "abbrev": "1" + }, + "bin": { + "nopt": "bin/nopt.js" + }, + "engines": { + "node": ">=6" + } + }, + "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": ">=10" + } + }, + "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-url": { + "version": "7.2.0", + "resolved": "https://registry.npmjs.org/normalize-url/-/normalize-url-7.2.0.tgz", + "integrity": "sha512-uhXOdZry0L6M2UIo9BTt7FdpBDiAGN/7oItedQwPKh8jh31ZlvC8U9Xl/EJ3aijDHaywXTW3QbZ6LuCocur1YA==", + "dev": true, + "engines": { + "node": ">=12.20" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" + } + }, + "node_modules/npm-bundled": { + "version": "1.1.2", + "resolved": "https://registry.npmjs.org/npm-bundled/-/npm-bundled-1.1.2.tgz", + "integrity": "sha512-x5DHup0SuyQcmL3s7Rx/YQ8sbw/Hzg0rj48eN0dV7hf5cmQq5PXIeioroH3raV1QC1yh3uTYuMThvEQF3iKgGQ==", + "dev": true, + "dependencies": { + "npm-normalize-package-bin": "^1.0.1" + } + }, + "node_modules/npm-check-updates": { + "version": "16.3.11", + "resolved": "https://registry.npmjs.org/npm-check-updates/-/npm-check-updates-16.3.11.tgz", + "integrity": "sha512-MxdqS3kXAJasoEaz5BLqTR1Dak+Dm6PoK2N4KdKcQGUEhdVwt0ggfJ0R0Yym8sWc48CYqEl02HBkUAZFUCufHA==", + "dev": true, + "dependencies": { + "chalk": "^5.0.1", + "cli-table": "^0.3.11", + "commander": "^9.4.1", + "fast-memoize": "^2.5.2", + "find-up": "5.0.0", + "fp-and-or": "^0.1.3", + "get-stdin": "^8.0.0", + "globby": "^11.0.4", + "hosted-git-info": "^5.1.0", + "json-parse-helpfulerror": "^1.0.3", + "jsonlines": "^0.1.1", + "lodash": "^4.17.21", + "minimatch": "^5.1.0", + "p-map": "^4.0.0", + "pacote": "^13.6.2", + "parse-github-url": "^1.0.2", + "progress": "^2.0.3", + "prompts-ncu": "^2.5.1", + "rc-config-loader": "^4.1.0", + "remote-git-tags": "^3.0.0", + "rimraf": "^3.0.2", + "semver": "^7.3.7", + "semver-utils": "^1.1.4", + "source-map-support": "^0.5.21", + "spawn-please": "^1.0.0", + "untildify": "^4.0.0", + "update-notifier": "^6.0.2", + "yaml": "^2.1.1" + }, + "bin": { + "ncu": "build/src/bin/cli.js", + "npm-check-updates": "build/src/bin/cli.js" + }, + "engines": { + "node": ">=14.14" + } + }, + "node_modules/npm-check-updates/node_modules/brace-expansion": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/brace-expansion/-/brace-expansion-2.0.1.tgz", + "integrity": "sha512-XnAIvQ8eM+kC6aULx6wuQiwVsnzsi9d3WxzV3FpWTGA19F621kwdbsAcFKXgKUHZWsy+mY6iL1sHTxWEFCytDA==", + "dev": true, + "dependencies": { + "balanced-match": "^1.0.0" + } + }, + "node_modules/npm-check-updates/node_modules/chalk": { + "version": "5.1.0", + "resolved": "https://registry.npmjs.org/chalk/-/chalk-5.1.0.tgz", + "integrity": "sha512-56zD4khRTBoIyzUYAFgDDaPhUMN/fC/rySe6aZGqbj/VWiU2eI3l6ZLOtYGFZAV5v02mwPjtpzlrOveJiz5eZQ==", + "dev": true, + "engines": { + "node": "^12.17.0 || ^14.13 || >=16.0.0" + }, + "funding": { + "url": "https://github.com/chalk/chalk?sponsor=1" + } + }, + "node_modules/npm-check-updates/node_modules/hosted-git-info": { + "version": "5.1.0", + "resolved": "https://registry.npmjs.org/hosted-git-info/-/hosted-git-info-5.1.0.tgz", + "integrity": "sha512-Ek+QmMEqZF8XrbFdwoDjSbm7rT23pCgEMOJmz6GPk/s4yH//RQfNPArhIxbguNxROq/+5lNBwCDHMhA903Kx1Q==", + "dev": true, + "dependencies": { + "lru-cache": "^7.5.1" + }, + "engines": { + "node": "^12.13.0 || ^14.15.0 || >=16.0.0" + } + }, + "node_modules/npm-check-updates/node_modules/minimatch": { + "version": "5.1.0", + "resolved": "https://registry.npmjs.org/minimatch/-/minimatch-5.1.0.tgz", + "integrity": "sha512-9TPBGGak4nHfGZsPBohm9AWg6NoT7QTCehS3BIJABslyZbzxfV78QM2Y6+i741OPZIafFAaiiEMh5OyIrJPgtg==", + "dev": true, + "dependencies": { + "brace-expansion": "^2.0.1" + }, + "engines": { + "node": ">=10" + } + }, + "node_modules/npm-check-updates/node_modules/yaml": { + "version": "2.1.3", + "resolved": "https://registry.npmjs.org/yaml/-/yaml-2.1.3.tgz", + "integrity": "sha512-AacA8nRULjKMX2DvWvOAdBZMOfQlypSFkjcOcu9FalllIDJ1kvlREzcdIZmidQUqqeMv7jorHjq2HlLv/+c2lg==", + "dev": true, + "engines": { + "node": ">= 14" + } + }, + "node_modules/npm-install-checks": { + "version": "5.0.0", + "resolved": "https://registry.npmjs.org/npm-install-checks/-/npm-install-checks-5.0.0.tgz", + "integrity": "sha512-65lUsMI8ztHCxFz5ckCEC44DRvEGdZX5usQFriauxHEwt7upv1FKaQEmAtU0YnOAdwuNWCmk64xYiQABNrEyLA==", + "dev": true, + "dependencies": { + "semver": "^7.1.1" + }, + "engines": { + "node": "^12.13.0 || ^14.15.0 || >=16.0.0" + } + }, + "node_modules/npm-normalize-package-bin": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/npm-normalize-package-bin/-/npm-normalize-package-bin-1.0.1.tgz", + "integrity": "sha512-EPfafl6JL5/rU+ot6P3gRSCpPDW5VmIzX959Ob1+ySFUuuYHWHekXpwdUZcKP5C+DS4GEtdJluwBjnsNDl+fSA==", + "dev": true + }, + "node_modules/npm-package-arg": { + "version": "8.1.1", + "resolved": "https://registry.npmjs.org/npm-package-arg/-/npm-package-arg-8.1.1.tgz", + "integrity": "sha512-CsP95FhWQDwNqiYS+Q0mZ7FAEDytDZAkNxQqea6IaAFJTAY9Lhhqyl0irU/6PMc7BGfUmnsbHcqxJD7XuVM/rg==", + "dev": true, + "dependencies": { + "hosted-git-info": "^3.0.6", + "semver": "^7.0.0", + "validate-npm-package-name": "^3.0.0" + }, + "engines": { + "node": ">=10" + } + }, + "node_modules/npm-package-arg/node_modules/builtins": { + "version": "1.0.3", + "resolved": "https://registry.npmjs.org/builtins/-/builtins-1.0.3.tgz", + "integrity": "sha512-uYBjakWipfaO/bXI7E8rq6kpwHRZK5cNYrUv2OzZSI/FvmdMyXJ2tG9dKcjEC5YHmHpUAwsargWIZNWdxb/bnQ==", + "dev": true + }, + "node_modules/npm-package-arg/node_modules/hosted-git-info": { + "version": "3.0.8", + "resolved": "https://registry.npmjs.org/hosted-git-info/-/hosted-git-info-3.0.8.tgz", + "integrity": "sha512-aXpmwoOhRBrw6X3j0h5RloK4x1OzsxMPyxqIHyNfSe2pypkVTZFpEiRoSipPEPlMrh0HW/XsjkJ5WgnCirpNUw==", + "dev": true, + "dependencies": { + "lru-cache": "^6.0.0" + }, + "engines": { + "node": ">=10" + } + }, + "node_modules/npm-package-arg/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/npm-package-arg/node_modules/validate-npm-package-name": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/validate-npm-package-name/-/validate-npm-package-name-3.0.0.tgz", + "integrity": "sha512-M6w37eVCMMouJ9V/sdPGnC5H4uDr73/+xdq0FBLO3TFFX1+7wiUY6Es328NN+y43tmY+doUdN9g9J21vqB7iLw==", + "dev": true, + "dependencies": { + "builtins": "^1.0.3" + } + }, + "node_modules/npm-packlist": { + "version": "5.1.3", + "resolved": "https://registry.npmjs.org/npm-packlist/-/npm-packlist-5.1.3.tgz", + "integrity": "sha512-263/0NGrn32YFYi4J533qzrQ/krmmrWwhKkzwTuM4f/07ug51odoaNjUexxO4vxlzURHcmYMH1QjvHjsNDKLVg==", + "dev": true, + "dependencies": { + "glob": "^8.0.1", + "ignore-walk": "^5.0.1", + "npm-bundled": "^2.0.0", + "npm-normalize-package-bin": "^2.0.0" + }, + "bin": { + "npm-packlist": "bin/index.js" + }, + "engines": { + "node": "^12.13.0 || ^14.15.0 || >=16.0.0" + } + }, + "node_modules/npm-packlist/node_modules/npm-bundled": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/npm-bundled/-/npm-bundled-2.0.1.tgz", + "integrity": "sha512-gZLxXdjEzE/+mOstGDqR6b0EkhJ+kM6fxM6vUuckuctuVPh80Q6pw/rSZj9s4Gex9GxWtIicO1pc8DB9KZWudw==", + "dev": true, + "dependencies": { + "npm-normalize-package-bin": "^2.0.0" + }, + "engines": { + "node": "^12.13.0 || ^14.15.0 || >=16.0.0" + } + }, + "node_modules/npm-packlist/node_modules/npm-normalize-package-bin": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/npm-normalize-package-bin/-/npm-normalize-package-bin-2.0.0.tgz", + "integrity": "sha512-awzfKUO7v0FscrSpRoogyNm0sajikhBWpU0QMrW09AMi9n1PoKU6WaIqUzuJSQnpciZZmJ/jMZ2Egfmb/9LiWQ==", + "dev": true, + "engines": { + "node": "^12.13.0 || ^14.15.0 || >=16.0.0" + } + }, + "node_modules/npm-pick-manifest": { + "version": "7.0.2", + "resolved": "https://registry.npmjs.org/npm-pick-manifest/-/npm-pick-manifest-7.0.2.tgz", + "integrity": "sha512-gk37SyRmlIjvTfcYl6RzDbSmS9Y4TOBXfsPnoYqTHARNgWbyDiCSMLUpmALDj4jjcTZpURiEfsSHJj9k7EV4Rw==", + "dev": true, + "dependencies": { + "npm-install-checks": "^5.0.0", + "npm-normalize-package-bin": "^2.0.0", + "npm-package-arg": "^9.0.0", + "semver": "^7.3.5" + }, + "engines": { + "node": "^12.13.0 || ^14.15.0 || >=16.0.0" + } + }, + "node_modules/npm-pick-manifest/node_modules/hosted-git-info": { + "version": "5.1.0", + "resolved": "https://registry.npmjs.org/hosted-git-info/-/hosted-git-info-5.1.0.tgz", + "integrity": "sha512-Ek+QmMEqZF8XrbFdwoDjSbm7rT23pCgEMOJmz6GPk/s4yH//RQfNPArhIxbguNxROq/+5lNBwCDHMhA903Kx1Q==", + "dev": true, + "dependencies": { + "lru-cache": "^7.5.1" + }, + "engines": { + "node": "^12.13.0 || ^14.15.0 || >=16.0.0" + } + }, + "node_modules/npm-pick-manifest/node_modules/npm-normalize-package-bin": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/npm-normalize-package-bin/-/npm-normalize-package-bin-2.0.0.tgz", + "integrity": "sha512-awzfKUO7v0FscrSpRoogyNm0sajikhBWpU0QMrW09AMi9n1PoKU6WaIqUzuJSQnpciZZmJ/jMZ2Egfmb/9LiWQ==", + "dev": true, + "engines": { + "node": "^12.13.0 || ^14.15.0 || >=16.0.0" + } + }, + "node_modules/npm-pick-manifest/node_modules/npm-package-arg": { + "version": "9.1.2", + "resolved": "https://registry.npmjs.org/npm-package-arg/-/npm-package-arg-9.1.2.tgz", + "integrity": "sha512-pzd9rLEx4TfNJkovvlBSLGhq31gGu2QDexFPWT19yCDh0JgnRhlBLNo5759N0AJmBk+kQ9Y/hXoLnlgFD+ukmg==", + "dev": true, + "dependencies": { + "hosted-git-info": "^5.0.0", + "proc-log": "^2.0.1", + "semver": "^7.3.5", + "validate-npm-package-name": "^4.0.0" + }, + "engines": { + "node": "^12.13.0 || ^14.15.0 || >=16.0.0" + } + }, + "node_modules/npm-registry-fetch": { + "version": "13.3.1", + "resolved": "https://registry.npmjs.org/npm-registry-fetch/-/npm-registry-fetch-13.3.1.tgz", + "integrity": "sha512-eukJPi++DKRTjSBRcDZSDDsGqRK3ehbxfFUcgaRd0Yp6kRwOwh2WVn0r+8rMB4nnuzvAk6rQVzl6K5CkYOmnvw==", + "dev": true, + "dependencies": { + "make-fetch-happen": "^10.0.6", + "minipass": "^3.1.6", + "minipass-fetch": "^2.0.3", + "minipass-json-stream": "^1.0.1", + "minizlib": "^2.1.2", + "npm-package-arg": "^9.0.1", + "proc-log": "^2.0.0" + }, + "engines": { + "node": "^12.13.0 || ^14.15.0 || >=16.0.0" + } + }, + "node_modules/npm-registry-fetch/node_modules/hosted-git-info": { + "version": "5.1.0", + "resolved": "https://registry.npmjs.org/hosted-git-info/-/hosted-git-info-5.1.0.tgz", + "integrity": "sha512-Ek+QmMEqZF8XrbFdwoDjSbm7rT23pCgEMOJmz6GPk/s4yH//RQfNPArhIxbguNxROq/+5lNBwCDHMhA903Kx1Q==", + "dev": true, + "dependencies": { + "lru-cache": "^7.5.1" + }, + "engines": { + "node": "^12.13.0 || ^14.15.0 || >=16.0.0" + } + }, + "node_modules/npm-registry-fetch/node_modules/npm-package-arg": { + "version": "9.1.2", + "resolved": "https://registry.npmjs.org/npm-package-arg/-/npm-package-arg-9.1.2.tgz", + "integrity": "sha512-pzd9rLEx4TfNJkovvlBSLGhq31gGu2QDexFPWT19yCDh0JgnRhlBLNo5759N0AJmBk+kQ9Y/hXoLnlgFD+ukmg==", + "dev": true, + "dependencies": { + "hosted-git-info": "^5.0.0", + "proc-log": "^2.0.1", + "semver": "^7.3.5", + "validate-npm-package-name": "^4.0.0" + }, + "engines": { + "node": "^12.13.0 || ^14.15.0 || >=16.0.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/npmlog": { + "version": "6.0.2", + "resolved": "https://registry.npmjs.org/npmlog/-/npmlog-6.0.2.tgz", + "integrity": "sha512-/vBvz5Jfr9dT/aFWd0FIRf+T/Q2WBsLENygUaFUqstqsycmZAP/t5BvFJTK0viFmSUxiUKTUplWy5vt+rvKIxg==", + "dev": true, + "dependencies": { + "are-we-there-yet": "^3.0.0", + "console-control-strings": "^1.1.0", + "gauge": "^4.0.3", + "set-blocking": "^2.0.0" + }, + "engines": { + "node": "^12.13.0 || ^14.15.0 || >=16.0.0" + } + }, + "node_modules/nx": { + "version": "14.8.4", + "resolved": "https://registry.npmjs.org/nx/-/nx-14.8.4.tgz", + "integrity": "sha512-J7QlmG6rsdR+1Ry0pohPZXHpPN1lzE70lvuCXveyU61VX8HsrbZBzgLif07BUT8lHbs7ORaOJSZd4BCqZBJSSw==", + "dev": true, + "hasInstallScript": true, + "dependencies": { + "@nrwl/cli": "14.8.4", + "@nrwl/tao": "14.8.4", + "@parcel/watcher": "2.0.4", + "@yarnpkg/lockfile": "^1.1.0", + "@yarnpkg/parsers": "^3.0.0-rc.18", + "@zkochan/js-yaml": "0.0.6", + "axios": "^1.0.0", + "chalk": "4.1.0", + "chokidar": "^3.5.1", + "cli-cursor": "3.1.0", + "cli-spinners": "2.6.1", + "cliui": "^7.0.2", + "dotenv": "~10.0.0", + "enquirer": "~2.3.6", + "fast-glob": "3.2.7", + "figures": "3.2.0", + "flat": "^5.0.2", + "fs-extra": "^10.1.0", + "glob": "7.1.4", + "ignore": "^5.0.4", + "js-yaml": "4.1.0", + "jsonc-parser": "3.2.0", + "minimatch": "3.0.5", + "npm-run-path": "^4.0.1", + "open": "^8.4.0", + "semver": "7.3.4", + "string-width": "^4.2.3", + "strong-log-transformer": "^2.1.0", + "tar-stream": "~2.2.0", + "tmp": "~0.2.1", + "tsconfig-paths": "^3.9.0", + "tslib": "^2.3.0", + "v8-compile-cache": "2.3.0", + "yargs": "^17.4.0", + "yargs-parser": "21.0.1" + }, + "bin": { + "nx": "bin/nx.js" + }, + "peerDependencies": { + "@swc-node/register": "^1.4.2", + "@swc/core": "^1.2.173" + }, + "peerDependenciesMeta": { + "@swc-node/register": { + "optional": true + }, + "@swc/core": { + "optional": true + } + } + }, + "node_modules/nx/node_modules/axios": { + "version": "1.1.2", + "resolved": "https://registry.npmjs.org/axios/-/axios-1.1.2.tgz", + "integrity": "sha512-bznQyETwElsXl2RK7HLLwb5GPpOLlycxHCtrpDR/4RqqBzjARaOTo3jz4IgtntWUYee7Ne4S8UHd92VCuzPaWA==", + "dev": true, + "dependencies": { + "follow-redirects": "^1.15.0", + "form-data": "^4.0.0", + "proxy-from-env": "^1.1.0" + } + }, + "node_modules/nx/node_modules/chalk": { + "version": "4.1.0", + "resolved": "https://registry.npmjs.org/chalk/-/chalk-4.1.0.tgz", + "integrity": "sha512-qwx12AxXe2Q5xQ43Ac//I6v5aXTipYrSESdOgzrN+9XjgEpyjpKuvSGaN4qE93f7TQTlerQQ8S+EQ0EyDoVL1A==", + "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/nx/node_modules/fast-glob": { + "version": "3.2.7", + "resolved": "https://registry.npmjs.org/fast-glob/-/fast-glob-3.2.7.tgz", + "integrity": "sha512-rYGMRwip6lUMvYD3BTScMwT1HtAs2d71SMv66Vrxs0IekGZEjhM0pcMfjQPnknBt2zeCwQMEupiN02ZP4DiT1Q==", + "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" + } + }, + "node_modules/nx/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/nx/node_modules/glob": { + "version": "7.1.4", + "resolved": "https://registry.npmjs.org/glob/-/glob-7.1.4.tgz", + "integrity": "sha512-hkLPepehmnKk41pUGm3sYxoFs/umurYfYJCerbXEyFIWcAzvpipAgVkBqqT9RBKMGjnq6kMuyYwha6csxbiM1A==", + "dev": true, + "dependencies": { + "fs.realpath": "^1.0.0", + "inflight": "^1.0.4", + "inherits": "2", + "minimatch": "^3.0.4", + "once": "^1.3.0", + "path-is-absolute": "^1.0.0" + }, + "engines": { + "node": "*" + } + }, + "node_modules/nx/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/nx/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/nx/node_modules/minimatch": { + "version": "3.0.5", + "resolved": "https://registry.npmjs.org/minimatch/-/minimatch-3.0.5.tgz", + "integrity": "sha512-tUpxzX0VAzJHjLu0xUfFv1gwVp9ba3IOuRAVH2EGuRW8a5emA2FlACLqiT/lDVtS1W+TGNwqz3sWaNyLgDJWuw==", + "dev": true, + "dependencies": { + "brace-expansion": "^1.1.7" + }, + "engines": { + "node": "*" + } + }, + "node_modules/nx/node_modules/semver": { + "version": "7.3.4", + "resolved": "https://registry.npmjs.org/semver/-/semver-7.3.4.tgz", + "integrity": "sha512-tCfb2WLjqFAtXn4KEdxIhalnRtoKFN7nAwj0B3ZXCbQloV2tq5eDbcTmT68JJD3nRJq24/XgxtQKFIpQdtvmVw==", + "dev": true, + "dependencies": { + "lru-cache": "^6.0.0" + }, + "bin": { + "semver": "bin/semver.js" + }, + "engines": { + "node": ">=10" + } + }, + "node_modules/nx/node_modules/tmp": { + "version": "0.2.1", + "resolved": "https://registry.npmjs.org/tmp/-/tmp-0.2.1.tgz", + "integrity": "sha512-76SUhtfqR2Ijn+xllcI5P1oyannHNHByD80W1q447gU3mp9G9PSpGdWmjUOHRDPiHYacIk66W7ubDTuPF3BEtQ==", + "dev": true, + "dependencies": { + "rimraf": "^3.0.0" + }, + "engines": { + "node": ">=8.17.0" + } + }, + "node_modules/nx/node_modules/yargs": { + "version": "17.6.0", + "resolved": "https://registry.npmjs.org/yargs/-/yargs-17.6.0.tgz", + "integrity": "sha512-8H/wTDqlSwoSnScvV2N/JHfLWOKuh5MVla9hqLjK3nsfyy6Y4kDSYSvkU5YCUEPOSnRXfIyx3Sq+B/IWudTo4g==", + "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.0.0" + }, + "engines": { + "node": ">=12" + } + }, + "node_modules/nx/node_modules/yargs-parser": { + "version": "21.0.1", + "resolved": "https://registry.npmjs.org/yargs-parser/-/yargs-parser-21.0.1.tgz", + "integrity": "sha512-9BK1jFpLzJROCI5TzwZL/TU4gqjK5xiHV/RfWLOahrjAko/e4DJkRDZQXfvqAsiZzzYhgAzbgz6lg48jcm4GLg==", + "dev": true, + "engines": { + "node": ">=12" + } + }, + "node_modules/nx/node_modules/yargs/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/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/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/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-cancelable": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/p-cancelable/-/p-cancelable-3.0.0.tgz", + "integrity": "sha512-mlVgR3PGuzlo0MmTdk4cXqXWlwQDLnONTAg6sm62XkMJEiRxN3GL3SffkYvqwonbkJBcrI7Uvv5Zh9yjvn2iUw==", + "dev": true, + "engines": { + "node": ">=12.20" + } + }, + "node_modules/p-finally": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/p-finally/-/p-finally-1.0.0.tgz", + "integrity": "sha512-LICb2p9CB7FS+0eR1oqWnHhp0FljGLZCWBE9aix0Uye9W8LTQPwMTYVGWQWIw9RdQiDg4+epXQODwIYJtSJaow==", + "dev": true, + "engines": { + "node": ">=4" + } + }, + "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-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-map": { + "version": "4.0.0", + "resolved": "https://registry.npmjs.org/p-map/-/p-map-4.0.0.tgz", + "integrity": "sha512-/bjOqmgETBYB5BoEeGVea8dmvHb2m9GLy1E9W43yeyfP6QQCZGFNa+XRceJEuDB6zqr+gKpIAmlLebMpykw/MQ==", + "dev": true, + "dependencies": { + "aggregate-error": "^3.0.0" + }, + "engines": { + "node": ">=10" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" + } + }, + "node_modules/p-map-series": { + "version": "2.1.0", + "resolved": "https://registry.npmjs.org/p-map-series/-/p-map-series-2.1.0.tgz", + "integrity": "sha512-RpYIIK1zXSNEOdwxcfe7FdvGcs7+y5n8rifMhMNWvaxRNMPINJHF5GDeuVxWqnfrcHPSCnp7Oo5yNXHId9Av2Q==", + "dev": true, + "engines": { + "node": ">=8" + } + }, + "node_modules/p-pipe": { + "version": "3.1.0", + "resolved": "https://registry.npmjs.org/p-pipe/-/p-pipe-3.1.0.tgz", + "integrity": "sha512-08pj8ATpzMR0Y80x50yJHn37NF6vjrqHutASaX5LiH5npS9XPvrUmscd9MF5R4fuYRHOxQR1FfMIlF7AzwoPqw==", + "dev": true, + "engines": { + "node": ">=8" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" + } + }, + "node_modules/p-queue": { + "version": "6.6.2", + "resolved": "https://registry.npmjs.org/p-queue/-/p-queue-6.6.2.tgz", + "integrity": "sha512-RwFpb72c/BhQLEXIZ5K2e+AhgNVmIejGlTgiB9MzZ0e93GRvqZ7uSi0dvRF7/XIXDeNkra2fNHBxTyPDGySpjQ==", + "dev": true, + "dependencies": { + "eventemitter3": "^4.0.4", + "p-timeout": "^3.2.0" + }, + "engines": { + "node": ">=8" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" + } + }, + "node_modules/p-reduce": { + "version": "2.1.0", + "resolved": "https://registry.npmjs.org/p-reduce/-/p-reduce-2.1.0.tgz", + "integrity": "sha512-2USApvnsutq8uoxZBGbbWM0JIYLiEMJ9RlaN7fAzVNb9OZN0SHjjTTfIcb667XynS5Y1VhwDJVDa72TnPzAYWw==", + "dev": true, + "engines": { + "node": ">=8" + } + }, + "node_modules/p-timeout": { + "version": "3.2.0", + "resolved": "https://registry.npmjs.org/p-timeout/-/p-timeout-3.2.0.tgz", + "integrity": "sha512-rhIwUycgwwKcP9yTOOFK/AKsAopjjCakVqLHePO3CC6Mir1Z99xT+R63jZxAT5lFZLa2inS5h+ZS2GvR99/FBg==", + "dev": true, + "dependencies": { + "p-finally": "^1.0.0" + }, + "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/p-waterfall": { + "version": "2.1.1", + "resolved": "https://registry.npmjs.org/p-waterfall/-/p-waterfall-2.1.1.tgz", + "integrity": "sha512-RRTnDb2TBG/epPRI2yYXsimO0v3BXC8Yd3ogr1545IaqKK17VGhbWVeGGN+XfCm/08OK8635nH31c8bATkHuSw==", + "dev": true, + "dependencies": { + "p-reduce": "^2.0.0" + }, + "engines": { + "node": ">=8" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" + } + }, + "node_modules/package-json": { + "version": "8.1.0", + "resolved": "https://registry.npmjs.org/package-json/-/package-json-8.1.0.tgz", + "integrity": "sha512-hySwcV8RAWeAfPsXb9/HGSPn8lwDnv6fabH+obUZKX169QknRkRhPxd1yMubpKDskLFATkl3jHpNtVtDPFA0Wg==", + "dev": true, + "dependencies": { + "got": "^12.1.0", + "registry-auth-token": "^5.0.1", + "registry-url": "^6.0.0", + "semver": "^7.3.7" + }, + "engines": { + "node": ">=14.16" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" + } + }, + "node_modules/pacote": { + "version": "13.6.2", + "resolved": "https://registry.npmjs.org/pacote/-/pacote-13.6.2.tgz", + "integrity": "sha512-Gu8fU3GsvOPkak2CkbojR7vjs3k3P9cA6uazKTHdsdV0gpCEQq2opelnEv30KRQWgVzP5Vd/5umjcedma3MKtg==", + "dev": true, + "dependencies": { + "@npmcli/git": "^3.0.0", + "@npmcli/installed-package-contents": "^1.0.7", + "@npmcli/promise-spawn": "^3.0.0", + "@npmcli/run-script": "^4.1.0", + "cacache": "^16.0.0", + "chownr": "^2.0.0", + "fs-minipass": "^2.1.0", + "infer-owner": "^1.0.4", + "minipass": "^3.1.6", + "mkdirp": "^1.0.4", + "npm-package-arg": "^9.0.0", + "npm-packlist": "^5.1.0", + "npm-pick-manifest": "^7.0.0", + "npm-registry-fetch": "^13.0.1", + "proc-log": "^2.0.0", + "promise-retry": "^2.0.1", + "read-package-json": "^5.0.0", + "read-package-json-fast": "^2.0.3", + "rimraf": "^3.0.2", + "ssri": "^9.0.0", + "tar": "^6.1.11" + }, + "bin": { + "pacote": "lib/bin.js" + }, + "engines": { + "node": "^12.13.0 || ^14.15.0 || >=16.0.0" + } + }, + "node_modules/pacote/node_modules/hosted-git-info": { + "version": "5.1.0", + "resolved": "https://registry.npmjs.org/hosted-git-info/-/hosted-git-info-5.1.0.tgz", + "integrity": "sha512-Ek+QmMEqZF8XrbFdwoDjSbm7rT23pCgEMOJmz6GPk/s4yH//RQfNPArhIxbguNxROq/+5lNBwCDHMhA903Kx1Q==", + "dev": true, + "dependencies": { + "lru-cache": "^7.5.1" + }, + "engines": { + "node": "^12.13.0 || ^14.15.0 || >=16.0.0" + } + }, + "node_modules/pacote/node_modules/npm-package-arg": { + "version": "9.1.2", + "resolved": "https://registry.npmjs.org/npm-package-arg/-/npm-package-arg-9.1.2.tgz", + "integrity": "sha512-pzd9rLEx4TfNJkovvlBSLGhq31gGu2QDexFPWT19yCDh0JgnRhlBLNo5759N0AJmBk+kQ9Y/hXoLnlgFD+ukmg==", + "dev": true, + "dependencies": { + "hosted-git-info": "^5.0.0", + "proc-log": "^2.0.1", + "semver": "^7.3.5", + "validate-npm-package-name": "^4.0.0" + }, + "engines": { + "node": "^12.13.0 || ^14.15.0 || >=16.0.0" + } + }, + "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-conflict-json": { + "version": "2.0.2", + "resolved": "https://registry.npmjs.org/parse-conflict-json/-/parse-conflict-json-2.0.2.tgz", + "integrity": "sha512-jDbRGb00TAPFsKWCpZZOT93SxVP9nONOSgES3AevqRq/CHvavEBvKAjxX9p5Y5F0RZLxH9Ufd9+RwtCsa+lFDA==", + "dev": true, + "dependencies": { + "json-parse-even-better-errors": "^2.3.1", + "just-diff": "^5.0.1", + "just-diff-apply": "^5.2.0" + }, + "engines": { + "node": "^12.13.0 || ^14.15.0 || >=16.0.0" + } + }, + "node_modules/parse-github-url": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/parse-github-url/-/parse-github-url-1.0.2.tgz", + "integrity": "sha512-kgBf6avCbO3Cn6+RnzRGLkUsv4ZVqv/VfAYkRsyBcgkshNvVBkRn1FEZcW0Jb+npXQWm2vHPnnOqFteZxRRGNw==", + "dev": true, + "bin": { + "parse-github-url": "cli.js" + }, + "engines": { + "node": ">=0.10.0" + } + }, + "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/parse-path": { + "version": "7.0.0", + "resolved": "https://registry.npmjs.org/parse-path/-/parse-path-7.0.0.tgz", + "integrity": "sha512-Euf9GG8WT9CdqwuWJGdf3RkUcTBArppHABkO7Lm8IzRQp0e2r/kkFnmhu4TSK30Wcu5rVAZLmfPKSBBi9tWFog==", + "dev": true, + "dependencies": { + "protocols": "^2.0.0" + } + }, + "node_modules/parse-url": { + "version": "8.1.0", + "resolved": "https://registry.npmjs.org/parse-url/-/parse-url-8.1.0.tgz", + "integrity": "sha512-xDvOoLU5XRrcOZvnI6b8zA6n9O9ejNk/GExuz1yBuWUGn9KA97GI6HTs6u02wKara1CeVmZhH+0TZFdWScR89w==", + "dev": true, + "dependencies": { + "parse-path": "^7.0.0" + } + }, + "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-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/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": "5.0.0", + "resolved": "https://registry.npmjs.org/pify/-/pify-5.0.0.tgz", + "integrity": "sha512-eW/gHNMlxdSP6dmG6uJip6FXN0EQBwm2clYYd8Wul42Cwu/DK8HEftzsapcNdYe2MfLiIwZqsDk2RDEsTE79hA==", + "dev": true, + "engines": { + "node": ">=10" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" + } + }, + "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/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/prettier": { + "version": "2.7.1", + "resolved": "https://registry.npmjs.org/prettier/-/prettier-2.7.1.tgz", + "integrity": "sha512-ujppO+MkdPqoVINuDFDRLClm7D78qbDt0/NR+wp5FqEZOoTNAjPHWj17QRhu7geIHJfcNhRk1XVQmF8Bp3ye+g==", + "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/proc-log": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/proc-log/-/proc-log-2.0.1.tgz", + "integrity": "sha512-Kcmo2FhfDTXdcbfDH76N7uBYHINxc/8GW7UAVuVP9I+Va3uHSerrnKV6dLooga/gh7GlgzuCCr/eoldnL1muGw==", + "dev": true, + "engines": { + "node": "^12.13.0 || ^14.15.0 || >=16.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/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/promise-all-reject-late": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/promise-all-reject-late/-/promise-all-reject-late-1.0.1.tgz", + "integrity": "sha512-vuf0Lf0lOxyQREH7GDIOUMLS7kz+gs8i6B+Yi8dC68a2sychGrHTJYghMBD6k7eUcH0H5P73EckCA48xijWqXw==", + "dev": true, + "funding": { + "url": "https://github.com/sponsors/isaacs" + } + }, + "node_modules/promise-call-limit": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/promise-call-limit/-/promise-call-limit-1.0.1.tgz", + "integrity": "sha512-3+hgaa19jzCGLuSCbieeRsu5C2joKfYn8pY6JAuXFRVfF4IO+L7UPpFWNTeWT9pM7uhskvbPPd/oEOktCn317Q==", + "dev": true, + "funding": { + "url": "https://github.com/sponsors/isaacs" + } + }, + "node_modules/promise-inflight": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/promise-inflight/-/promise-inflight-1.0.1.tgz", + "integrity": "sha512-6zWPyEOFaQBJYcGMHBKTKJ3u6TBsnMFOIZSa6ce1e/ZrrsOlnHRHbabMjLiBYKp+n44X9eUI6VUPaukCXHuG4g==", + "dev": true + }, + "node_modules/promise-retry": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/promise-retry/-/promise-retry-2.0.1.tgz", + "integrity": "sha512-y+WKFlBR8BGXnsNlIHFGPZmyDf3DFMoLhaflAnyZgV6rG6xu+JwesTo2Q9R6XwYmtmwAFCkAk3e35jEdoeh/3g==", + "dev": true, + "dependencies": { + "err-code": "^2.0.2", + "retry": "^0.12.0" + }, + "engines": { + "node": ">=10" + } + }, + "node_modules/prompts-ncu": { + "version": "2.5.1", + "resolved": "https://registry.npmjs.org/prompts-ncu/-/prompts-ncu-2.5.1.tgz", + "integrity": "sha512-Hdd7GgV7b76Yh9FP9HL1D9xqtJCJdVPpiM2vDtuoc8W1KfweJe15gutFYmxkq83ViFaagFM8K0UcPCQ/tZq8bA==", + "dev": true, + "dependencies": { + "kleur": "^4.0.1", + "sisteransi": "^1.0.5" + }, + "engines": { + "node": ">= 6" + } + }, + "node_modules/promzard": { + "version": "0.3.0", + "resolved": "https://registry.npmjs.org/promzard/-/promzard-0.3.0.tgz", + "integrity": "sha512-JZeYqd7UAcHCwI+sTOeUDYkvEU+1bQ7iE0UT1MgB/tERkAPkesW46MrpIySzODi+owTjZtiF8Ay5j9m60KmMBw==", + "dev": true, + "dependencies": { + "read": "1" + } + }, + "node_modules/proto-list": { + "version": "1.2.4", + "resolved": "https://registry.npmjs.org/proto-list/-/proto-list-1.2.4.tgz", + "integrity": "sha512-vtK/94akxsTMhe0/cbfpR+syPuszcuwhqVjJq26CuNDgFGj682oRBXOP5MJpv2r7JtE8MsiepGIqvvOTBwn2vA==", + "dev": true + }, + "node_modules/protocols": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/protocols/-/protocols-2.0.1.tgz", + "integrity": "sha512-/XJ368cyBJ7fzLMwLKv1e4vLxOju2MNAIokcr7meSaNcVbWz/CPcW22cP04mwxOErdA5mwjA8Q6w/cdAQxVn7Q==", + "dev": true + }, + "node_modules/proxy-from-env": { + "version": "1.1.0", + "resolved": "https://registry.npmjs.org/proxy-from-env/-/proxy-from-env-1.1.0.tgz", + "integrity": "sha512-D+zkORCbA9f1tdWRK0RaCR3GPv50cMxcrz4X8k5LTSUD1Dkw47mKJEZQNunItRTkWwgtaUSo1RVFRIG9ZXiFYg==", + "dev": true + }, + "node_modules/punycode": { + "version": "2.1.1", + "resolved": "https://registry.npmjs.org/punycode/-/punycode-2.1.1.tgz", + "integrity": "sha512-XRsRjdf+j5ml+y/6GKHPZbrF/8p2Yga0JPtdqTIY2Xe5ohJPD9saDJJLPvp9+NSBprVvevdXZybnj2cv8OEd0A==", + "dev": true, + "engines": { + "node": ">=6" + } + }, + "node_modules/pupa": { + "version": "3.1.0", + "resolved": "https://registry.npmjs.org/pupa/-/pupa-3.1.0.tgz", + "integrity": "sha512-FLpr4flz5xZTSJxSeaheeMKN/EDzMdK7b8PTOC6a5PYFKTucWbdqjgqaEyH0shFiSJrVB1+Qqi4Tk19ccU6Aug==", + "dev": true, + "dependencies": { + "escape-goat": "^4.0.0" + }, + "engines": { + "node": ">=12.20" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" + } + }, + "node_modules/q": { + "version": "1.5.1", + "resolved": "https://registry.npmjs.org/q/-/q-1.5.1.tgz", + "integrity": "sha512-kV/CThkXo6xyFEZUugw/+pIOywXcDbFYgSct5cT3gqlbkBE1SJdwy6UQoZvodiWF/ckQLZyDE/Bu1M6gVu5lVw==", + "dev": true, + "engines": { + "node": ">=0.6.0", + "teleport": ">=0.2.0" + } + }, + "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/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/rc": { + "version": "1.2.8", + "resolved": "https://registry.npmjs.org/rc/-/rc-1.2.8.tgz", + "integrity": "sha512-y3bGgqKj3QBdxLbLkomlohkvsA8gdAiUQlSBJnBhfn+BPxg4bc62d8TcBW15wavDfgexCgccckhcZvywyQYPOw==", + "dev": true, + "dependencies": { + "deep-extend": "^0.6.0", + "ini": "~1.3.0", + "minimist": "^1.2.0", + "strip-json-comments": "~2.0.1" + }, + "bin": { + "rc": "cli.js" + } + }, + "node_modules/rc-config-loader": { + "version": "4.1.0", + "resolved": "https://registry.npmjs.org/rc-config-loader/-/rc-config-loader-4.1.0.tgz", + "integrity": "sha512-aW+kX4qy0CiM9L4fG4Us3oEOpIrOrXzWykAn+xldD07Y9PXWjTH744oHbv0Kc9ZwWaylw3jMjxaf14RgStrNrA==", + "dev": true, + "dependencies": { + "debug": "^4.1.1", + "js-yaml": "^4.0.0", + "json5": "^2.1.2", + "require-from-string": "^2.0.2" + } + }, + "node_modules/rc/node_modules/strip-json-comments": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/strip-json-comments/-/strip-json-comments-2.0.1.tgz", + "integrity": "sha512-4gB8na07fecVVkOI6Rs4e7T6NOTki5EmL7TUduTs6bu3EdnSycntVJ4re8kgZA+wx9IueI2Y11bfbgwtzuE0KQ==", + "dev": true, + "engines": { + "node": ">=0.10.0" + } + }, + "node_modules/read": { + "version": "1.0.7", + "resolved": "https://registry.npmjs.org/read/-/read-1.0.7.tgz", + "integrity": "sha512-rSOKNYUmaxy0om1BNjMN4ezNT6VKK+2xF4GBhc81mkH7L60i6dp8qPYrkndNLT3QPphoII3maL9PVC9XmhHwVQ==", + "dev": true, + "dependencies": { + "mute-stream": "~0.0.4" + }, + "engines": { + "node": ">=0.8" + } + }, + "node_modules/read-cmd-shim": { + "version": "3.0.1", + "resolved": "https://registry.npmjs.org/read-cmd-shim/-/read-cmd-shim-3.0.1.tgz", + "integrity": "sha512-kEmDUoYf/CDy8yZbLTmhB1X9kkjf9Q80PCNsDMb7ufrGd6zZSQA1+UyjrO+pZm5K/S4OXCWJeiIt1JA8kAsa6g==", + "dev": true, + "engines": { + "node": "^12.13.0 || ^14.15.0 || >=16.0.0" + } + }, + "node_modules/read-package-json": { + "version": "5.0.2", + "resolved": "https://registry.npmjs.org/read-package-json/-/read-package-json-5.0.2.tgz", + "integrity": "sha512-BSzugrt4kQ/Z0krro8zhTwV1Kd79ue25IhNN/VtHFy1mG/6Tluyi+msc0UpwaoQzxSHa28mntAjIZY6kEgfR9Q==", + "dev": true, + "dependencies": { + "glob": "^8.0.1", + "json-parse-even-better-errors": "^2.3.1", + "normalize-package-data": "^4.0.0", + "npm-normalize-package-bin": "^2.0.0" + }, + "engines": { + "node": "^12.13.0 || ^14.15.0 || >=16.0.0" + } + }, + "node_modules/read-package-json-fast": { + "version": "2.0.3", + "resolved": "https://registry.npmjs.org/read-package-json-fast/-/read-package-json-fast-2.0.3.tgz", + "integrity": "sha512-W/BKtbL+dUjTuRL2vziuYhp76s5HZ9qQhd/dKfWIZveD0O40453QNyZhC0e63lqZrAQ4jiOapVoeJ7JrszenQQ==", + "dev": true, + "dependencies": { + "json-parse-even-better-errors": "^2.3.0", + "npm-normalize-package-bin": "^1.0.1" + }, + "engines": { + "node": ">=10" + } + }, + "node_modules/read-package-json/node_modules/hosted-git-info": { + "version": "5.1.0", + "resolved": "https://registry.npmjs.org/hosted-git-info/-/hosted-git-info-5.1.0.tgz", + "integrity": "sha512-Ek+QmMEqZF8XrbFdwoDjSbm7rT23pCgEMOJmz6GPk/s4yH//RQfNPArhIxbguNxROq/+5lNBwCDHMhA903Kx1Q==", + "dev": true, + "dependencies": { + "lru-cache": "^7.5.1" + }, + "engines": { + "node": "^12.13.0 || ^14.15.0 || >=16.0.0" + } + }, + "node_modules/read-package-json/node_modules/normalize-package-data": { + "version": "4.0.1", + "resolved": "https://registry.npmjs.org/normalize-package-data/-/normalize-package-data-4.0.1.tgz", + "integrity": "sha512-EBk5QKKuocMJhB3BILuKhmaPjI8vNRSpIfO9woLC6NyHVkKKdVEdAO1mrT0ZfxNR1lKwCcTkuZfmGIFdizZ8Pg==", + "dev": true, + "dependencies": { + "hosted-git-info": "^5.0.0", + "is-core-module": "^2.8.1", + "semver": "^7.3.5", + "validate-npm-package-license": "^3.0.4" + }, + "engines": { + "node": "^12.13.0 || ^14.15.0 || >=16.0.0" + } + }, + "node_modules/read-package-json/node_modules/npm-normalize-package-bin": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/npm-normalize-package-bin/-/npm-normalize-package-bin-2.0.0.tgz", + "integrity": "sha512-awzfKUO7v0FscrSpRoogyNm0sajikhBWpU0QMrW09AMi9n1PoKU6WaIqUzuJSQnpciZZmJ/jMZ2Egfmb/9LiWQ==", + "dev": true, + "engines": { + "node": "^12.13.0 || ^14.15.0 || >=16.0.0" + } + }, + "node_modules/read-pkg": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/read-pkg/-/read-pkg-3.0.0.tgz", + "integrity": "sha512-BLq/cCO9two+lBgiTYNqD6GdtK8s4NpaWrl6/rCO9w0TUS8oJl7cmToOZfRYllKTISY6nt1U7jQ53brmKqY6BA==", + "dev": true, + "dependencies": { + "load-json-file": "^4.0.0", + "normalize-package-data": "^2.3.2", + "path-type": "^3.0.0" + }, + "engines": { + "node": ">=4" + } + }, + "node_modules/read-pkg-up": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/read-pkg-up/-/read-pkg-up-3.0.0.tgz", + "integrity": "sha512-YFzFrVvpC6frF1sz8psoHDBGF7fLPc+llq/8NB43oagqWkx8ar5zYtsTORtOjw9W2RHLpWP+zTWwBvf1bCmcSw==", + "dev": true, + "dependencies": { + "find-up": "^2.0.0", + "read-pkg": "^3.0.0" + }, + "engines": { + "node": ">=4" + } + }, + "node_modules/read-pkg-up/node_modules/find-up": { + "version": "2.1.0", + "resolved": "https://registry.npmjs.org/find-up/-/find-up-2.1.0.tgz", + "integrity": "sha512-NWzkk0jSJtTt08+FBFMvXoeZnOJD+jTtsRmBYbAIzJdX6l7dLgR7CTubCM5/eDdPUBvLCeVasP1brfVR/9/EZQ==", + "dev": true, + "dependencies": { + "locate-path": "^2.0.0" + }, + "engines": { + "node": ">=4" + } + }, + "node_modules/read-pkg-up/node_modules/locate-path": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/locate-path/-/locate-path-2.0.0.tgz", + "integrity": "sha512-NCI2kiDkyR7VeEKm27Kda/iQHyKJe1Bu0FlTbYp3CqJu+9IFe9bLyAjMxf5ZDDbEg+iMPzB5zYyUTSm8wVTKmA==", + "dev": true, + "dependencies": { + "p-locate": "^2.0.0", + "path-exists": "^3.0.0" + }, + "engines": { + "node": ">=4" + } + }, + "node_modules/read-pkg-up/node_modules/p-limit": { + "version": "1.3.0", + "resolved": "https://registry.npmjs.org/p-limit/-/p-limit-1.3.0.tgz", + "integrity": "sha512-vvcXsLAJ9Dr5rQOPk7toZQZJApBl2K4J6dANSsEuh6QI41JYcsS/qhTGa9ErIUUgK3WNQoJYvylxvjqmiqEA9Q==", + "dev": true, + "dependencies": { + "p-try": "^1.0.0" + }, + "engines": { + "node": ">=4" + } + }, + "node_modules/read-pkg-up/node_modules/p-locate": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/p-locate/-/p-locate-2.0.0.tgz", + "integrity": "sha512-nQja7m7gSKuewoVRen45CtVfODR3crN3goVQ0DDZ9N3yHxgpkuBhZqsaiotSQRrADUrne346peY7kT3TSACykg==", + "dev": true, + "dependencies": { + "p-limit": "^1.1.0" + }, + "engines": { + "node": ">=4" + } + }, + "node_modules/read-pkg-up/node_modules/p-try": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/p-try/-/p-try-1.0.0.tgz", + "integrity": "sha512-U1etNYuMJoIz3ZXSrrySFjsXQTWOx2/jdi86L+2pRvph/qMKL6sbcCYdH23fqsbm8TH2Gn0OybpT4eSFlCVHww==", + "dev": true, + "engines": { + "node": ">=4" + } + }, + "node_modules/read-pkg-up/node_modules/path-exists": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/path-exists/-/path-exists-3.0.0.tgz", + "integrity": "sha512-bpC7GYwiDYQ4wYLe+FA8lhRjhQCMcQGuSgGGqDkg/QerRWw9CmGRT0iSOVRSZJ29NMLZgIzqaljJ63oaL4NIJQ==", + "dev": true, + "engines": { + "node": ">=4" + } + }, + "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/load-json-file": { + "version": "4.0.0", + "resolved": "https://registry.npmjs.org/load-json-file/-/load-json-file-4.0.0.tgz", + "integrity": "sha512-Kx8hMakjX03tiGTLAIdJ+lL0htKnXjEZN6hk/tozf/WOuYGdZBJrZ+rCJRbVCugsjB3jMLn9746NsQIf5VjBMw==", + "dev": true, + "dependencies": { + "graceful-fs": "^4.1.2", + "parse-json": "^4.0.0", + "pify": "^3.0.0", + "strip-bom": "^3.0.0" + }, + "engines": { + "node": ">=4" + } + }, + "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/parse-json": { + "version": "4.0.0", + "resolved": "https://registry.npmjs.org/parse-json/-/parse-json-4.0.0.tgz", + "integrity": "sha512-aOIos8bujGN93/8Ox/jPLh7RwVnPEysynVFE+fQZyg6jKELEHwzgKdLRFHUgXJL6kylijVSBC4BvN9OmsB48Rw==", + "dev": true, + "dependencies": { + "error-ex": "^1.3.1", + "json-parse-better-errors": "^1.0.1" + }, + "engines": { + "node": ">=4" + } + }, + "node_modules/read-pkg/node_modules/path-type": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/path-type/-/path-type-3.0.0.tgz", + "integrity": "sha512-T2ZUsdZFHgA3u4e5PfPbjd7HDDpxPnQb5jN0SrDsjNSuVXHJqtwTnWqG0B1jZrgmJ/7lj1EmVIByWt1gxGkWvg==", + "dev": true, + "dependencies": { + "pify": "^3.0.0" + }, + "engines": { + "node": ">=4" + } + }, + "node_modules/read-pkg/node_modules/pify": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/pify/-/pify-3.0.0.tgz", + "integrity": "sha512-C3FsVNH1udSEX48gGX1xfvwTWfsYWj5U+8/uK15BGzIGrKoUpghX8hWZwa/OFnakBiiVNmBvemTJR5mcy7iPcg==", + "dev": true, + "engines": { + "node": ">=4" + } + }, + "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/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/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/readdir-scoped-modules": { + "version": "1.1.0", + "resolved": "https://registry.npmjs.org/readdir-scoped-modules/-/readdir-scoped-modules-1.1.0.tgz", + "integrity": "sha512-asaikDeqAQg7JifRsZn1NJZXo9E+VwlyCfbkZhwyISinqk5zNS6266HS5kah6P0SaQKGF6SkNnZVHUzHFYxYDw==", + "dev": true, + "dependencies": { + "debuglog": "^1.0.1", + "dezalgo": "^1.0.0", + "graceful-fs": "^4.1.2", + "once": "^1.3.0" + } + }, + "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/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/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/registry-auth-token": { + "version": "5.0.1", + "resolved": "https://registry.npmjs.org/registry-auth-token/-/registry-auth-token-5.0.1.tgz", + "integrity": "sha512-UfxVOj8seK1yaIOiieV4FIP01vfBDLsY0H9sQzi9EbbUdJiuuBjJgLa1DpImXMNPnVkBD4eVxTEXcrZA6kfpJA==", + "dev": true, + "dependencies": { + "@pnpm/npm-conf": "^1.0.4" + }, + "engines": { + "node": ">=14" + } + }, + "node_modules/registry-url": { + "version": "6.0.1", + "resolved": "https://registry.npmjs.org/registry-url/-/registry-url-6.0.1.tgz", + "integrity": "sha512-+crtS5QjFRqFCoQmvGduwYWEBng99ZvmFvF+cUJkGYF1L1BfU8C6Zp9T7f5vPAwyLkUExpvK+ANVZmGU49qi4Q==", + "dev": true, + "dependencies": { + "rc": "1.2.8" + }, + "engines": { + "node": ">=12" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" + } + }, + "node_modules/remote-git-tags": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/remote-git-tags/-/remote-git-tags-3.0.0.tgz", + "integrity": "sha512-C9hAO4eoEsX+OXA4rla66pXZQ+TLQ8T9dttgQj18yuKlPMTVkIkdYXvlMC55IuUsIkV6DpmQYi10JKFLaU+l7w==", + "dev": true, + "engines": { + "node": ">=8" + } + }, + "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-alpn": { + "version": "1.2.1", + "resolved": "https://registry.npmjs.org/resolve-alpn/-/resolve-alpn-1.2.1.tgz", + "integrity": "sha512-0a1F4l73/ZFZOakJnQ3FvkJ2+gSTQWz/r2KE5OdDY0TxPm5h4GkqkWWfM47T7HsbnOtcJVEF4epCVy6u7Q3K+g==", + "dev": true + }, + "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/responselike": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/responselike/-/responselike-3.0.0.tgz", + "integrity": "sha512-40yHxbNcl2+rzXvZuVkrYohathsSJlMTXKryG5y8uciHv1+xDLHQpgjG64JUO9nrEq2jGLH6IZ8BcZyw3wrweg==", + "dev": true, + "dependencies": { + "lowercase-keys": "^3.0.0" + }, + "engines": { + "node": ">=14.16" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" + } + }, + "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/retry": { + "version": "0.12.0", + "resolved": "https://registry.npmjs.org/retry/-/retry-0.12.0.tgz", + "integrity": "sha512-9LkiTwjUh6rT555DtE9rTX+BKByPfrMzEAtnlEtdEwr3Nkffwiihqe2bWADg+OQRjt9gl6ICdmB/ZFDCGAtSow==", + "dev": true, + "engines": { + "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": "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/rimraf/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/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.5.7", + "resolved": "https://registry.npmjs.org/rxjs/-/rxjs-7.5.7.tgz", + "integrity": "sha512-z9MzKh/UcOqB3i20H6rtrlaE/CgjLOvheWK/9ILrbhROGTweAi1BaFsTT9FbwZi5Trr1qNRs+MXkhmR06awzQA==", + "dev": true, + "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==", + "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/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-diff": { + "version": "4.0.0", + "resolved": "https://registry.npmjs.org/semver-diff/-/semver-diff-4.0.0.tgz", + "integrity": "sha512-0Ju4+6A8iOnpL/Thra7dZsSlOHYAHIeMxfhWQRI1/VLcT3WDBZKKtQt/QkBOsiIN9ZpuvHE6cGZ0x4glCMmfiA==", + "dev": true, + "dependencies": { + "semver": "^7.3.5" + }, + "engines": { + "node": ">=12" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" + } + }, + "node_modules/semver-utils": { + "version": "1.1.4", + "resolved": "https://registry.npmjs.org/semver-utils/-/semver-utils-1.1.4.tgz", + "integrity": "sha512-EjnoLE5OGmDAVV/8YDoN5KiajNadjzIp9BAHOhYeQHt7j0UWxjmgsx4YD48wp4Ue1Qogq38F1GNUJNqF1kKKxA==", + "dev": true + }, + "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/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==", + "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/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/smart-buffer": { + "version": "4.2.0", + "resolved": "https://registry.npmjs.org/smart-buffer/-/smart-buffer-4.2.0.tgz", + "integrity": "sha512-94hK0Hh8rPqQl2xXc3HsaBoOXKV20MToPkcXvwbISWLEs+64sBq5kFgn2kJDHb1Pry9yrP0dxrCI9RRci7RXKg==", + "dev": 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==", + "dev": true, + "dependencies": { + "ip": "^2.0.0", + "smart-buffer": "^4.2.0" + }, + "engines": { + "node": ">= 10.13.0", + "npm": ">= 3.0.0" + } + }, + "node_modules/socks-proxy-agent": { + "version": "7.0.0", + "resolved": "https://registry.npmjs.org/socks-proxy-agent/-/socks-proxy-agent-7.0.0.tgz", + "integrity": "sha512-Fgl0YPZ902wEsAyiQ+idGd1A7rSFx/ayC1CQVMw5P+EQx2V0SgpGtf6OKFhVjPflPUl9YMmEOnmfjCdMUsygww==", + "dev": true, + "dependencies": { + "agent-base": "^6.0.2", + "debug": "^4.3.3", + "socks": "^2.6.2" + }, + "engines": { + "node": ">= 10" + } + }, + "node_modules/sort-keys": { + "version": "4.2.0", + "resolved": "https://registry.npmjs.org/sort-keys/-/sort-keys-4.2.0.tgz", + "integrity": "sha512-aUYIEU/UviqPgc8mHR6IW1EGxkAXpeRETYcrzg8cLAvUPZcpAlleSXHV2mY7G12GphSH6Gzv+4MMVSSkbdteHg==", + "dev": true, + "dependencies": { + "is-plain-obj": "^2.0.0" + }, + "engines": { + "node": ">=8" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" + } + }, + "node_modules/sort-keys/node_modules/is-plain-obj": { + "version": "2.1.0", + "resolved": "https://registry.npmjs.org/is-plain-obj/-/is-plain-obj-2.1.0.tgz", + "integrity": "sha512-YWnfyRwxL/+SsrWYfOpUtz5b3YD+nyfkHvjbcanzk8zgyO4ASD67uVMRt8k5bM4lLMDnXfriRhOpemw+NfT1eA==", + "dev": true, + "engines": { + "node": ">=8" + } + }, + "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-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/spawn-please": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/spawn-please/-/spawn-please-1.0.0.tgz", + "integrity": "sha512-Kz33ip6NRNKuyTRo3aDWyWxeGeM0ORDO552Fs6E1nj4pLWPkl37SrRtTnq+MEopVaqgmaO6bAvVS+v64BJ5M/A==", + "dev": true, + "engines": { + "node": ">=10" + } + }, + "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/split": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/split/-/split-1.0.1.tgz", + "integrity": "sha512-mTyOoPbrivtXnwnIxZRFYRrPNtEFKlpB2fvjSnCQUiAA6qAZzqwna5envK4uk6OIeP17CsdF3rSBGYVBsU0Tkg==", + "dev": true, + "dependencies": { + "through": "2" + }, + "engines": { + "node": "*" + } + }, + "node_modules/split2": { + "version": "3.2.2", + "resolved": "https://registry.npmjs.org/split2/-/split2-3.2.2.tgz", + "integrity": "sha512-9NThjpgZnifTkJpzTZ7Eue85S49QwpNhZTq6GRJwObb6jnLFNGB7Qm73V5HewTROPyxD0C29xqmaI68bQtV+hg==", + "dev": true, + "dependencies": { + "readable-stream": "^3.0.0" + } + }, + "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/ssri": { + "version": "9.0.1", + "resolved": "https://registry.npmjs.org/ssri/-/ssri-9.0.1.tgz", + "integrity": "sha512-o57Wcn66jMQvfHG1FlYbWeZWW/dHZhJXjpIcTfXldXEk5nz5lStPo3mK0OJQfGR3RbZUlbISexbljkJzuEj/8Q==", + "dev": true, + "dependencies": { + "minipass": "^3.1.1" + }, + "engines": { + "node": "^12.13.0 || ^14.15.0 || >=16.0.0" + } + }, + "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/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/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-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", + "integrity": "sha512-6fPc+R4ihwqP6N/aIv2f1gMH8lOVtWQHoqC4yK6oSDVVocumAsfCqjkXnqiYMhmMwS/mEHLp7Vehlt3ql6lEig==", + "dev": true, + "engines": { + "node": ">=8" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" + } + }, + "node_modules/strong-log-transformer": { + "version": "2.1.0", + "resolved": "https://registry.npmjs.org/strong-log-transformer/-/strong-log-transformer-2.1.0.tgz", + "integrity": "sha512-B3Hgul+z0L9a236FAUC9iZsL+nVHgoCJnqCbN588DjYxvGXaXaaFbfmQ/JhvKjZwsOukuR72XbHv71Qkug0HxA==", + "dev": true, + "dependencies": { + "duplexer": "^0.1.1", + "minimist": "^1.2.0", + "through": "^2.3.4" + }, + "bin": { + "sl-log-transformer": "bin/sl-log-transformer.js" + }, + "engines": { + "node": ">=4" + } + }, + "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", + "integrity": "sha512-ot0WnXS9fgdkgIcePe6RHNk1WA8+muPa6cSjeR3V8K27q9BB1rTE3R1p7Hv0z1ZyAc8s6Vvv8DIyWf681MAt0w==", + "dev": true, + "engines": { + "node": ">= 0.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/tar": { + "version": "6.1.11", + "resolved": "https://registry.npmjs.org/tar/-/tar-6.1.11.tgz", + "integrity": "sha512-an/KZQzQUkZCkuoAA64hM92X0Urb6VpRhAFllDzz44U2mcD5scmT3zBc4VgVpkugF580+DQn8eAFSyoQt0tznA==", + "dev": true, + "dependencies": { + "chownr": "^2.0.0", + "fs-minipass": "^2.0.0", + "minipass": "^3.0.0", + "minizlib": "^2.1.1", + "mkdirp": "^1.0.3", + "yallist": "^4.0.0" + }, + "engines": { + "node": ">= 10" + } + }, + "node_modules/tar-stream": { + "version": "2.2.0", + "resolved": "https://registry.npmjs.org/tar-stream/-/tar-stream-2.2.0.tgz", + "integrity": "sha512-ujeqbceABgwMZxEJnk2HDY2DlnUZ+9oEcb1KzTVfYHio0UE6dG71n60d8D2I4qNvleWrrXpmjpt7vZeF1LnMZQ==", + "dev": true, + "dependencies": { + "bl": "^4.0.3", + "end-of-stream": "^1.4.1", + "fs-constants": "^1.0.0", + "inherits": "^2.0.3", + "readable-stream": "^3.1.1" + }, + "engines": { + "node": ">=6" + } + }, + "node_modules/temp-dir": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/temp-dir/-/temp-dir-1.0.0.tgz", + "integrity": "sha512-xZFXEGbG7SNC3itwBzI3RYjq/cEhBkx2hJuKGIUOcEULmkQExXiHat2z/qkISYsuR+IKumhEfKKbV5qXmhICFQ==", + "dev": true, + "engines": { + "node": ">=4" + } + }, + "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/test-exclude/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/text-extensions": { + "version": "1.9.0", + "resolved": "https://registry.npmjs.org/text-extensions/-/text-extensions-1.9.0.tgz", + "integrity": "sha512-wiBrwC1EhBelW12Zy26JeOUkQ5mRu+5o8rpsJk5+2t+Y5vE7e842qtZDQ2g1NpX/29HdyFeJ4nSIhI47ENSxlQ==", + "dev": true, + "engines": { + "node": ">=0.10" + } + }, + "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/through2": { + "version": "4.0.2", + "resolved": "https://registry.npmjs.org/through2/-/through2-4.0.2.tgz", + "integrity": "sha512-iOqSav00cVxEEICeD7TjLB1sueEL+81Wpzp2bY17uZjZN0pWZPuo4suZ/61VujxmqSGFfgOcNuTZ85QJwNZQpw==", + "dev": true, + "dependencies": { + "readable-stream": "3" + } + }, + "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/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/tr46": { + "version": "0.0.3", + "resolved": "https://registry.npmjs.org/tr46/-/tr46-0.0.3.tgz", + "integrity": "sha512-N3WMsuqV66lT30CrXNbEjx4GEwlow3v6rr4mCcv6prnfwhS01rkgyFdjPNBYd9br7LpXV1+Emh01fHnq2Gdgrw==", + "dev": true + }, + "node_modules/treeverse": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/treeverse/-/treeverse-2.0.0.tgz", + "integrity": "sha512-N5gJCkLu1aXccpOTtqV6ddSEi6ZmGkh3hjmbu1IjcavJK4qyOVQmi0myQKM7z5jVGmD68SJoliaVrMmVObhj6A==", + "dev": true, + "engines": { + "node": "^12.13.0 || ^14.15.0 || >=16.0.0" + } + }, + "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", + "integrity": "sha512-fxDhWnFSLt3VuTwtvJt5fpwxBHg5AdKWMsgcPOOIilyjymcYVZoCQF8fvFRezCNfblEXmi+PcM1eYHeOAgXCOQ==", + "dev": 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.1", + "resolved": "https://registry.npmjs.org/json5/-/json5-1.0.1.tgz", + "integrity": "sha512-aKS4WQjPenRxiQsC93MNfjx+nbF4PAdYzmd/1JIj8HYzqfbu86beTuNgXDzPknWk0n0uARlyewZo4s++ES36Ow==", + "dev": true, + "dependencies": { + "minimist": "^1.2.0" + }, + "bin": { + "json5": "lib/cli.js" + } + }, + "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.4.0", + "resolved": "https://registry.npmjs.org/tslib/-/tslib-2.4.0.tgz", + "integrity": "sha512-d6xOpEDfsi2CZVlPQzGeux8XMwLT9hssAsaPYExaQMuYskwb+x1x7J371tWlbBdWHroy99KnVB6qIkUbs5X3UQ==", + "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/typedarray": { + "version": "0.0.6", + "resolved": "https://registry.npmjs.org/typedarray/-/typedarray-0.0.6.tgz", + "integrity": "sha512-/aCDEGatGvZ2BIk+HmLf4ifCJFwvKFNb9/JeZPMulfgFracn9QFcAf5GO8B/mweUjSoblS5In0cWhqpfs/5PQA==", + "dev": true + }, + "node_modules/typedarray-to-buffer": { + "version": "3.1.5", + "resolved": "https://registry.npmjs.org/typedarray-to-buffer/-/typedarray-to-buffer-3.1.5.tgz", + "integrity": "sha512-zdu8XMNEDepKKR+XYOXAVPtWui0ly0NtohUscw+UmaHiAWT8hrV1rr//H6V+0DvJ3OQ19S979M0laLfX8rm82Q==", + "dev": true, + "dependencies": { + "is-typedarray": "^1.0.0" + } + }, + "node_modules/typescript": { + "version": "4.8.4", + "resolved": "https://registry.npmjs.org/typescript/-/typescript-4.8.4.tgz", + "integrity": "sha512-QCh+85mCy+h0IGff8r5XWzOVSbBO+KfeYrMQh7NJ58QujwcE22u+NUSmUxqF+un70P9GXKxa2HCNiTTMJknyjQ==", + "dev": true, + "bin": { + "tsc": "bin/tsc", + "tsserver": "bin/tsserver" + }, + "engines": { + "node": ">=4.2.0" + } + }, + "node_modules/uglify-js": { + "version": "3.17.3", + "resolved": "https://registry.npmjs.org/uglify-js/-/uglify-js-3.17.3.tgz", + "integrity": "sha512-JmMFDME3iufZnBpyKL+uS78LRiC+mK55zWfM5f/pWBJfpOttXAqYfdDGRukYhJuyRinvPVAtUhvy7rlDybNtFg==", + "dev": true, + "optional": true, + "bin": { + "uglifyjs": "bin/uglifyjs" + }, + "engines": { + "node": ">=0.8.0" + } + }, + "node_modules/unique-filename": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/unique-filename/-/unique-filename-2.0.1.tgz", + "integrity": "sha512-ODWHtkkdx3IAR+veKxFV+VBkUMcN+FaqzUUd7IZzt+0zhDZFPFxhlqwPF3YQvMHx1TD0tdgYl+kuPnJ8E6ql7A==", + "dev": true, + "dependencies": { + "unique-slug": "^3.0.0" + }, + "engines": { + "node": "^12.13.0 || ^14.15.0 || >=16.0.0" + } + }, + "node_modules/unique-slug": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/unique-slug/-/unique-slug-3.0.0.tgz", + "integrity": "sha512-8EyMynh679x/0gqE9fT9oilG+qEt+ibFyqjuVTsZn1+CMxH+XLlpvr2UZx4nVcCwTpx81nICr2JQFkM+HPLq4w==", + "dev": true, + "dependencies": { + "imurmurhash": "^0.1.4" + }, + "engines": { + "node": "^12.13.0 || ^14.15.0 || >=16.0.0" + } + }, + "node_modules/unique-string": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/unique-string/-/unique-string-3.0.0.tgz", + "integrity": "sha512-VGXBUVwxKMBUznyffQweQABPRRW1vHZAbadFZud4pLFAqRGvv/96vafgjWFqzourzr8YonlQiPgH0YCJfawoGQ==", + "dev": true, + "dependencies": { + "crypto-random-string": "^4.0.0" + }, + "engines": { + "node": ">=12" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" + } + }, + "node_modules/universal-user-agent": { + "version": "6.0.0", + "resolved": "https://registry.npmjs.org/universal-user-agent/-/universal-user-agent-6.0.0.tgz", + "integrity": "sha512-isyNax3wXoKaulPDZWHQqbmIx1k2tb9fb3GGDBRxCscfYV2Ch7WxPArBsFEG8s/safwXTT7H4QGhaIkTp9447w==", + "dev": true + }, + "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/untildify": { + "version": "4.0.0", + "resolved": "https://registry.npmjs.org/untildify/-/untildify-4.0.0.tgz", + "integrity": "sha512-KK8xQ1mkzZeg9inewmFVDNkg3l5LUhoq9kN6iWYB/CC9YMG8HA+c1Q8HwDe6dEX7kErrEVNVBO3fWsVq5iDgtw==", + "dev": true, + "engines": { + "node": ">=8" + } + }, + "node_modules/upath": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/upath/-/upath-2.0.1.tgz", + "integrity": "sha512-1uEe95xksV1O0CYKXo8vQvN1JEbtJp7lb7C5U9HMsIp6IVwntkH/oNUzyVNQSd4S1sYk2FpSSW44FqMc8qee5w==", + "dev": true, + "engines": { + "node": ">=4", + "yarn": "*" + } + }, + "node_modules/update-notifier": { + "version": "6.0.2", + "resolved": "https://registry.npmjs.org/update-notifier/-/update-notifier-6.0.2.tgz", + "integrity": "sha512-EDxhTEVPZZRLWYcJ4ZXjGFN0oP7qYvbXWzEgRm/Yql4dHX5wDbvh89YHP6PK1lzZJYrMtXUuZZz8XGK+U6U1og==", + "dev": true, + "dependencies": { + "boxen": "^7.0.0", + "chalk": "^5.0.1", + "configstore": "^6.0.0", + "has-yarn": "^3.0.0", + "import-lazy": "^4.0.0", + "is-ci": "^3.0.1", + "is-installed-globally": "^0.4.0", + "is-npm": "^6.0.0", + "is-yarn-global": "^0.4.0", + "latest-version": "^7.0.0", + "pupa": "^3.1.0", + "semver": "^7.3.7", + "semver-diff": "^4.0.0", + "xdg-basedir": "^5.1.0" + }, + "engines": { + "node": ">=14.16" + }, + "funding": { + "url": "https://github.com/yeoman/update-notifier?sponsor=1" + } + }, + "node_modules/update-notifier/node_modules/chalk": { + "version": "5.1.0", + "resolved": "https://registry.npmjs.org/chalk/-/chalk-5.1.0.tgz", + "integrity": "sha512-56zD4khRTBoIyzUYAFgDDaPhUMN/fC/rySe6aZGqbj/VWiU2eI3l6ZLOtYGFZAV5v02mwPjtpzlrOveJiz5eZQ==", + "dev": true, + "engines": { + "node": "^12.17.0 || ^14.13 || >=16.0.0" + }, + "funding": { + "url": "https://github.com/chalk/chalk?sponsor=1" + } + }, + "node_modules/update-notifier/node_modules/ci-info": { + "version": "3.5.0", + "resolved": "https://registry.npmjs.org/ci-info/-/ci-info-3.5.0.tgz", + "integrity": "sha512-yH4RezKOGlOhxkmhbeNuC4eYZKAUsEaGtBuBzDDP1eFUKiccDWzBABxBfOx31IDwDIXMTxWuwAxUGModvkbuVw==", + "dev": true + }, + "node_modules/update-notifier/node_modules/is-ci": { + "version": "3.0.1", + "resolved": "https://registry.npmjs.org/is-ci/-/is-ci-3.0.1.tgz", + "integrity": "sha512-ZYvCgrefwqoQ6yTyYUbQu64HsITZ3NfKX1lzaEYdkTDcfKzzCI/wthRRYKkdjHKFVgNiXKAKm65Zo1pk2as/QQ==", + "dev": true, + "dependencies": { + "ci-info": "^3.2.0" + }, + "bin": { + "is-ci": "bin.js" + } + }, + "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==", + "dev": true + }, + "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-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/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/validate-npm-package-name": { + "version": "4.0.0", + "resolved": "https://registry.npmjs.org/validate-npm-package-name/-/validate-npm-package-name-4.0.0.tgz", + "integrity": "sha512-mzR0L8ZDktZjpX4OB46KT+56MAhl4EIazWP/+G/HPGuvfdaqg4YsCdtOm6U9+LOFyYDoh4dpnpxZRB9MQQns5Q==", + "dev": true, + "dependencies": { + "builtins": "^5.0.0" + }, + "engines": { + "node": "^12.13.0 || ^14.15.0 || >=16.0.0" + } + }, + "node_modules/walk-up-path": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/walk-up-path/-/walk-up-path-1.0.0.tgz", + "integrity": "sha512-hwj/qMDUEjCU5h0xr90KGCf0tg0/LgJbmOWgrWKYlcJZM7XvquvUJZ0G/HMGr7F7OQMOUuPHWP9JpriinkAlkg==", + "dev": true + }, + "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==", + "dev": true + }, + "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==", + "dev": true, + "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/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==", + "dev": true, + "dependencies": { + "string-width": "^1.0.2 || 2 || 3 || 4" + } + }, + "node_modules/widest-line": { + "version": "4.0.1", + "resolved": "https://registry.npmjs.org/widest-line/-/widest-line-4.0.1.tgz", + "integrity": "sha512-o0cyEG0e8GPzT4iGHphIOh0cJOV8fivsXxddQasHPHfoZf1ZexrfeA21w2NaEN1RHE+fXlfISmOE8R9N3u3Qig==", + "dev": true, + "dependencies": { + "string-width": "^5.0.1" + }, + "engines": { + "node": ">=12" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" + } + }, + "node_modules/widest-line/node_modules/ansi-regex": { + "version": "6.0.1", + "resolved": "https://registry.npmjs.org/ansi-regex/-/ansi-regex-6.0.1.tgz", + "integrity": "sha512-n5M855fKb2SsfMIiFFoVrABHJC8QtHwVx+mHWP3QcEqBHYienj5dHSgjbxtC0WEZXYt4wcD6zrQElDPhFuZgfA==", + "dev": true, + "engines": { + "node": ">=12" + }, + "funding": { + "url": "https://github.com/chalk/ansi-regex?sponsor=1" + } + }, + "node_modules/widest-line/node_modules/emoji-regex": { + "version": "9.2.2", + "resolved": "https://registry.npmjs.org/emoji-regex/-/emoji-regex-9.2.2.tgz", + "integrity": "sha512-L18DaJsXSUk2+42pv8mLs5jJT2hqFkFE4j21wOmgbUqsZ2hL72NsUU785g9RXgo3s0ZNgVl42TiHp3ZtOv/Vyg==", + "dev": true + }, + "node_modules/widest-line/node_modules/string-width": { + "version": "5.1.2", + "resolved": "https://registry.npmjs.org/string-width/-/string-width-5.1.2.tgz", + "integrity": "sha512-HnLOCR3vjcY8beoNLtcjZ5/nxn2afmME6lhrDrebokqMap+XbeW8n9TXpPDOqdGK5qcI3oT0GKTW6wC7EMiVqA==", + "dev": true, + "dependencies": { + "eastasianwidth": "^0.2.0", + "emoji-regex": "^9.2.2", + "strip-ansi": "^7.0.1" + }, + "engines": { + "node": ">=12" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" + } + }, + "node_modules/widest-line/node_modules/strip-ansi": { + "version": "7.0.1", + "resolved": "https://registry.npmjs.org/strip-ansi/-/strip-ansi-7.0.1.tgz", + "integrity": "sha512-cXNxvT8dFNRVfhVME3JAe98mkXDYN2O1l7jmcwMnOslDeESg1rF/OZMtK0nRAhiari1unG5cD4jG3rapUAkLbw==", + "dev": true, + "dependencies": { + "ansi-regex": "^6.0.1" + }, + "engines": { + "node": ">=12" + }, + "funding": { + "url": "https://github.com/chalk/strip-ansi?sponsor=1" + } + }, + "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/wordwrap": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/wordwrap/-/wordwrap-1.0.0.tgz", + "integrity": "sha512-gvVzJFlPycKc5dZN4yPkP8w7Dc37BtP1yczEneOb4uq34pXZcvrtRTmWV8W+Ume+XCxKgbjM+nevkyFPMybd4Q==", + "dev": true + }, + "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": "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/write-json-file": { + "version": "4.3.0", + "resolved": "https://registry.npmjs.org/write-json-file/-/write-json-file-4.3.0.tgz", + "integrity": "sha512-PxiShnxf0IlnQuMYOPPhPkhExoCQuTUNPOa/2JWCYTmBquU9njyyDuwRKN26IZBlp4yn1nt+Agh2HOOBl+55HQ==", + "dev": true, + "dependencies": { + "detect-indent": "^6.0.0", + "graceful-fs": "^4.1.15", + "is-plain-obj": "^2.0.0", + "make-dir": "^3.0.0", + "sort-keys": "^4.0.0", + "write-file-atomic": "^3.0.0" + }, + "engines": { + "node": ">=8.3" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" + } + }, + "node_modules/write-json-file/node_modules/is-plain-obj": { + "version": "2.1.0", + "resolved": "https://registry.npmjs.org/is-plain-obj/-/is-plain-obj-2.1.0.tgz", + "integrity": "sha512-YWnfyRwxL/+SsrWYfOpUtz5b3YD+nyfkHvjbcanzk8zgyO4ASD67uVMRt8k5bM4lLMDnXfriRhOpemw+NfT1eA==", + "dev": true, + "engines": { + "node": ">=8" + } + }, + "node_modules/write-json-file/node_modules/write-file-atomic": { + "version": "3.0.3", + "resolved": "https://registry.npmjs.org/write-file-atomic/-/write-file-atomic-3.0.3.tgz", + "integrity": "sha512-AvHcyZ5JnSfq3ioSyjrBkH9yW4m7Ayk8/9My/DD9onKeu/94fwrMocemO2QAJFAlnnDN+ZDS+ZjAR5ua1/PV/Q==", + "dev": true, + "dependencies": { + "imurmurhash": "^0.1.4", + "is-typedarray": "^1.0.0", + "signal-exit": "^3.0.2", + "typedarray-to-buffer": "^3.1.5" + } + }, + "node_modules/write-pkg": { + "version": "4.0.0", + "resolved": "https://registry.npmjs.org/write-pkg/-/write-pkg-4.0.0.tgz", + "integrity": "sha512-v2UQ+50TNf2rNHJ8NyWttfm/EJUBWMJcx6ZTYZr6Qp52uuegWw/lBkCtCbnYZEmPRNL61m+u67dAmGxo+HTULA==", + "dev": true, + "dependencies": { + "sort-keys": "^2.0.0", + "type-fest": "^0.4.1", + "write-json-file": "^3.2.0" + }, + "engines": { + "node": ">=8" + } + }, + "node_modules/write-pkg/node_modules/detect-indent": { + "version": "5.0.0", + "resolved": "https://registry.npmjs.org/detect-indent/-/detect-indent-5.0.0.tgz", + "integrity": "sha512-rlpvsxUtM0PQvy9iZe640/IWwWYyBsTApREbA1pHOpmOUIl9MkP/U4z7vTtg4Oaojvqhxt7sdufnT0EzGaR31g==", + "dev": true, + "engines": { + "node": ">=4" + } + }, + "node_modules/write-pkg/node_modules/make-dir": { + "version": "2.1.0", + "resolved": "https://registry.npmjs.org/make-dir/-/make-dir-2.1.0.tgz", + "integrity": "sha512-LS9X+dc8KLxXCb8dni79fLIIUA5VyZoyjSMCwTluaXA0o27cCK0bhXkpgw+sTXVpPy/lSO57ilRixqk0vDmtRA==", + "dev": true, + "dependencies": { + "pify": "^4.0.1", + "semver": "^5.6.0" + }, + "engines": { + "node": ">=6" + } + }, + "node_modules/write-pkg/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/write-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/write-pkg/node_modules/sort-keys": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/sort-keys/-/sort-keys-2.0.0.tgz", + "integrity": "sha512-/dPCrG1s3ePpWm6yBbxZq5Be1dXGLyLn9Z791chDC3NFrpkVbWGzkBwPN1knaciexFXgRJ7hzdnwZ4stHSDmjg==", + "dev": true, + "dependencies": { + "is-plain-obj": "^1.0.0" + }, + "engines": { + "node": ">=4" + } + }, + "node_modules/write-pkg/node_modules/type-fest": { + "version": "0.4.1", + "resolved": "https://registry.npmjs.org/type-fest/-/type-fest-0.4.1.tgz", + "integrity": "sha512-IwzA/LSfD2vC1/YDYMv/zHP4rDF1usCwllsDpbolT3D4fUepIO7f9K70jjmUewU/LmGUKJcwcVtDCpnKk4BPMw==", + "dev": true, + "engines": { + "node": ">=6" + } + }, + "node_modules/write-pkg/node_modules/write-file-atomic": { + "version": "2.4.3", + "resolved": "https://registry.npmjs.org/write-file-atomic/-/write-file-atomic-2.4.3.tgz", + "integrity": "sha512-GaETH5wwsX+GcnzhPgKcKjJ6M2Cq3/iZp1WyY/X1CSqrW+jVNM9Y7D8EC2sM4ZG/V8wZlSniJnCKWPmBYAucRQ==", + "dev": true, + "dependencies": { + "graceful-fs": "^4.1.11", + "imurmurhash": "^0.1.4", + "signal-exit": "^3.0.2" + } + }, + "node_modules/write-pkg/node_modules/write-json-file": { + "version": "3.2.0", + "resolved": "https://registry.npmjs.org/write-json-file/-/write-json-file-3.2.0.tgz", + "integrity": "sha512-3xZqT7Byc2uORAatYiP3DHUUAVEkNOswEWNs9H5KXiicRTvzYzYqKjYc4G7p+8pltvAw641lVByKVtMpf+4sYQ==", + "dev": true, + "dependencies": { + "detect-indent": "^5.0.0", + "graceful-fs": "^4.1.15", + "make-dir": "^2.1.0", + "pify": "^4.0.1", + "sort-keys": "^2.0.0", + "write-file-atomic": "^2.4.2" + }, + "engines": { + "node": ">=6" + } + }, + "node_modules/xdg-basedir": { + "version": "5.1.0", + "resolved": "https://registry.npmjs.org/xdg-basedir/-/xdg-basedir-5.1.0.tgz", + "integrity": "sha512-GCPAHLvrIH13+c0SuacwvRYj2SxJXQ4kaVTT5xgL3kPrz56XxkF21IGhjSE1+W0aw7gpBWRGXLCPnPby6lSpmQ==", + "dev": true, + "engines": { + "node": ">=12" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" + } + }, + "node_modules/xtend": { + "version": "4.0.2", + "resolved": "https://registry.npmjs.org/xtend/-/xtend-4.0.2.tgz", + "integrity": "sha512-LKYU1iAXJXUgAXn9URjiu+MWhyUXHsvfp7mcuYm9dSUKK0/CjtrUwFAxD82/mCWbtLsGjFIad0wIsod4zrTAEQ==", + "dev": true, + "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": "4.0.0", + "resolved": "https://registry.npmjs.org/yallist/-/yallist-4.0.0.tgz", + "integrity": "sha512-3wdGidZyq5PB084XLES5TpOSRA3wjXAlIWMhum2kRcv/41Sn2emQ0dycQW4uZXLejwKvg6EsvbdlVL+FYEct7A==", + "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": "16.2.0", + "resolved": "https://registry.npmjs.org/yargs/-/yargs-16.2.0.tgz", + "integrity": "sha512-D1mvvtDG0L5ft/jGWkLpG1+m0eQxOfaBvTNELraWj22wSVUMWxZUvYgJYcKh6jGGIkJFhH4IZPQhR4TKpc8mBw==", + "dev": true, + "dependencies": { + "cliui": "^7.0.2", + "escalade": "^3.1.1", + "get-caller-file": "^2.0.5", + "require-directory": "^2.1.1", + "string-width": "^4.2.0", + "y18n": "^5.0.5", + "yargs-parser": "^20.2.2" + }, + "engines": { + "node": ">=10" + } + }, + "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", + "integrity": "sha512-rVksvsnNCdJ/ohGc6xgPwyN8eheCxsiLM8mxuE/t/mOVqJewPuO1miLpTHQiRgTKCLexL4MeAFVagts7HmNZ2Q==", + "dev": true, + "engines": { + "node": ">=10" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" + } + } + }, + "dependencies": { + "@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, + "requires": { + "@babel/highlight": "^7.18.6" + } + }, + "@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 + }, + "@babel/highlight": { + "version": "7.18.6", + "resolved": "https://registry.npmjs.org/@babel/highlight/-/highlight-7.18.6.tgz", + "integrity": "sha512-u7stbOuYjaPezCuLj29hNW1v64M2Md2qupEKP1fHc7WdOA3DgLh37suiSrZYY7haUB7iBeQZ9P1uiRF359do3g==", + "dev": true, + "requires": { + "@babel/helper-validator-identifier": "^7.18.6", + "chalk": "^2.0.0", + "js-tokens": "^4.0.0" + }, + "dependencies": { + "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, + "requires": { + "color-convert": "^1.9.0" + } + }, + "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, + "requires": { + "ansi-styles": "^3.2.1", + "escape-string-regexp": "^1.0.5", + "supports-color": "^5.3.0" + } + }, + "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, + "requires": { + "color-name": "1.1.3" + } + }, + "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 + }, + "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 + }, + "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 + }, + "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, + "requires": { + "has-flag": "^3.0.0" + } + } + } + }, + "@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 + }, + "@eslint/eslintrc": { + "version": "1.3.3", + "resolved": "https://registry.npmjs.org/@eslint/eslintrc/-/eslintrc-1.3.3.tgz", + "integrity": "sha512-uj3pT6Mg+3t39fvLrj8iuCIJ38zKO9FpGtJ4BBJebJhEwjoT+KLVNCcHT5QC9NGRIEi7fZ0ZR8YRb884auB4Lg==", + "dev": true, + "requires": { + "ajv": "^6.12.4", + "debug": "^4.3.2", + "espree": "^9.4.0", + "globals": "^13.15.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" + }, + "dependencies": { + "ajv": { + "version": "6.12.6", + "resolved": "https://registry.npmjs.org/ajv/-/ajv-6.12.6.tgz", + "integrity": "sha512-j3fVLgvTo527anyYyJOGTYJbG+vnnQYvE0m5mmkc1TK+nxAppkCLMIL0aZ4dblVCNoGShhm+kzE4ZUykBoMg4g==", + "dev": true, + "requires": { + "fast-deep-equal": "^3.1.1", + "fast-json-stable-stringify": "^2.0.0", + "json-schema-traverse": "^0.4.1", + "uri-js": "^4.2.2" + } + }, + "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 + } + } + }, + "@gar/promisify": { + "version": "1.1.3", + "resolved": "https://registry.npmjs.org/@gar/promisify/-/promisify-1.1.3.tgz", + "integrity": "sha512-k2Ty1JcVojjJFwrg/ThKi2ujJ7XNLYaFGNB/bWT9wGR+oSMJHMa5w+CUq6p/pVrKeNNgA7pCqEcjSnHVoqJQFw==", + "dev": true + }, + "@humanwhocodes/config-array": { + "version": "0.10.7", + "resolved": "https://registry.npmjs.org/@humanwhocodes/config-array/-/config-array-0.10.7.tgz", + "integrity": "sha512-MDl6D6sBsaV452/QSdX+4CXIjZhIcI0PELsxUjk4U828yd58vk3bTIvk/6w5FY+4hIy9sLW0sfrV7K7Kc++j/w==", + "dev": true, + "requires": { + "@humanwhocodes/object-schema": "^1.2.1", + "debug": "^4.1.1", + "minimatch": "^3.0.4" + } + }, + "@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 + }, + "@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 + }, + "@hutson/parse-repository-url": { + "version": "3.0.2", + "resolved": "https://registry.npmjs.org/@hutson/parse-repository-url/-/parse-repository-url-3.0.2.tgz", + "integrity": "sha512-H9XAx3hc0BQHY6l+IFSWHDySypcXsvsuLhgYLUGywmJ5pswRVQJUHpOsobnLYp2ZUaUlKiKDrgWWhosOwAEM8Q==", + "dev": true + }, + "@isaacs/string-locale-compare": { + "version": "1.1.0", + "resolved": "https://registry.npmjs.org/@isaacs/string-locale-compare/-/string-locale-compare-1.1.0.tgz", + "integrity": "sha512-SQ7Kzhh9+D+ZW9MA0zkYv3VXhIDNx+LzM6EJ+/65I3QY+enU6Itte7E5XX7EWrqLW2FN4n06GWzBnPoC3th2aQ==", + "dev": true + }, + "@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 + }, + "@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 + }, + "@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 + }, + "@jridgewell/trace-mapping": { + "version": "0.3.16", + "resolved": "https://registry.npmjs.org/@jridgewell/trace-mapping/-/trace-mapping-0.3.16.tgz", + "integrity": "sha512-LCQ+NeThyJ4k1W2d+vIKdxuSt9R3pQSZ4P92m7EakaYuXcVWbHuT5bjNcqLd4Rdgi6xYWYDvBJZJLZSLanjDcA==", + "dev": true, + "requires": { + "@jridgewell/resolve-uri": "3.1.0", + "@jridgewell/sourcemap-codec": "1.4.14" + } + }, + "@lerna/add": { + "version": "5.6.2", + "resolved": "https://registry.npmjs.org/@lerna/add/-/add-5.6.2.tgz", + "integrity": "sha512-NHrm7kYiqP+EviguY7/NltJ3G9vGmJW6v2BASUOhP9FZDhYbq3O+rCDlFdoVRNtcyrSg90rZFMOWHph4KOoCQQ==", + "dev": true, + "requires": { + "@lerna/bootstrap": "5.6.2", + "@lerna/command": "5.6.2", + "@lerna/filter-options": "5.6.2", + "@lerna/npm-conf": "5.6.2", + "@lerna/validation-error": "5.6.2", + "dedent": "^0.7.0", + "npm-package-arg": "8.1.1", + "p-map": "^4.0.0", + "pacote": "^13.6.1", + "semver": "^7.3.4" + } + }, + "@lerna/bootstrap": { + "version": "5.6.2", + "resolved": "https://registry.npmjs.org/@lerna/bootstrap/-/bootstrap-5.6.2.tgz", + "integrity": "sha512-S2fMOEXbef7nrybQhzBywIGSLhuiQ5huPp1sU+v9Y6XEBsy/2IA+lb0gsZosvPqlRfMtiaFstL+QunaBhlWECA==", + "dev": true, + "requires": { + "@lerna/command": "5.6.2", + "@lerna/filter-options": "5.6.2", + "@lerna/has-npm-version": "5.6.2", + "@lerna/npm-install": "5.6.2", + "@lerna/package-graph": "5.6.2", + "@lerna/pulse-till-done": "5.6.2", + "@lerna/rimraf-dir": "5.6.2", + "@lerna/run-lifecycle": "5.6.2", + "@lerna/run-topologically": "5.6.2", + "@lerna/symlink-binary": "5.6.2", + "@lerna/symlink-dependencies": "5.6.2", + "@lerna/validation-error": "5.6.2", + "@npmcli/arborist": "5.3.0", + "dedent": "^0.7.0", + "get-port": "^5.1.1", + "multimatch": "^5.0.0", + "npm-package-arg": "8.1.1", + "npmlog": "^6.0.2", + "p-map": "^4.0.0", + "p-map-series": "^2.1.0", + "p-waterfall": "^2.1.1", + "semver": "^7.3.4" + } + }, + "@lerna/changed": { + "version": "5.6.2", + "resolved": "https://registry.npmjs.org/@lerna/changed/-/changed-5.6.2.tgz", + "integrity": "sha512-uUgrkdj1eYJHQGsXXlpH5oEAfu3x0qzeTjgvpdNrxHEdQWi7zWiW59hRadmiImc14uJJYIwVK5q/QLugrsdGFQ==", + "dev": true, + "requires": { + "@lerna/collect-updates": "5.6.2", + "@lerna/command": "5.6.2", + "@lerna/listable": "5.6.2", + "@lerna/output": "5.6.2" + } + }, + "@lerna/check-working-tree": { + "version": "5.6.2", + "resolved": "https://registry.npmjs.org/@lerna/check-working-tree/-/check-working-tree-5.6.2.tgz", + "integrity": "sha512-6Vf3IB6p+iNIubwVgr8A/KOmGh5xb4SyRmhFtAVqe33yWl2p3yc+mU5nGoz4ET3JLF1T9MhsePj0hNt6qyOTLQ==", + "dev": true, + "requires": { + "@lerna/collect-uncommitted": "5.6.2", + "@lerna/describe-ref": "5.6.2", + "@lerna/validation-error": "5.6.2" + } + }, + "@lerna/child-process": { + "version": "5.6.2", + "resolved": "https://registry.npmjs.org/@lerna/child-process/-/child-process-5.6.2.tgz", + "integrity": "sha512-QIOQ3jIbWdduHd5892fbo3u7/dQgbhzEBB7cvf+Ys/iCPP8UQrBECi1lfRgA4kcTKC2MyMz0SoyXZz/lFcXc3A==", + "dev": true, + "requires": { + "chalk": "^4.1.0", + "execa": "^5.0.0", + "strong-log-transformer": "^2.1.0" + } + }, + "@lerna/clean": { + "version": "5.6.2", + "resolved": "https://registry.npmjs.org/@lerna/clean/-/clean-5.6.2.tgz", + "integrity": "sha512-A7j8r0Hk2pGyLUyaCmx4keNHen1L/KdcOjb4nR6X8GtTJR5AeA47a8rRKOCz9wwdyMPlo2Dau7d3RV9viv7a5g==", + "dev": true, + "requires": { + "@lerna/command": "5.6.2", + "@lerna/filter-options": "5.6.2", + "@lerna/prompt": "5.6.2", + "@lerna/pulse-till-done": "5.6.2", + "@lerna/rimraf-dir": "5.6.2", + "p-map": "^4.0.0", + "p-map-series": "^2.1.0", + "p-waterfall": "^2.1.1" + } + }, + "@lerna/cli": { + "version": "5.6.2", + "resolved": "https://registry.npmjs.org/@lerna/cli/-/cli-5.6.2.tgz", + "integrity": "sha512-w0NRIEqDOmYKlA5t0iyqx0hbY7zcozvApmfvwF0lhkuhf3k6LRAFSamtimGQWicC779a7J2NXw4ASuBV47Fs1Q==", + "dev": true, + "requires": { + "@lerna/global-options": "5.6.2", + "dedent": "^0.7.0", + "npmlog": "^6.0.2", + "yargs": "^16.2.0" + } + }, + "@lerna/collect-uncommitted": { + "version": "5.6.2", + "resolved": "https://registry.npmjs.org/@lerna/collect-uncommitted/-/collect-uncommitted-5.6.2.tgz", + "integrity": "sha512-i0jhxpypyOsW2PpPwIw4xg6EPh7/N3YuiI6P2yL7PynZ8nOv8DkIdoyMkhUP4gALjBfckH8Bj94eIaKMviqW4w==", + "dev": true, + "requires": { + "@lerna/child-process": "5.6.2", + "chalk": "^4.1.0", + "npmlog": "^6.0.2" + } + }, + "@lerna/collect-updates": { + "version": "5.6.2", + "resolved": "https://registry.npmjs.org/@lerna/collect-updates/-/collect-updates-5.6.2.tgz", + "integrity": "sha512-DdTK13X6PIsh9HINiMniFeiivAizR/1FBB+hDVe6tOhsXFBfjHMw1xZhXlE+mYIoFmDm1UFK7zvQSexoaxRqFA==", + "dev": true, + "requires": { + "@lerna/child-process": "5.6.2", + "@lerna/describe-ref": "5.6.2", + "minimatch": "^3.0.4", + "npmlog": "^6.0.2", + "slash": "^3.0.0" + } + }, + "@lerna/command": { + "version": "5.6.2", + "resolved": "https://registry.npmjs.org/@lerna/command/-/command-5.6.2.tgz", + "integrity": "sha512-eLVGI9TmxcaGt1M7TXGhhBZoeWOtOedMiH7NuCGHtL6TMJ9k+SCExyx+KpNmE6ImyNOzws6EvYLPLjftiqmoaA==", + "dev": true, + "requires": { + "@lerna/child-process": "5.6.2", + "@lerna/package-graph": "5.6.2", + "@lerna/project": "5.6.2", + "@lerna/validation-error": "5.6.2", + "@lerna/write-log-file": "5.6.2", + "clone-deep": "^4.0.1", + "dedent": "^0.7.0", + "execa": "^5.0.0", + "is-ci": "^2.0.0", + "npmlog": "^6.0.2" + } + }, + "@lerna/conventional-commits": { + "version": "5.6.2", + "resolved": "https://registry.npmjs.org/@lerna/conventional-commits/-/conventional-commits-5.6.2.tgz", + "integrity": "sha512-fPrJpYJhxCgY2uyOCTcAAC6+T6lUAtpEGxLbjWHWTb13oKKEygp9THoFpe6SbAD0fYMb3jeZCZCqNofM62rmuA==", + "dev": true, + "requires": { + "@lerna/validation-error": "5.6.2", + "conventional-changelog-angular": "^5.0.12", + "conventional-changelog-core": "^4.2.4", + "conventional-recommended-bump": "^6.1.0", + "fs-extra": "^9.1.0", + "get-stream": "^6.0.0", + "npm-package-arg": "8.1.1", + "npmlog": "^6.0.2", + "pify": "^5.0.0", + "semver": "^7.3.4" + } + }, + "@lerna/create": { + "version": "5.6.2", + "resolved": "https://registry.npmjs.org/@lerna/create/-/create-5.6.2.tgz", + "integrity": "sha512-+Y5cMUxMNXjTTU9IHpgRYIwKo39w+blui1P+s+qYlZUSCUAew0xNpOBG8iN0Nc5X9op4U094oIdHxv7Dyz6tWQ==", + "dev": true, + "requires": { + "@lerna/child-process": "5.6.2", + "@lerna/command": "5.6.2", + "@lerna/npm-conf": "5.6.2", + "@lerna/validation-error": "5.6.2", + "dedent": "^0.7.0", + "fs-extra": "^9.1.0", + "init-package-json": "^3.0.2", + "npm-package-arg": "8.1.1", + "p-reduce": "^2.1.0", + "pacote": "^13.6.1", + "pify": "^5.0.0", + "semver": "^7.3.4", + "slash": "^3.0.0", + "validate-npm-package-license": "^3.0.4", + "validate-npm-package-name": "^4.0.0", + "yargs-parser": "20.2.4" + }, + "dependencies": { + "yargs-parser": { + "version": "20.2.4", + "resolved": "https://registry.npmjs.org/yargs-parser/-/yargs-parser-20.2.4.tgz", + "integrity": "sha512-WOkpgNhPTlE73h4VFAFsOnomJVaovO8VqLDzy5saChRBFQFBoMYirowyW+Q9HB4HFF4Z7VZTiG3iSzJJA29yRA==", + "dev": true + } + } + }, + "@lerna/create-symlink": { + "version": "5.6.2", + "resolved": "https://registry.npmjs.org/@lerna/create-symlink/-/create-symlink-5.6.2.tgz", + "integrity": "sha512-0WIs3P6ohPVh2+t5axrLZDE5Dt7fe3Kv0Auj0sBiBd6MmKZ2oS76apIl0Bspdbv8jX8+TRKGv6ib0280D0dtEw==", + "dev": true, + "requires": { + "cmd-shim": "^5.0.0", + "fs-extra": "^9.1.0", + "npmlog": "^6.0.2" + } + }, + "@lerna/describe-ref": { + "version": "5.6.2", + "resolved": "https://registry.npmjs.org/@lerna/describe-ref/-/describe-ref-5.6.2.tgz", + "integrity": "sha512-UqU0N77aT1W8duYGir7R+Sk3jsY/c4lhcCEcnayMpFScMbAp0ETGsW04cYsHK29sgg+ZCc5zEwebBqabWhMhnA==", + "dev": true, + "requires": { + "@lerna/child-process": "5.6.2", + "npmlog": "^6.0.2" + } + }, + "@lerna/diff": { + "version": "5.6.2", + "resolved": "https://registry.npmjs.org/@lerna/diff/-/diff-5.6.2.tgz", + "integrity": "sha512-aHKzKvUvUI8vOcshC2Za/bdz+plM3r/ycqUrPqaERzp+kc1pYHyPeXezydVdEmgmmwmyKI5hx4+2QNnzOnun2A==", + "dev": true, + "requires": { + "@lerna/child-process": "5.6.2", + "@lerna/command": "5.6.2", + "@lerna/validation-error": "5.6.2", + "npmlog": "^6.0.2" + } + }, + "@lerna/exec": { + "version": "5.6.2", + "resolved": "https://registry.npmjs.org/@lerna/exec/-/exec-5.6.2.tgz", + "integrity": "sha512-meZozok5stK7S0oAVn+kdbTmU+kHj9GTXjW7V8kgwG9ld+JJMTH3nKK1L3mEKyk9TFu9vFWyEOF7HNK6yEOoVg==", + "dev": true, + "requires": { + "@lerna/child-process": "5.6.2", + "@lerna/command": "5.6.2", + "@lerna/filter-options": "5.6.2", + "@lerna/profiler": "5.6.2", + "@lerna/run-topologically": "5.6.2", + "@lerna/validation-error": "5.6.2", + "p-map": "^4.0.0" + } + }, + "@lerna/filter-options": { + "version": "5.6.2", + "resolved": "https://registry.npmjs.org/@lerna/filter-options/-/filter-options-5.6.2.tgz", + "integrity": "sha512-4Z0HIhPak2TabTsUqEBQaQeOqgqEt0qyskvsY0oviYvqP/nrJfJBZh4H93jIiNQF59LJCn5Ce3KJJrLExxjlzw==", + "dev": true, + "requires": { + "@lerna/collect-updates": "5.6.2", + "@lerna/filter-packages": "5.6.2", + "dedent": "^0.7.0", + "npmlog": "^6.0.2" + } + }, + "@lerna/filter-packages": { + "version": "5.6.2", + "resolved": "https://registry.npmjs.org/@lerna/filter-packages/-/filter-packages-5.6.2.tgz", + "integrity": "sha512-el9V2lTEG0Bbz+Omo45hATkRVnChCTJhcTpth19cMJ6mQ4M5H4IgbWCJdFMBi/RpTnOhz9BhJxDbj95kuIvvzw==", + "dev": true, + "requires": { + "@lerna/validation-error": "5.6.2", + "multimatch": "^5.0.0", + "npmlog": "^6.0.2" + } + }, + "@lerna/get-npm-exec-opts": { + "version": "5.6.2", + "resolved": "https://registry.npmjs.org/@lerna/get-npm-exec-opts/-/get-npm-exec-opts-5.6.2.tgz", + "integrity": "sha512-0RbSDJ+QC9D5UWZJh3DN7mBIU1NhBmdHOE289oHSkjDY+uEjdzMPkEUy+wZ8fCzMLFnnNQkAEqNaOAzZ7dmFLA==", + "dev": true, + "requires": { + "npmlog": "^6.0.2" + } + }, + "@lerna/get-packed": { + "version": "5.6.2", + "resolved": "https://registry.npmjs.org/@lerna/get-packed/-/get-packed-5.6.2.tgz", + "integrity": "sha512-pp5nNDmtrtd21aKHjwwOY5CS7XNIHxINzGa+Jholn1jMDYUtdskpN++ZqYbATGpW831++NJuiuBVyqAWi9xbXg==", + "dev": true, + "requires": { + "fs-extra": "^9.1.0", + "ssri": "^9.0.1", + "tar": "^6.1.0" + } + }, + "@lerna/github-client": { + "version": "5.6.2", + "resolved": "https://registry.npmjs.org/@lerna/github-client/-/github-client-5.6.2.tgz", + "integrity": "sha512-pjALazZoRZtKqfwLBwmW3HPptVhQm54PvA8s3qhCQ+3JkqrZiIFwkkxNZxs3jwzr+aaSOzfhSzCndg0urb0GXA==", + "dev": true, + "requires": { + "@lerna/child-process": "5.6.2", + "@octokit/plugin-enterprise-rest": "^6.0.1", + "@octokit/rest": "^19.0.3", + "git-url-parse": "^13.1.0", + "npmlog": "^6.0.2" + } + }, + "@lerna/gitlab-client": { + "version": "5.6.2", + "resolved": "https://registry.npmjs.org/@lerna/gitlab-client/-/gitlab-client-5.6.2.tgz", + "integrity": "sha512-TInJmbrsmYIwUyrRxytjO82KjJbRwm67F7LoZs1shAq6rMvNqi4NxSY9j+hT/939alFmEq1zssoy/caeLXHRfQ==", + "dev": true, + "requires": { + "node-fetch": "^2.6.1", + "npmlog": "^6.0.2" + } + }, + "@lerna/global-options": { + "version": "5.6.2", + "resolved": "https://registry.npmjs.org/@lerna/global-options/-/global-options-5.6.2.tgz", + "integrity": "sha512-kaKELURXTlczthNJskdOvh6GGMyt24qat0xMoJZ8plYMdofJfhz24h1OFcvB/EwCUwP/XV1+ohE5P+vdktbrEg==", + "dev": true + }, + "@lerna/has-npm-version": { + "version": "5.6.2", + "resolved": "https://registry.npmjs.org/@lerna/has-npm-version/-/has-npm-version-5.6.2.tgz", + "integrity": "sha512-kXCnSzffmTWsaK0ol30coyCfO8WH26HFbmJjRBzKv7VGkuAIcB6gX2gqRRgNLLlvI+Yrp+JSlpVNVnu15SEH2g==", + "dev": true, + "requires": { + "@lerna/child-process": "5.6.2", + "semver": "^7.3.4" + } + }, + "@lerna/import": { + "version": "5.6.2", + "resolved": "https://registry.npmjs.org/@lerna/import/-/import-5.6.2.tgz", + "integrity": "sha512-xQUE49mtcP0z3KUdXBsyvp8rGDz6phuYUoQbhcFRJ7WPcQKzMvtm0XYrER6c2YWEX7QOuDac6tU82P8zTrTBaA==", + "dev": true, + "requires": { + "@lerna/child-process": "5.6.2", + "@lerna/command": "5.6.2", + "@lerna/prompt": "5.6.2", + "@lerna/pulse-till-done": "5.6.2", + "@lerna/validation-error": "5.6.2", + "dedent": "^0.7.0", + "fs-extra": "^9.1.0", + "p-map-series": "^2.1.0" + } + }, + "@lerna/info": { + "version": "5.6.2", + "resolved": "https://registry.npmjs.org/@lerna/info/-/info-5.6.2.tgz", + "integrity": "sha512-MPjY5Olj+fiZHgfEdwXUFRKamdEuLr9Ob/qut8JsB/oQSQ4ALdQfnrOcMT8lJIcC2R67EA5yav2lHPBIkezm8A==", + "dev": true, + "requires": { + "@lerna/command": "5.6.2", + "@lerna/output": "5.6.2", + "envinfo": "^7.7.4" + } + }, + "@lerna/init": { + "version": "5.6.2", + "resolved": "https://registry.npmjs.org/@lerna/init/-/init-5.6.2.tgz", + "integrity": "sha512-ahU3/lgF+J8kdJAQysihFJROHthkIDXfHmvhw7AYnzf94HjxGNXj7nz6i3At1/dM/1nQhR+4/uNR1/OU4tTYYQ==", + "dev": true, + "requires": { + "@lerna/child-process": "5.6.2", + "@lerna/command": "5.6.2", + "@lerna/project": "5.6.2", + "fs-extra": "^9.1.0", + "p-map": "^4.0.0", + "write-json-file": "^4.3.0" + } + }, + "@lerna/link": { + "version": "5.6.2", + "resolved": "https://registry.npmjs.org/@lerna/link/-/link-5.6.2.tgz", + "integrity": "sha512-hXxQ4R3z6rUF1v2x62oIzLyeHL96u7ZBhxqYMJrm763D1VMSDcHKF9CjJfc6J9vH5Z2ZbL6CQg50Hw5mUpJbjg==", + "dev": true, + "requires": { + "@lerna/command": "5.6.2", + "@lerna/package-graph": "5.6.2", + "@lerna/symlink-dependencies": "5.6.2", + "@lerna/validation-error": "5.6.2", + "p-map": "^4.0.0", + "slash": "^3.0.0" + } + }, + "@lerna/list": { + "version": "5.6.2", + "resolved": "https://registry.npmjs.org/@lerna/list/-/list-5.6.2.tgz", + "integrity": "sha512-WjE5O2tQ3TcS+8LqXUaxi0YdldhxUhNihT5+Gg4vzGdIlrPDioO50Zjo9d8jOU7i3LMIk6EzCma0sZr2CVfEGg==", + "dev": true, + "requires": { + "@lerna/command": "5.6.2", + "@lerna/filter-options": "5.6.2", + "@lerna/listable": "5.6.2", + "@lerna/output": "5.6.2" + } + }, + "@lerna/listable": { + "version": "5.6.2", + "resolved": "https://registry.npmjs.org/@lerna/listable/-/listable-5.6.2.tgz", + "integrity": "sha512-8Yp49BwkY/5XqVru38Zko+6Wj/sgbwzJfIGEPy3Qu575r1NA/b9eI1gX22aMsEeXUeGOybR7nWT5ewnPQHjqvA==", + "dev": true, + "requires": { + "@lerna/query-graph": "5.6.2", + "chalk": "^4.1.0", + "columnify": "^1.6.0" + } + }, + "@lerna/log-packed": { + "version": "5.6.2", + "resolved": "https://registry.npmjs.org/@lerna/log-packed/-/log-packed-5.6.2.tgz", + "integrity": "sha512-O9GODG7tMtWk+2fufn2MOkIDBYMRoKBhYMHshO5Aw/VIsH76DIxpX1koMzWfUngM/C70R4uNAKcVWineX4qzIw==", + "dev": true, + "requires": { + "byte-size": "^7.0.0", + "columnify": "^1.6.0", + "has-unicode": "^2.0.1", + "npmlog": "^6.0.2" + } + }, + "@lerna/npm-conf": { + "version": "5.6.2", + "resolved": "https://registry.npmjs.org/@lerna/npm-conf/-/npm-conf-5.6.2.tgz", + "integrity": "sha512-gWDPhw1wjXYXphk/PAghTLexO5T6abVFhXb+KOMCeem366mY0F5bM88PiorL73aErTNUoR8n+V4X29NTZzDZpQ==", + "dev": true, + "requires": { + "config-chain": "^1.1.12", + "pify": "^5.0.0" + } + }, + "@lerna/npm-dist-tag": { + "version": "5.6.2", + "resolved": "https://registry.npmjs.org/@lerna/npm-dist-tag/-/npm-dist-tag-5.6.2.tgz", + "integrity": "sha512-t2RmxV6Eog4acXkUI+EzWuYVbeVVY139pANIWS9qtdajfgp4GVXZi1S8mAIb70yeHdNpCp1mhK0xpCrFH9LvGQ==", + "dev": true, + "requires": { + "@lerna/otplease": "5.6.2", + "npm-package-arg": "8.1.1", + "npm-registry-fetch": "^13.3.0", + "npmlog": "^6.0.2" + } + }, + "@lerna/npm-install": { + "version": "5.6.2", + "resolved": "https://registry.npmjs.org/@lerna/npm-install/-/npm-install-5.6.2.tgz", + "integrity": "sha512-AT226zdEo+uGENd37jwYgdALKJAIJK4pNOfmXWZWzVb9oMOr8I2YSjPYvSYUNG7gOo2YJQU8x5Zd7OShv2924Q==", + "dev": true, + "requires": { + "@lerna/child-process": "5.6.2", + "@lerna/get-npm-exec-opts": "5.6.2", + "fs-extra": "^9.1.0", + "npm-package-arg": "8.1.1", + "npmlog": "^6.0.2", + "signal-exit": "^3.0.3", + "write-pkg": "^4.0.0" + } + }, + "@lerna/npm-publish": { + "version": "5.6.2", + "resolved": "https://registry.npmjs.org/@lerna/npm-publish/-/npm-publish-5.6.2.tgz", + "integrity": "sha512-ldSyewCfv9fAeC5xNjL0HKGSUxcC048EJoe/B+KRUmd+IPidvZxMEzRu08lSC/q3V9YeUv9ZvRnxATXOM8CffA==", + "dev": true, + "requires": { + "@lerna/otplease": "5.6.2", + "@lerna/run-lifecycle": "5.6.2", + "fs-extra": "^9.1.0", + "libnpmpublish": "^6.0.4", + "npm-package-arg": "8.1.1", + "npmlog": "^6.0.2", + "pify": "^5.0.0", + "read-package-json": "^5.0.1" + } + }, + "@lerna/npm-run-script": { + "version": "5.6.2", + "resolved": "https://registry.npmjs.org/@lerna/npm-run-script/-/npm-run-script-5.6.2.tgz", + "integrity": "sha512-MOQoWNcAyJivM8SYp0zELM7vg/Dj07j4YMdxZkey+S1UO0T4/vKBxb575o16hH4WeNzC3Pd7WBlb7C8dLOfNwQ==", + "dev": true, + "requires": { + "@lerna/child-process": "5.6.2", + "@lerna/get-npm-exec-opts": "5.6.2", + "npmlog": "^6.0.2" + } + }, + "@lerna/otplease": { + "version": "5.6.2", + "resolved": "https://registry.npmjs.org/@lerna/otplease/-/otplease-5.6.2.tgz", + "integrity": "sha512-dGS4lzkEQVTMAgji82jp8RK6UK32wlzrBAO4P4iiVHCUTuwNLsY9oeBXvVXSMrosJnl6Hbe0NOvi43mqSucGoA==", + "dev": true, + "requires": { + "@lerna/prompt": "5.6.2" + } + }, + "@lerna/output": { + "version": "5.6.2", + "resolved": "https://registry.npmjs.org/@lerna/output/-/output-5.6.2.tgz", + "integrity": "sha512-++d+bfOQwY66yo7q1XuAvRcqtRHCG45e/awP5xQomTZ6R1rhWiZ3whWdc9Z6lF7+UtBB9toSYYffKU/xc3L0yQ==", + "dev": true, + "requires": { + "npmlog": "^6.0.2" + } + }, + "@lerna/pack-directory": { + "version": "5.6.2", + "resolved": "https://registry.npmjs.org/@lerna/pack-directory/-/pack-directory-5.6.2.tgz", + "integrity": "sha512-w5Jk5fo+HkN4Le7WMOudTcmAymcf0xPd302TqAQncjXpk0cb8tZbj+5bbNHsGb58GRjOIm5icQbHXooQUxbHhA==", + "dev": true, + "requires": { + "@lerna/get-packed": "5.6.2", + "@lerna/package": "5.6.2", + "@lerna/run-lifecycle": "5.6.2", + "@lerna/temp-write": "5.6.2", + "npm-packlist": "^5.1.1", + "npmlog": "^6.0.2", + "tar": "^6.1.0" + } + }, + "@lerna/package": { + "version": "5.6.2", + "resolved": "https://registry.npmjs.org/@lerna/package/-/package-5.6.2.tgz", + "integrity": "sha512-LaOC8moyM5J9WnRiWZkedjOninSclBOJyPqhif6mHb2kCFX6jAroNYzE8KM4cphu8CunHuhI6Ixzswtv+Dultw==", + "dev": true, + "requires": { + "load-json-file": "^6.2.0", + "npm-package-arg": "8.1.1", + "write-pkg": "^4.0.0" + } + }, + "@lerna/package-graph": { + "version": "5.6.2", + "resolved": "https://registry.npmjs.org/@lerna/package-graph/-/package-graph-5.6.2.tgz", + "integrity": "sha512-TmL61qBBvA3Tc4qICDirZzdFFwWOA6qicIXUruLiE2PblRowRmCO1bKrrP6XbDOspzwrkPef6N2F2/5gHQAnkQ==", + "dev": true, + "requires": { + "@lerna/prerelease-id-from-version": "5.6.2", + "@lerna/validation-error": "5.6.2", + "npm-package-arg": "8.1.1", + "npmlog": "^6.0.2", + "semver": "^7.3.4" + } + }, + "@lerna/prerelease-id-from-version": { + "version": "5.6.2", + "resolved": "https://registry.npmjs.org/@lerna/prerelease-id-from-version/-/prerelease-id-from-version-5.6.2.tgz", + "integrity": "sha512-7gIm9fecWFVNy2kpj/KbH11bRcpyANAwpsft3X5m6J7y7A6FTUscCbEvl3ZNdpQKHNuvnHgCtkm3A5PMSCEgkA==", + "dev": true, + "requires": { + "semver": "^7.3.4" + } + }, + "@lerna/profiler": { + "version": "5.6.2", + "resolved": "https://registry.npmjs.org/@lerna/profiler/-/profiler-5.6.2.tgz", + "integrity": "sha512-okwkagP5zyRIOYTceu/9/esW7UZFt7lyL6q6ZgpSG3TYC5Ay+FXLtS6Xiha/FQdVdumFqKULDWTGovzUlxcwaw==", + "dev": true, + "requires": { + "fs-extra": "^9.1.0", + "npmlog": "^6.0.2", + "upath": "^2.0.1" + } + }, + "@lerna/project": { + "version": "5.6.2", + "resolved": "https://registry.npmjs.org/@lerna/project/-/project-5.6.2.tgz", + "integrity": "sha512-kPIMcIy/0DVWM91FPMMFmXyAnCuuLm3NdhnA8NusE//VuY9wC6QC/3OwuCY39b2dbko/fPZheqKeAZkkMH6sGg==", + "dev": true, + "requires": { + "@lerna/package": "5.6.2", + "@lerna/validation-error": "5.6.2", + "cosmiconfig": "^7.0.0", + "dedent": "^0.7.0", + "dot-prop": "^6.0.1", + "glob-parent": "^5.1.1", + "globby": "^11.0.2", + "js-yaml": "^4.1.0", + "load-json-file": "^6.2.0", + "npmlog": "^6.0.2", + "p-map": "^4.0.0", + "resolve-from": "^5.0.0", + "write-json-file": "^4.3.0" + }, + "dependencies": { + "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, + "requires": { + "is-glob": "^4.0.1" + } + }, + "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 + } + } + }, + "@lerna/prompt": { + "version": "5.6.2", + "resolved": "https://registry.npmjs.org/@lerna/prompt/-/prompt-5.6.2.tgz", + "integrity": "sha512-4hTNmVYADEr0GJTMegWV+GW6n+dzKx1vN9v2ISqyle283Myv930WxuyO0PeYGqTrkneJsyPreCMovuEGCvZ0iQ==", + "dev": true, + "requires": { + "inquirer": "^8.2.4", + "npmlog": "^6.0.2" + } + }, + "@lerna/publish": { + "version": "5.6.2", + "resolved": "https://registry.npmjs.org/@lerna/publish/-/publish-5.6.2.tgz", + "integrity": "sha512-QaW0GjMJMuWlRNjeDCjmY/vjriGSWgkLS23yu8VKNtV5U3dt5yIKA3DNGV3HgZACuu45kQxzMDsfLzgzbGNtYA==", + "dev": true, + "requires": { + "@lerna/check-working-tree": "5.6.2", + "@lerna/child-process": "5.6.2", + "@lerna/collect-updates": "5.6.2", + "@lerna/command": "5.6.2", + "@lerna/describe-ref": "5.6.2", + "@lerna/log-packed": "5.6.2", + "@lerna/npm-conf": "5.6.2", + "@lerna/npm-dist-tag": "5.6.2", + "@lerna/npm-publish": "5.6.2", + "@lerna/otplease": "5.6.2", + "@lerna/output": "5.6.2", + "@lerna/pack-directory": "5.6.2", + "@lerna/prerelease-id-from-version": "5.6.2", + "@lerna/prompt": "5.6.2", + "@lerna/pulse-till-done": "5.6.2", + "@lerna/run-lifecycle": "5.6.2", + "@lerna/run-topologically": "5.6.2", + "@lerna/validation-error": "5.6.2", + "@lerna/version": "5.6.2", + "fs-extra": "^9.1.0", + "libnpmaccess": "^6.0.3", + "npm-package-arg": "8.1.1", + "npm-registry-fetch": "^13.3.0", + "npmlog": "^6.0.2", + "p-map": "^4.0.0", + "p-pipe": "^3.1.0", + "pacote": "^13.6.1", + "semver": "^7.3.4" + } + }, + "@lerna/pulse-till-done": { + "version": "5.6.2", + "resolved": "https://registry.npmjs.org/@lerna/pulse-till-done/-/pulse-till-done-5.6.2.tgz", + "integrity": "sha512-eA/X1RCxU5YGMNZmbgPi+Kyfx1Q3bn4P9jo/LZy+/NRRr1po3ASXP2GJZ1auBh/9A2ELDvvKTOXCVHqczKC6rA==", + "dev": true, + "requires": { + "npmlog": "^6.0.2" + } + }, + "@lerna/query-graph": { + "version": "5.6.2", + "resolved": "https://registry.npmjs.org/@lerna/query-graph/-/query-graph-5.6.2.tgz", + "integrity": "sha512-KRngr96yBP8XYDi9/U62fnGO+ZXqm04Qk6a2HtoTr/ha8QvO1s7Tgm0xs/G7qWXDQHZgunWIbmK/LhxM7eFQrw==", + "dev": true, + "requires": { + "@lerna/package-graph": "5.6.2" + } + }, + "@lerna/resolve-symlink": { + "version": "5.6.2", + "resolved": "https://registry.npmjs.org/@lerna/resolve-symlink/-/resolve-symlink-5.6.2.tgz", + "integrity": "sha512-PDQy+7M8JEFtwIVHJgWvSxHkxJf9zXCENkvIWDB+SsoDPhw9+caewt46bTeP5iGm9pOMu3oZukaWo/TvF7sNjg==", + "dev": true, + "requires": { + "fs-extra": "^9.1.0", + "npmlog": "^6.0.2", + "read-cmd-shim": "^3.0.0" + } + }, + "@lerna/rimraf-dir": { + "version": "5.6.2", + "resolved": "https://registry.npmjs.org/@lerna/rimraf-dir/-/rimraf-dir-5.6.2.tgz", + "integrity": "sha512-jgEfzz7uBUiQKteq3G8MtJiA2D2VoKmZSSY3VSiW/tPOSXYxxSHxEsClQdCeNa6+sYrDNDT8fP6MJ3lPLjDeLA==", + "dev": true, + "requires": { + "@lerna/child-process": "5.6.2", + "npmlog": "^6.0.2", + "path-exists": "^4.0.0", + "rimraf": "^3.0.2" + } + }, + "@lerna/run": { + "version": "5.6.2", + "resolved": "https://registry.npmjs.org/@lerna/run/-/run-5.6.2.tgz", + "integrity": "sha512-c2kJxdFrNg5KOkrhmgwKKUOsfSrGNlFCe26EttufOJ3xfY0VnXlEw9rHOkTgwtu7969rfCdyaVP1qckMrF1Dgw==", + "dev": true, + "requires": { + "@lerna/command": "5.6.2", + "@lerna/filter-options": "5.6.2", + "@lerna/npm-run-script": "5.6.2", + "@lerna/output": "5.6.2", + "@lerna/profiler": "5.6.2", + "@lerna/run-topologically": "5.6.2", + "@lerna/timer": "5.6.2", + "@lerna/validation-error": "5.6.2", + "fs-extra": "^9.1.0", + "p-map": "^4.0.0" + } + }, + "@lerna/run-lifecycle": { + "version": "5.6.2", + "resolved": "https://registry.npmjs.org/@lerna/run-lifecycle/-/run-lifecycle-5.6.2.tgz", + "integrity": "sha512-u9gGgq/50Fm8dvfcc/TSHOCAQvzLD7poVanDMhHYWOAqRDnellJEEmA1K/Yka4vZmySrzluahkry9G6jcREt+g==", + "dev": true, + "requires": { + "@lerna/npm-conf": "5.6.2", + "@npmcli/run-script": "^4.1.7", + "npmlog": "^6.0.2", + "p-queue": "^6.6.2" + } + }, + "@lerna/run-topologically": { + "version": "5.6.2", + "resolved": "https://registry.npmjs.org/@lerna/run-topologically/-/run-topologically-5.6.2.tgz", + "integrity": "sha512-QQ/jGOIsVvUg3izShWsd67RlWYh9UOH2yw97Ol1zySX9+JspCMVQrn9eKq1Pk8twQOFhT87LpT/aaxbTBgREPw==", + "dev": true, + "requires": { + "@lerna/query-graph": "5.6.2", + "p-queue": "^6.6.2" + } + }, + "@lerna/symlink-binary": { + "version": "5.6.2", + "resolved": "https://registry.npmjs.org/@lerna/symlink-binary/-/symlink-binary-5.6.2.tgz", + "integrity": "sha512-Cth+miwYyO81WAmrQbPBrLHuF+F0UUc0el5kRXLH6j5zzaRS3kMM68r40M7MmfH8m3GPi7691UARoWFEotW5jw==", + "dev": true, + "requires": { + "@lerna/create-symlink": "5.6.2", + "@lerna/package": "5.6.2", + "fs-extra": "^9.1.0", + "p-map": "^4.0.0" + } + }, + "@lerna/symlink-dependencies": { + "version": "5.6.2", + "resolved": "https://registry.npmjs.org/@lerna/symlink-dependencies/-/symlink-dependencies-5.6.2.tgz", + "integrity": "sha512-dUVNQLEcjVOIQiT9OlSAKt0ykjyJPy8l9i4NJDe2/0XYaUjo8PWsxJ0vrutz27jzi2aZUy07ASmowQZEmnLHAw==", + "dev": true, + "requires": { + "@lerna/create-symlink": "5.6.2", + "@lerna/resolve-symlink": "5.6.2", + "@lerna/symlink-binary": "5.6.2", + "fs-extra": "^9.1.0", + "p-map": "^4.0.0", + "p-map-series": "^2.1.0" + } + }, + "@lerna/temp-write": { + "version": "5.6.2", + "resolved": "https://registry.npmjs.org/@lerna/temp-write/-/temp-write-5.6.2.tgz", + "integrity": "sha512-S5ZNVTurSwWBmc9kh5alfSjmO3+BnRT6shYtOlmVIUYqWeYVYA5C1Htj322bbU4CSNCMFK6NQl4qGKL17HMuig==", + "dev": true, + "requires": { + "graceful-fs": "^4.1.15", + "is-stream": "^2.0.0", + "make-dir": "^3.0.0", + "temp-dir": "^1.0.0", + "uuid": "^8.3.2" + }, + "dependencies": { + "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 + } + } + }, + "@lerna/timer": { + "version": "5.6.2", + "resolved": "https://registry.npmjs.org/@lerna/timer/-/timer-5.6.2.tgz", + "integrity": "sha512-AjMOiLc2B+5Nzdd9hNORetAdZ/WK8YNGX/+2ypzM68TMAPfIT5C40hMlSva9Yg4RsBz22REopXgM5s2zQd5ZQA==", + "dev": true + }, + "@lerna/validation-error": { + "version": "5.6.2", + "resolved": "https://registry.npmjs.org/@lerna/validation-error/-/validation-error-5.6.2.tgz", + "integrity": "sha512-4WlDUHaa+RSJNyJRtX3gVIAPVzjZD2tle8AJ0ZYBfdZnZmG0VlB2pD1FIbOQPK8sY2h5m0cHLRvfLoLncqHvdQ==", + "dev": true, + "requires": { + "npmlog": "^6.0.2" + } + }, + "@lerna/version": { + "version": "5.6.2", + "resolved": "https://registry.npmjs.org/@lerna/version/-/version-5.6.2.tgz", + "integrity": "sha512-odNSR2rTbHW++xMZSQKu/F6Syrd/sUvwDLPaMKktoOSPKmycHt/eWcuQQyACdtc43Iqeu4uQd7PCLsniqOVFrw==", + "dev": true, + "requires": { + "@lerna/check-working-tree": "5.6.2", + "@lerna/child-process": "5.6.2", + "@lerna/collect-updates": "5.6.2", + "@lerna/command": "5.6.2", + "@lerna/conventional-commits": "5.6.2", + "@lerna/github-client": "5.6.2", + "@lerna/gitlab-client": "5.6.2", + "@lerna/output": "5.6.2", + "@lerna/prerelease-id-from-version": "5.6.2", + "@lerna/prompt": "5.6.2", + "@lerna/run-lifecycle": "5.6.2", + "@lerna/run-topologically": "5.6.2", + "@lerna/temp-write": "5.6.2", + "@lerna/validation-error": "5.6.2", + "@nrwl/devkit": ">=14.8.1 < 16", + "chalk": "^4.1.0", + "dedent": "^0.7.0", + "load-json-file": "^6.2.0", + "minimatch": "^3.0.4", + "npmlog": "^6.0.2", + "p-map": "^4.0.0", + "p-pipe": "^3.1.0", + "p-reduce": "^2.1.0", + "p-waterfall": "^2.1.1", + "semver": "^7.3.4", + "slash": "^3.0.0", + "write-json-file": "^4.3.0" + } + }, + "@lerna/write-log-file": { + "version": "5.6.2", + "resolved": "https://registry.npmjs.org/@lerna/write-log-file/-/write-log-file-5.6.2.tgz", + "integrity": "sha512-J09l18QnWQ3sXIRwuJkjXY3+KwPR2uO5NgbZGE3GXJK1V/LzOBRMvjGAIbuQHXw25uqe7vpLUpB8drtnFrubCQ==", + "dev": true, + "requires": { + "npmlog": "^6.0.2", + "write-file-atomic": "^4.0.1" + } + }, + "@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, + "requires": { + "@nodelib/fs.stat": "2.0.5", + "run-parallel": "^1.1.9" + } + }, + "@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 + }, + "@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, + "requires": { + "@nodelib/fs.scandir": "2.1.5", + "fastq": "^1.6.0" + } + }, + "@npmcli/arborist": { + "version": "5.3.0", + "resolved": "https://registry.npmjs.org/@npmcli/arborist/-/arborist-5.3.0.tgz", + "integrity": "sha512-+rZ9zgL1lnbl8Xbb1NQdMjveOMwj4lIYfcDtyJHHi5x4X8jtR6m8SXooJMZy5vmFVZ8w7A2Bnd/oX9eTuU8w5A==", + "dev": true, + "requires": { + "@isaacs/string-locale-compare": "^1.1.0", + "@npmcli/installed-package-contents": "^1.0.7", + "@npmcli/map-workspaces": "^2.0.3", + "@npmcli/metavuln-calculator": "^3.0.1", + "@npmcli/move-file": "^2.0.0", + "@npmcli/name-from-folder": "^1.0.1", + "@npmcli/node-gyp": "^2.0.0", + "@npmcli/package-json": "^2.0.0", + "@npmcli/run-script": "^4.1.3", + "bin-links": "^3.0.0", + "cacache": "^16.0.6", + "common-ancestor-path": "^1.0.1", + "json-parse-even-better-errors": "^2.3.1", + "json-stringify-nice": "^1.1.4", + "mkdirp": "^1.0.4", + "mkdirp-infer-owner": "^2.0.0", + "nopt": "^5.0.0", + "npm-install-checks": "^5.0.0", + "npm-package-arg": "^9.0.0", + "npm-pick-manifest": "^7.0.0", + "npm-registry-fetch": "^13.0.0", + "npmlog": "^6.0.2", + "pacote": "^13.6.1", + "parse-conflict-json": "^2.0.1", + "proc-log": "^2.0.0", + "promise-all-reject-late": "^1.0.0", + "promise-call-limit": "^1.0.1", + "read-package-json-fast": "^2.0.2", + "readdir-scoped-modules": "^1.1.0", + "rimraf": "^3.0.2", + "semver": "^7.3.7", + "ssri": "^9.0.0", + "treeverse": "^2.0.0", + "walk-up-path": "^1.0.0" + }, + "dependencies": { + "hosted-git-info": { + "version": "5.1.0", + "resolved": "https://registry.npmjs.org/hosted-git-info/-/hosted-git-info-5.1.0.tgz", + "integrity": "sha512-Ek+QmMEqZF8XrbFdwoDjSbm7rT23pCgEMOJmz6GPk/s4yH//RQfNPArhIxbguNxROq/+5lNBwCDHMhA903Kx1Q==", + "dev": true, + "requires": { + "lru-cache": "^7.5.1" + } + }, + "npm-package-arg": { + "version": "9.1.2", + "resolved": "https://registry.npmjs.org/npm-package-arg/-/npm-package-arg-9.1.2.tgz", + "integrity": "sha512-pzd9rLEx4TfNJkovvlBSLGhq31gGu2QDexFPWT19yCDh0JgnRhlBLNo5759N0AJmBk+kQ9Y/hXoLnlgFD+ukmg==", + "dev": true, + "requires": { + "hosted-git-info": "^5.0.0", + "proc-log": "^2.0.1", + "semver": "^7.3.5", + "validate-npm-package-name": "^4.0.0" + } + } + } + }, + "@npmcli/fs": { + "version": "2.1.2", + "resolved": "https://registry.npmjs.org/@npmcli/fs/-/fs-2.1.2.tgz", + "integrity": "sha512-yOJKRvohFOaLqipNtwYB9WugyZKhC/DZC4VYPmpaCzDBrA8YpK3qHZ8/HGscMnE4GqbkLNuVcCnxkeQEdGt6LQ==", + "dev": true, + "requires": { + "@gar/promisify": "^1.1.3", + "semver": "^7.3.5" + } + }, + "@npmcli/git": { + "version": "3.0.2", + "resolved": "https://registry.npmjs.org/@npmcli/git/-/git-3.0.2.tgz", + "integrity": "sha512-CAcd08y3DWBJqJDpfuVL0uijlq5oaXaOJEKHKc4wqrjd00gkvTZB+nFuLn+doOOKddaQS9JfqtNoFCO2LCvA3w==", + "dev": true, + "requires": { + "@npmcli/promise-spawn": "^3.0.0", + "lru-cache": "^7.4.4", + "mkdirp": "^1.0.4", + "npm-pick-manifest": "^7.0.0", + "proc-log": "^2.0.0", + "promise-inflight": "^1.0.1", + "promise-retry": "^2.0.1", + "semver": "^7.3.5", + "which": "^2.0.2" + } + }, + "@npmcli/installed-package-contents": { + "version": "1.0.7", + "resolved": "https://registry.npmjs.org/@npmcli/installed-package-contents/-/installed-package-contents-1.0.7.tgz", + "integrity": "sha512-9rufe0wnJusCQoLpV9ZPKIVP55itrM5BxOXs10DmdbRfgWtHy1LDyskbwRnBghuB0PrF7pNPOqREVtpz4HqzKw==", + "dev": true, + "requires": { + "npm-bundled": "^1.1.1", + "npm-normalize-package-bin": "^1.0.1" + } + }, + "@npmcli/map-workspaces": { + "version": "2.0.4", + "resolved": "https://registry.npmjs.org/@npmcli/map-workspaces/-/map-workspaces-2.0.4.tgz", + "integrity": "sha512-bMo0aAfwhVwqoVM5UzX1DJnlvVvzDCHae821jv48L1EsrYwfOZChlqWYXEtto/+BkBXetPbEWgau++/brh4oVg==", + "dev": true, + "requires": { + "@npmcli/name-from-folder": "^1.0.1", + "glob": "^8.0.1", + "minimatch": "^5.0.1", + "read-package-json-fast": "^2.0.3" + }, + "dependencies": { + "brace-expansion": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/brace-expansion/-/brace-expansion-2.0.1.tgz", + "integrity": "sha512-XnAIvQ8eM+kC6aULx6wuQiwVsnzsi9d3WxzV3FpWTGA19F621kwdbsAcFKXgKUHZWsy+mY6iL1sHTxWEFCytDA==", + "dev": true, + "requires": { + "balanced-match": "^1.0.0" + } + }, + "minimatch": { + "version": "5.1.0", + "resolved": "https://registry.npmjs.org/minimatch/-/minimatch-5.1.0.tgz", + "integrity": "sha512-9TPBGGak4nHfGZsPBohm9AWg6NoT7QTCehS3BIJABslyZbzxfV78QM2Y6+i741OPZIafFAaiiEMh5OyIrJPgtg==", + "dev": true, + "requires": { + "brace-expansion": "^2.0.1" + } + } + } + }, + "@npmcli/metavuln-calculator": { + "version": "3.1.1", + "resolved": "https://registry.npmjs.org/@npmcli/metavuln-calculator/-/metavuln-calculator-3.1.1.tgz", + "integrity": "sha512-n69ygIaqAedecLeVH3KnO39M6ZHiJ2dEv5A7DGvcqCB8q17BGUgW8QaanIkbWUo2aYGZqJaOORTLAlIvKjNDKA==", + "dev": true, + "requires": { + "cacache": "^16.0.0", + "json-parse-even-better-errors": "^2.3.1", + "pacote": "^13.0.3", + "semver": "^7.3.5" + } + }, + "@npmcli/move-file": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/@npmcli/move-file/-/move-file-2.0.1.tgz", + "integrity": "sha512-mJd2Z5TjYWq/ttPLLGqArdtnC74J6bOzg4rMDnN+p1xTacZ2yPRCk2y0oSWQtygLR9YVQXgOcONrwtnk3JupxQ==", + "dev": true, + "requires": { + "mkdirp": "^1.0.4", + "rimraf": "^3.0.2" + } + }, + "@npmcli/name-from-folder": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/@npmcli/name-from-folder/-/name-from-folder-1.0.1.tgz", + "integrity": "sha512-qq3oEfcLFwNfEYOQ8HLimRGKlD8WSeGEdtUa7hmzpR8Sa7haL1KVQrvgO6wqMjhWFFVjgtrh1gIxDz+P8sjUaA==", + "dev": true + }, + "@npmcli/node-gyp": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/@npmcli/node-gyp/-/node-gyp-2.0.0.tgz", + "integrity": "sha512-doNI35wIe3bBaEgrlPfdJPaCpUR89pJWep4Hq3aRdh6gKazIVWfs0jHttvSSoq47ZXgC7h73kDsUl8AoIQUB+A==", + "dev": true + }, + "@npmcli/package-json": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/@npmcli/package-json/-/package-json-2.0.0.tgz", + "integrity": "sha512-42jnZ6yl16GzjWSH7vtrmWyJDGVa/LXPdpN2rcUWolFjc9ON2N3uz0qdBbQACfmhuJZ2lbKYtmK5qx68ZPLHMA==", + "dev": true, + "requires": { + "json-parse-even-better-errors": "^2.3.1" + } + }, + "@npmcli/promise-spawn": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/@npmcli/promise-spawn/-/promise-spawn-3.0.0.tgz", + "integrity": "sha512-s9SgS+p3a9Eohe68cSI3fi+hpcZUmXq5P7w0kMlAsWVtR7XbK3ptkZqKT2cK1zLDObJ3sR+8P59sJE0w/KTL1g==", + "dev": true, + "requires": { + "infer-owner": "^1.0.4" + } + }, + "@npmcli/run-script": { + "version": "4.2.1", + "resolved": "https://registry.npmjs.org/@npmcli/run-script/-/run-script-4.2.1.tgz", + "integrity": "sha512-7dqywvVudPSrRCW5nTHpHgeWnbBtz8cFkOuKrecm6ih+oO9ciydhWt6OF7HlqupRRmB8Q/gECVdB9LMfToJbRg==", + "dev": true, + "requires": { + "@npmcli/node-gyp": "^2.0.0", + "@npmcli/promise-spawn": "^3.0.0", + "node-gyp": "^9.0.0", + "read-package-json-fast": "^2.0.3", + "which": "^2.0.2" + } + }, + "@nrwl/cli": { + "version": "14.8.4", + "resolved": "https://registry.npmjs.org/@nrwl/cli/-/cli-14.8.4.tgz", + "integrity": "sha512-JBoMw1IUFbtahDWolv3iBWJyO3ZXHOsqUt2AvWSrKfteOCjhSfG9GdQYGlnV9ZpWAx4bDf4f7Xz5z6+DJuaONA==", + "dev": true, + "requires": { + "nx": "14.8.4" + } + }, + "@nrwl/devkit": { + "version": "14.8.4", + "resolved": "https://registry.npmjs.org/@nrwl/devkit/-/devkit-14.8.4.tgz", + "integrity": "sha512-GmHZ8SVE0aL4iRfkYRzzE5I09rl6MgHpLDkuGAYQOPLOm4REjZ5jFjoODS2M7AydrJ34JxAq9eAFXGFr4cKauA==", + "dev": true, + "requires": { + "@phenomnomnominal/tsquery": "4.1.1", + "ejs": "^3.1.7", + "ignore": "^5.0.4", + "tslib": "^2.3.0" + } + }, + "@nrwl/tao": { + "version": "14.8.4", + "resolved": "https://registry.npmjs.org/@nrwl/tao/-/tao-14.8.4.tgz", + "integrity": "sha512-wEDBELOYzfvp96xCnoWoMr4UA/e3cUri7kAXDGK3hrGGcCUplJ+notHiKJoZXmB3yHME2PMJca4dHcG4zVgA0w==", + "dev": true, + "requires": { + "nx": "14.8.4" + } + }, + "@octokit/auth-token": { + "version": "3.0.1", + "resolved": "https://registry.npmjs.org/@octokit/auth-token/-/auth-token-3.0.1.tgz", + "integrity": "sha512-/USkK4cioY209wXRpund6HZzHo9GmjakpV9ycOkpMcMxMk7QVcVFVyCMtzvXYiHsB2crgDgrtNYSELYFBXhhaA==", + "dev": true, + "requires": { + "@octokit/types": "^7.0.0" + } + }, + "@octokit/core": { + "version": "4.0.5", + "resolved": "https://registry.npmjs.org/@octokit/core/-/core-4.0.5.tgz", + "integrity": "sha512-4R3HeHTYVHCfzSAi0C6pbGXV8UDI5Rk+k3G7kLVNckswN9mvpOzW9oENfjfH3nEmzg8y3AmKmzs8Sg6pLCeOCA==", + "dev": true, + "requires": { + "@octokit/auth-token": "^3.0.0", + "@octokit/graphql": "^5.0.0", + "@octokit/request": "^6.0.0", + "@octokit/request-error": "^3.0.0", + "@octokit/types": "^7.0.0", + "before-after-hook": "^2.2.0", + "universal-user-agent": "^6.0.0" + } + }, + "@octokit/endpoint": { + "version": "7.0.2", + "resolved": "https://registry.npmjs.org/@octokit/endpoint/-/endpoint-7.0.2.tgz", + "integrity": "sha512-8/AUACfE9vpRpehE6ZLfEtzkibe5nfsSwFZVMsG8qabqRt1M81qZYUFRZa1B8w8lP6cdfDJfRq9HWS+MbmR7tw==", + "dev": true, + "requires": { + "@octokit/types": "^7.0.0", + "is-plain-object": "^5.0.0", + "universal-user-agent": "^6.0.0" + } + }, + "@octokit/graphql": { + "version": "5.0.1", + "resolved": "https://registry.npmjs.org/@octokit/graphql/-/graphql-5.0.1.tgz", + "integrity": "sha512-sxmnewSwAixkP1TrLdE6yRG53eEhHhDTYUykUwdV9x8f91WcbhunIHk9x1PZLALdBZKRPUO2HRcm4kezZ79HoA==", + "dev": true, + "requires": { + "@octokit/request": "^6.0.0", + "@octokit/types": "^7.0.0", + "universal-user-agent": "^6.0.0" + } + }, + "@octokit/openapi-types": { + "version": "13.13.1", + "resolved": "https://registry.npmjs.org/@octokit/openapi-types/-/openapi-types-13.13.1.tgz", + "integrity": "sha512-4EuKSk3N95UBWFau3Bz9b3pheQ8jQYbKmBL5+GSuY8YDPDwu03J4BjI+66yNi8aaX/3h1qDpb0mbBkLdr+cfGQ==", + "dev": true + }, + "@octokit/plugin-enterprise-rest": { + "version": "6.0.1", + "resolved": "https://registry.npmjs.org/@octokit/plugin-enterprise-rest/-/plugin-enterprise-rest-6.0.1.tgz", + "integrity": "sha512-93uGjlhUD+iNg1iWhUENAtJata6w5nE+V4urXOAlIXdco6xNZtUSfYY8dzp3Udy74aqO/B5UZL80x/YMa5PKRw==", + "dev": true + }, + "@octokit/plugin-paginate-rest": { + "version": "4.3.1", + "resolved": "https://registry.npmjs.org/@octokit/plugin-paginate-rest/-/plugin-paginate-rest-4.3.1.tgz", + "integrity": "sha512-h8KKxESmSFTcXX409CAxlaOYscEDvN2KGQRsLCGT1NSqRW+D6EXLVQ8vuHhFznS9MuH9QYw1GfsUN30bg8hjVA==", + "dev": true, + "requires": { + "@octokit/types": "^7.5.0" + } + }, + "@octokit/plugin-request-log": { + "version": "1.0.4", + "resolved": "https://registry.npmjs.org/@octokit/plugin-request-log/-/plugin-request-log-1.0.4.tgz", + "integrity": "sha512-mLUsMkgP7K/cnFEw07kWqXGF5LKrOkD+lhCrKvPHXWDywAwuDUeDwWBpc69XK3pNX0uKiVt8g5z96PJ6z9xCFA==", + "dev": true, + "requires": {} + }, + "@octokit/plugin-rest-endpoint-methods": { + "version": "6.6.2", + "resolved": "https://registry.npmjs.org/@octokit/plugin-rest-endpoint-methods/-/plugin-rest-endpoint-methods-6.6.2.tgz", + "integrity": "sha512-n9dL5KMpz9qVFSNdcVWC8ZPbl68QbTk7+CMPXCXqaMZOLn1n1YuoSFFCy84Ge0fx333fUqpnBHv8BFjwGtUQkA==", + "dev": true, + "requires": { + "@octokit/types": "^7.5.0", + "deprecation": "^2.3.1" + } + }, + "@octokit/request": { + "version": "6.2.1", + "resolved": "https://registry.npmjs.org/@octokit/request/-/request-6.2.1.tgz", + "integrity": "sha512-gYKRCia3cpajRzDSU+3pt1q2OcuC6PK8PmFIyxZDWCzRXRSIBH8jXjFJ8ZceoygBIm0KsEUg4x1+XcYBz7dHPQ==", + "dev": true, + "requires": { + "@octokit/endpoint": "^7.0.0", + "@octokit/request-error": "^3.0.0", + "@octokit/types": "^7.0.0", + "is-plain-object": "^5.0.0", + "node-fetch": "^2.6.7", + "universal-user-agent": "^6.0.0" + } + }, + "@octokit/request-error": { + "version": "3.0.1", + "resolved": "https://registry.npmjs.org/@octokit/request-error/-/request-error-3.0.1.tgz", + "integrity": "sha512-ym4Bp0HTP7F3VFssV88WD1ZyCIRoE8H35pXSKwLeMizcdZAYc/t6N9X9Yr9n6t3aG9IH75XDnZ6UeZph0vHMWQ==", + "dev": true, + "requires": { + "@octokit/types": "^7.0.0", + "deprecation": "^2.0.0", + "once": "^1.4.0" + } + }, + "@octokit/rest": { + "version": "19.0.4", + "resolved": "https://registry.npmjs.org/@octokit/rest/-/rest-19.0.4.tgz", + "integrity": "sha512-LwG668+6lE8zlSYOfwPj4FxWdv/qFXYBpv79TWIQEpBLKA9D/IMcWsF/U9RGpA3YqMVDiTxpgVpEW3zTFfPFTA==", + "dev": true, + "requires": { + "@octokit/core": "^4.0.0", + "@octokit/plugin-paginate-rest": "^4.0.0", + "@octokit/plugin-request-log": "^1.0.4", + "@octokit/plugin-rest-endpoint-methods": "^6.0.0" + } + }, + "@octokit/types": { + "version": "7.5.1", + "resolved": "https://registry.npmjs.org/@octokit/types/-/types-7.5.1.tgz", + "integrity": "sha512-Zk4OUMLCSpXNI8KZZn47lVLJSsgMyCimsWWQI5hyjZg7hdYm0kjotaIkbG0Pp8SfU2CofMBzonboTqvzn3FrJA==", + "dev": true, + "requires": { + "@octokit/openapi-types": "^13.11.0" + } + }, + "@parcel/watcher": { + "version": "2.0.4", + "resolved": "https://registry.npmjs.org/@parcel/watcher/-/watcher-2.0.4.tgz", + "integrity": "sha512-cTDi+FUDBIUOBKEtj+nhiJ71AZVlkAsQFuGQTun5tV9mwQBQgZvhCzG+URPQc8myeN32yRVZEfVAPCs1RW+Jvg==", + "dev": true, + "requires": { + "node-addon-api": "^3.2.1", + "node-gyp-build": "^4.3.0" + } + }, + "@phenomnomnominal/tsquery": { + "version": "4.1.1", + "resolved": "https://registry.npmjs.org/@phenomnomnominal/tsquery/-/tsquery-4.1.1.tgz", + "integrity": "sha512-jjMmK1tnZbm1Jq5a7fBliM4gQwjxMU7TFoRNwIyzwlO+eHPRCFv/Nv+H/Gi1jc3WR7QURG8D5d0Tn12YGrUqBQ==", + "dev": true, + "requires": { + "esquery": "^1.0.1" + } + }, + "@pnpm/network.ca-file": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/@pnpm/network.ca-file/-/network.ca-file-1.0.1.tgz", + "integrity": "sha512-gkINruT2KUhZLTaiHxwCOh1O4NVnFT0wLjWFBHmTz9vpKag/C/noIMJXBxFe4F0mYpUVX2puLwAieLYFg2NvoA==", + "dev": true, + "requires": { + "graceful-fs": "4.2.10" + } + }, + "@pnpm/npm-conf": { + "version": "1.0.5", + "resolved": "https://registry.npmjs.org/@pnpm/npm-conf/-/npm-conf-1.0.5.tgz", + "integrity": "sha512-hD8ml183638O3R6/Txrh0L8VzGOrFXgRtRDG4qQC4tONdZ5Z1M+tlUUDUvrjYdmK6G+JTBTeaCLMna11cXzi8A==", + "dev": true, + "requires": { + "@pnpm/network.ca-file": "^1.0.1", + "config-chain": "^1.1.11" + } + }, + "@sindresorhus/is": { + "version": "5.3.0", + "resolved": "https://registry.npmjs.org/@sindresorhus/is/-/is-5.3.0.tgz", + "integrity": "sha512-CX6t4SYQ37lzxicAqsBtxA3OseeoVrh9cSJ5PFYam0GksYlupRfy1A+Q4aYD3zvcfECLc0zO2u+ZnR2UYKvCrw==", + "dev": true + }, + "@szmarczak/http-timer": { + "version": "5.0.1", + "resolved": "https://registry.npmjs.org/@szmarczak/http-timer/-/http-timer-5.0.1.tgz", + "integrity": "sha512-+PmQX0PiAYPMeVYe237LJAYvOMYW1j2rH5YROyS3b4CTVJum34HfRvKvAzozHAQG0TnHNdUfY9nCeUyRAs//cw==", + "dev": true, + "requires": { + "defer-to-connect": "^2.0.1" + } + }, + "@tootallnate/once": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/@tootallnate/once/-/once-2.0.0.tgz", + "integrity": "sha512-XCuKFP5PS55gnMVu3dty8KPatLqUoy/ZYzDzAGCQ8JNFCkLXzmI7vNHCR+XpbZaMWQK/vQubr7PkYq8g470J/A==", + "dev": true + }, + "@types/http-cache-semantics": { + "version": "4.0.1", + "resolved": "https://registry.npmjs.org/@types/http-cache-semantics/-/http-cache-semantics-4.0.1.tgz", + "integrity": "sha512-SZs7ekbP8CN0txVG2xVRH6EgKmEm31BOxA07vkFaETzZz1xh+cbt8BcI0slpymvwhx5dlFnQG2rTlPVQn+iRPQ==", + "dev": true + }, + "@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 + }, + "@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 + }, + "@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 + }, + "@types/minimatch": { + "version": "3.0.5", + "resolved": "https://registry.npmjs.org/@types/minimatch/-/minimatch-3.0.5.tgz", + "integrity": "sha512-Klz949h02Gz2uZCMGwDUSDS1YBlTdDDgbWHi+81l29tQALUtvz4rAYi5uoVhE5Lagoq6DeqAUlbrHvW/mXDgdQ==", + "dev": true + }, + "@types/minimist": { + "version": "1.2.2", + "resolved": "https://registry.npmjs.org/@types/minimist/-/minimist-1.2.2.tgz", + "integrity": "sha512-jhuKLIRrhvCPLqwPcx6INqmKeiA5EWrsCOPhrlFSrbrmU4ZMPjj5Ul/oLCMDO98XRUIwVm78xICz4EPCektzeQ==", + "dev": true + }, + "@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 + }, + "@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 + }, + "@typescript-eslint/eslint-plugin": { + "version": "5.40.0", + "resolved": "https://registry.npmjs.org/@typescript-eslint/eslint-plugin/-/eslint-plugin-5.40.0.tgz", + "integrity": "sha512-FIBZgS3DVJgqPwJzvZTuH4HNsZhHMa9SjxTKAZTlMsPw/UzpEjcf9f4dfgDJEHjK+HboUJo123Eshl6niwEm/Q==", + "dev": true, + "requires": { + "@typescript-eslint/scope-manager": "5.40.0", + "@typescript-eslint/type-utils": "5.40.0", + "@typescript-eslint/utils": "5.40.0", + "debug": "^4.3.4", + "ignore": "^5.2.0", + "regexpp": "^3.2.0", + "semver": "^7.3.7", + "tsutils": "^3.21.0" + } + }, + "@typescript-eslint/parser": { + "version": "5.40.0", + "resolved": "https://registry.npmjs.org/@typescript-eslint/parser/-/parser-5.40.0.tgz", + "integrity": "sha512-Ah5gqyX2ySkiuYeOIDg7ap51/b63QgWZA7w6AHtFrag7aH0lRQPbLzUjk0c9o5/KZ6JRkTTDKShL4AUrQa6/hw==", + "dev": true, + "requires": { + "@typescript-eslint/scope-manager": "5.40.0", + "@typescript-eslint/types": "5.40.0", + "@typescript-eslint/typescript-estree": "5.40.0", + "debug": "^4.3.4" + } + }, + "@typescript-eslint/scope-manager": { + "version": "5.40.0", + "resolved": "https://registry.npmjs.org/@typescript-eslint/scope-manager/-/scope-manager-5.40.0.tgz", + "integrity": "sha512-d3nPmjUeZtEWRvyReMI4I1MwPGC63E8pDoHy0BnrYjnJgilBD3hv7XOiETKLY/zTwI7kCnBDf2vWTRUVpYw0Uw==", + "dev": true, + "requires": { + "@typescript-eslint/types": "5.40.0", + "@typescript-eslint/visitor-keys": "5.40.0" + } + }, + "@typescript-eslint/type-utils": { + "version": "5.40.0", + "resolved": "https://registry.npmjs.org/@typescript-eslint/type-utils/-/type-utils-5.40.0.tgz", + "integrity": "sha512-nfuSdKEZY2TpnPz5covjJqav+g5qeBqwSHKBvz7Vm1SAfy93SwKk/JeSTymruDGItTwNijSsno5LhOHRS1pcfw==", + "dev": true, + "requires": { + "@typescript-eslint/typescript-estree": "5.40.0", + "@typescript-eslint/utils": "5.40.0", + "debug": "^4.3.4", + "tsutils": "^3.21.0" + } + }, + "@typescript-eslint/types": { + "version": "5.40.0", + "resolved": "https://registry.npmjs.org/@typescript-eslint/types/-/types-5.40.0.tgz", + "integrity": "sha512-V1KdQRTXsYpf1Y1fXCeZ+uhjW48Niiw0VGt4V8yzuaDTU8Z1Xl7yQDyQNqyAFcVhpYXIVCEuxSIWTsLDpHgTbw==", + "dev": true + }, + "@typescript-eslint/typescript-estree": { + "version": "5.40.0", + "resolved": "https://registry.npmjs.org/@typescript-eslint/typescript-estree/-/typescript-estree-5.40.0.tgz", + "integrity": "sha512-b0GYlDj8TLTOqwX7EGbw2gL5EXS2CPEWhF9nGJiGmEcmlpNBjyHsTwbqpyIEPVpl6br4UcBOYlcI2FJVtJkYhg==", + "dev": true, + "requires": { + "@typescript-eslint/types": "5.40.0", + "@typescript-eslint/visitor-keys": "5.40.0", + "debug": "^4.3.4", + "globby": "^11.1.0", + "is-glob": "^4.0.3", + "semver": "^7.3.7", + "tsutils": "^3.21.0" + } + }, + "@typescript-eslint/utils": { + "version": "5.40.0", + "resolved": "https://registry.npmjs.org/@typescript-eslint/utils/-/utils-5.40.0.tgz", + "integrity": "sha512-MO0y3T5BQ5+tkkuYZJBjePewsY+cQnfkYeRqS6tPh28niiIwPnQ1t59CSRcs1ZwJJNOdWw7rv9pF8aP58IMihA==", + "dev": true, + "requires": { + "@types/json-schema": "^7.0.9", + "@typescript-eslint/scope-manager": "5.40.0", + "@typescript-eslint/types": "5.40.0", + "@typescript-eslint/typescript-estree": "5.40.0", + "eslint-scope": "^5.1.1", + "eslint-utils": "^3.0.0", + "semver": "^7.3.7" + } + }, + "@typescript-eslint/visitor-keys": { + "version": "5.40.0", + "resolved": "https://registry.npmjs.org/@typescript-eslint/visitor-keys/-/visitor-keys-5.40.0.tgz", + "integrity": "sha512-ijJ+6yig+x9XplEpG2K6FUdJeQGGj/15U3S56W9IqXKJqleuD7zJ2AX/miLezwxpd7ZxDAqO87zWufKg+RPZyQ==", + "dev": true, + "requires": { + "@typescript-eslint/types": "5.40.0", + "eslint-visitor-keys": "^3.3.0" + } + }, + "@yarnpkg/lockfile": { + "version": "1.1.0", + "resolved": "https://registry.npmjs.org/@yarnpkg/lockfile/-/lockfile-1.1.0.tgz", + "integrity": "sha512-GpSwvyXOcOOlV70vbnzjj4fW5xW/FdUF6nQEt1ENy7m4ZCczi1+/buVUPAqmGfqznsORNFzUMjctTIp8a9tuCQ==", + "dev": true + }, + "@yarnpkg/parsers": { + "version": "3.0.0-rc.25", + "resolved": "https://registry.npmjs.org/@yarnpkg/parsers/-/parsers-3.0.0-rc.25.tgz", + "integrity": "sha512-uotaIJwVQeV/DcGA9G2EVuVFHnEEdxDy3yRLeh9VHS6Lx7nZETaWzJPU1bgAwnAa3gplol2NIQhlsr2eqgq9qA==", + "dev": true, + "requires": { + "js-yaml": "^3.10.0", + "tslib": "^2.4.0" + }, + "dependencies": { + "argparse": { + "version": "1.0.10", + "resolved": "https://registry.npmjs.org/argparse/-/argparse-1.0.10.tgz", + "integrity": "sha512-o5Roy6tNG4SL/FOkCAN6RzjiakZS25RLYFrcMttJqbdd8BWrnA+fGz57iN5Pb06pvBGvl5gQ0B48dJlslXvoTg==", + "dev": true, + "requires": { + "sprintf-js": "~1.0.2" + } + }, + "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, + "requires": { + "argparse": "^1.0.7", + "esprima": "^4.0.0" + } + } + } + }, + "@zkochan/js-yaml": { + "version": "0.0.6", + "resolved": "https://registry.npmjs.org/@zkochan/js-yaml/-/js-yaml-0.0.6.tgz", + "integrity": "sha512-nzvgl3VfhcELQ8LyVrYOru+UtAy1nrygk2+AGbTm8a5YcO6o8lSjAT+pfg3vJWxIoZKOUhrK6UU7xW/+00kQrg==", + "dev": true, + "requires": { + "argparse": "^2.0.1" + } + }, + "abbrev": { + "version": "1.1.1", + "resolved": "https://registry.npmjs.org/abbrev/-/abbrev-1.1.1.tgz", + "integrity": "sha512-nne9/IiQ/hzIhY6pdDnbBtz7DjPTKrY00P/zvPSm5pOFkl6xuGrGnXn/VtTNNfNtAfZ9/1RtehkszU9qcTii0Q==", + "dev": true + }, + "acorn": { + "version": "8.8.0", + "resolved": "https://registry.npmjs.org/acorn/-/acorn-8.8.0.tgz", + "integrity": "sha512-QOxyigPVrpZ2GXT+PFyZTl6TtOFc5egxHIP9IlQ+RbupQuX4RkT/Bee4/kQuC02Xkzg84JcT7oLYtDIQxp+v7w==", + "dev": true + }, + "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, + "requires": {} + }, + "add-stream": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/add-stream/-/add-stream-1.0.0.tgz", + "integrity": "sha512-qQLMr+8o0WC4FZGQTcJiKBVC59JylcPSrTtk6usvmIDFUOCKegapy1VHQwRbFMOFyb/inzUVqHs+eMYKDM1YeQ==", + "dev": true + }, + "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==", + "dev": true, + "requires": { + "debug": "4" + } + }, + "agentkeepalive": { + "version": "4.2.1", + "resolved": "https://registry.npmjs.org/agentkeepalive/-/agentkeepalive-4.2.1.tgz", + "integrity": "sha512-Zn4cw2NEqd+9fiSVWMscnjyQ1a8Yfoc5oBajLeo5w+YBHgDUcEBY2hS4YpTz6iN5f/2zQiktcuM6tS8x1p9dpA==", + "dev": true, + "requires": { + "debug": "^4.1.0", + "depd": "^1.1.2", + "humanize-ms": "^1.2.1" + } + }, + "aggregate-error": { + "version": "3.1.0", + "resolved": "https://registry.npmjs.org/aggregate-error/-/aggregate-error-3.1.0.tgz", + "integrity": "sha512-4I7Td01quW/RpocfNayFdFVk1qSuoh0E7JrbRJ16nH01HhKFQ88INq9Sd+nd72zqRySlr9BmDA8xlEJ6vJMrYA==", + "dev": true, + "requires": { + "clean-stack": "^2.0.0", + "indent-string": "^4.0.0" + } + }, + "ansi-align": { + "version": "3.0.1", + "resolved": "https://registry.npmjs.org/ansi-align/-/ansi-align-3.0.1.tgz", + "integrity": "sha512-IOfwwBF5iczOjp/WeY4YxyjqAFMQoZufdQWDd19SEExbVLNXqvpzSJ/M7Za4/sCPmQ0+GRquoA7bGcINcxew6w==", + "dev": true, + "requires": { + "string-width": "^4.1.0" + } + }, + "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 + }, + "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, + "requires": { + "type-fest": "^0.21.3" + }, + "dependencies": { + "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 + } + } + }, + "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 + }, + "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, + "requires": { + "color-convert": "^2.0.1" + } + }, + "anymatch": { + "version": "3.1.2", + "resolved": "https://registry.npmjs.org/anymatch/-/anymatch-3.1.2.tgz", + "integrity": "sha512-P43ePfOAIupkguHUycrc4qJ9kz8ZiuOUijaETwX7THt0Y/GNK7v0aa8rY816xWjZ7rJdA5XdMcpVFTKMq+RvWg==", + "dev": true, + "requires": { + "normalize-path": "^3.0.0", + "picomatch": "^2.0.4" + } + }, + "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==", + "dev": true + }, + "are-we-there-yet": { + "version": "3.0.1", + "resolved": "https://registry.npmjs.org/are-we-there-yet/-/are-we-there-yet-3.0.1.tgz", + "integrity": "sha512-QZW4EDmGwlYur0Yyf/b2uGucHQMa8aFUP7eu9ddR73vvhFyt4V0Vl3QHPcTNJ8l6qYOBdxgXdnBXQrHilfRQBg==", + "dev": true, + "requires": { + "delegates": "^1.0.0", + "readable-stream": "^3.6.0" + } + }, + "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 + }, + "array-differ": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/array-differ/-/array-differ-3.0.0.tgz", + "integrity": "sha512-THtfYS6KtME/yIAhKjZ2ul7XI96lQGHRputJQHO80LAWQnuGP4iCIN8vdMRboGbIEYBwU33q8Tch1os2+X0kMg==", + "dev": true + }, + "array-ify": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/array-ify/-/array-ify-1.0.0.tgz", + "integrity": "sha512-c5AMf34bKdvPhQ7tBGhqkgKNUzMr4WUs+WDtC2ZUGOUncbxKMTvqxYctiseW3+L4bA8ec+GcZ6/A/FW4m8ukng==", + "dev": true + }, + "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 + }, + "arrify": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/arrify/-/arrify-1.0.1.tgz", + "integrity": "sha512-3CYzex9M9FGQjCGMGyi6/31c8GJbgb0qGyrx5HWxPd0aCwh4cB2YjMb2Xf9UuoogrMrlO9cTqnB5rI5GHZTcUA==", + "dev": true + }, + "asap": { + "version": "2.0.6", + "resolved": "https://registry.npmjs.org/asap/-/asap-2.0.6.tgz", + "integrity": "sha512-BSHWgDSAiKs50o2Re8ppvp3seVHXSRM44cdSsT9FfNEUUZLOGWVCsiWaRPWM1Znn+mqZ1OfVZ3z3DWEzSp7hRA==", + "dev": true + }, + "async": { + "version": "3.2.4", + "resolved": "https://registry.npmjs.org/async/-/async-3.2.4.tgz", + "integrity": "sha512-iAB+JbDEGXhyIUavoDl9WP/Jj106Kz9DEn1DPgYw5ruDn0e3Wgi3sKFm55sASdGBNOQB8F59d9qQ7deqrHA8wQ==", + "dev": true + }, + "asynckit": { + "version": "0.4.0", + "resolved": "https://registry.npmjs.org/asynckit/-/asynckit-0.4.0.tgz", + "integrity": "sha512-Oei9OH4tRh0YqU3GxhX79dM/mwVgvbZJaSNaRk+bshkj0S5cfHcgYakreBjrHwatXKbz+IoIdYLxrKim2MjW0Q==", + "dev": true + }, + "at-least-node": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/at-least-node/-/at-least-node-1.0.0.tgz", + "integrity": "sha512-+q/t7Ekv1EDY2l6Gda6LLiX14rU9TV20Wa3ofeQmwPFZbOMo9DXrLbOjFaaclkXKWidIaopwAObQDqwWtGUjqg==", + "dev": true + }, + "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 + }, + "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 + }, + "before-after-hook": { + "version": "2.2.3", + "resolved": "https://registry.npmjs.org/before-after-hook/-/before-after-hook-2.2.3.tgz", + "integrity": "sha512-NzUnlZexiaH/46WDhANlyR2bXRopNg4F/zuSA3OpZnllCUgRaOF2znDioDWrmbNVsuZk6l9pMquQB38cfBZwkQ==", + "dev": true + }, + "bin-links": { + "version": "3.0.3", + "resolved": "https://registry.npmjs.org/bin-links/-/bin-links-3.0.3.tgz", + "integrity": "sha512-zKdnMPWEdh4F5INR07/eBrodC7QrF5JKvqskjz/ZZRXg5YSAZIbn8zGhbhUrElzHBZ2fvEQdOU59RHcTG3GiwA==", + "dev": true, + "requires": { + "cmd-shim": "^5.0.0", + "mkdirp-infer-owner": "^2.0.0", + "npm-normalize-package-bin": "^2.0.0", + "read-cmd-shim": "^3.0.0", + "rimraf": "^3.0.0", + "write-file-atomic": "^4.0.0" + }, + "dependencies": { + "npm-normalize-package-bin": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/npm-normalize-package-bin/-/npm-normalize-package-bin-2.0.0.tgz", + "integrity": "sha512-awzfKUO7v0FscrSpRoogyNm0sajikhBWpU0QMrW09AMi9n1PoKU6WaIqUzuJSQnpciZZmJ/jMZ2Egfmb/9LiWQ==", + "dev": true + } + } + }, + "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 + }, + "bl": { + "version": "4.1.0", + "resolved": "https://registry.npmjs.org/bl/-/bl-4.1.0.tgz", + "integrity": "sha512-1W07cM9gS6DcLperZfFSj+bWLtaPGSOHWhPiGzXmvVJbRLdG82sH/Kn8EtW1VqWVA54AKf2h5k5BbnIbwF3h6w==", + "dev": true, + "requires": { + "buffer": "^5.5.0", + "inherits": "^2.0.4", + "readable-stream": "^3.4.0" + } + }, + "boxen": { + "version": "7.0.0", + "resolved": "https://registry.npmjs.org/boxen/-/boxen-7.0.0.tgz", + "integrity": "sha512-j//dBVuyacJbvW+tvZ9HuH03fZ46QcaKvvhZickZqtB271DxJ7SNRSNxrV/dZX0085m7hISRZWbzWlJvx/rHSg==", + "dev": true, + "requires": { + "ansi-align": "^3.0.1", + "camelcase": "^7.0.0", + "chalk": "^5.0.1", + "cli-boxes": "^3.0.0", + "string-width": "^5.1.2", + "type-fest": "^2.13.0", + "widest-line": "^4.0.1", + "wrap-ansi": "^8.0.1" + }, + "dependencies": { + "ansi-regex": { + "version": "6.0.1", + "resolved": "https://registry.npmjs.org/ansi-regex/-/ansi-regex-6.0.1.tgz", + "integrity": "sha512-n5M855fKb2SsfMIiFFoVrABHJC8QtHwVx+mHWP3QcEqBHYienj5dHSgjbxtC0WEZXYt4wcD6zrQElDPhFuZgfA==", + "dev": true + }, + "ansi-styles": { + "version": "6.2.0", + "resolved": "https://registry.npmjs.org/ansi-styles/-/ansi-styles-6.2.0.tgz", + "integrity": "sha512-3MWBO/XxbkDtc/qpECaUwDM0DQ++ujBjdjs0ElZvChUoPv/P7GOnl3x+R2RF2My5UJHEW5R87q556MiR8U3PLw==", + "dev": true + }, + "camelcase": { + "version": "7.0.0", + "resolved": "https://registry.npmjs.org/camelcase/-/camelcase-7.0.0.tgz", + "integrity": "sha512-JToIvOmz6nhGsUhAYScbo2d6Py5wojjNfoxoc2mEVLUdJ70gJK2gnd+ABY1Tc3sVMyK7QDPtN0T/XdlCQWITyQ==", + "dev": true + }, + "chalk": { + "version": "5.1.0", + "resolved": "https://registry.npmjs.org/chalk/-/chalk-5.1.0.tgz", + "integrity": "sha512-56zD4khRTBoIyzUYAFgDDaPhUMN/fC/rySe6aZGqbj/VWiU2eI3l6ZLOtYGFZAV5v02mwPjtpzlrOveJiz5eZQ==", + "dev": true + }, + "emoji-regex": { + "version": "9.2.2", + "resolved": "https://registry.npmjs.org/emoji-regex/-/emoji-regex-9.2.2.tgz", + "integrity": "sha512-L18DaJsXSUk2+42pv8mLs5jJT2hqFkFE4j21wOmgbUqsZ2hL72NsUU785g9RXgo3s0ZNgVl42TiHp3ZtOv/Vyg==", + "dev": true + }, + "string-width": { + "version": "5.1.2", + "resolved": "https://registry.npmjs.org/string-width/-/string-width-5.1.2.tgz", + "integrity": "sha512-HnLOCR3vjcY8beoNLtcjZ5/nxn2afmME6lhrDrebokqMap+XbeW8n9TXpPDOqdGK5qcI3oT0GKTW6wC7EMiVqA==", + "dev": true, + "requires": { + "eastasianwidth": "^0.2.0", + "emoji-regex": "^9.2.2", + "strip-ansi": "^7.0.1" + } + }, + "strip-ansi": { + "version": "7.0.1", + "resolved": "https://registry.npmjs.org/strip-ansi/-/strip-ansi-7.0.1.tgz", + "integrity": "sha512-cXNxvT8dFNRVfhVME3JAe98mkXDYN2O1l7jmcwMnOslDeESg1rF/OZMtK0nRAhiari1unG5cD4jG3rapUAkLbw==", + "dev": true, + "requires": { + "ansi-regex": "^6.0.1" + } + }, + "type-fest": { + "version": "2.19.0", + "resolved": "https://registry.npmjs.org/type-fest/-/type-fest-2.19.0.tgz", + "integrity": "sha512-RAH822pAdBgcNMAfWnCBU3CFZcfZ/i1eZjwFU/dsLKumyuuP3niueg2UAukXYF0E2AAoc82ZSSf9J0WQBinzHA==", + "dev": true + }, + "wrap-ansi": { + "version": "8.0.1", + "resolved": "https://registry.npmjs.org/wrap-ansi/-/wrap-ansi-8.0.1.tgz", + "integrity": "sha512-QFF+ufAqhoYHvoHdajT/Po7KoXVBPXS2bgjIam5isfWJPfIOnQZ50JtUiVvCv/sjgacf3yRrt2ZKUZ/V4itN4g==", + "dev": true, + "requires": { + "ansi-styles": "^6.1.0", + "string-width": "^5.0.1", + "strip-ansi": "^7.0.1" + } + } + } + }, + "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, + "requires": { + "balanced-match": "^1.0.0", + "concat-map": "0.0.1" + } + }, + "braces": { + "version": "3.0.2", + "resolved": "https://registry.npmjs.org/braces/-/braces-3.0.2.tgz", + "integrity": "sha512-b8um+L1RzM3WDSzvhm6gIz1yfTbBt6YTlcEKAvsmqCZZFw46z626lVj9j1yEPW33H5H+lBQpZMP1k8l+78Ha0A==", + "dev": true, + "requires": { + "fill-range": "^7.0.1" + } + }, + "buffer": { + "version": "5.7.1", + "resolved": "https://registry.npmjs.org/buffer/-/buffer-5.7.1.tgz", + "integrity": "sha512-EHcyIPBQ4BSGlvjB16k5KgAJ27CIsHY/2JBmCRReo48y9rQ3MaUzWX3KVlBa4U7MyX02HdVj0K7C3WaB3ju7FQ==", + "dev": true, + "requires": { + "base64-js": "^1.3.1", + "ieee754": "^1.1.13" + } + }, + "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 + }, + "builtins": { + "version": "5.0.1", + "resolved": "https://registry.npmjs.org/builtins/-/builtins-5.0.1.tgz", + "integrity": "sha512-qwVpFEHNfhYJIzNRBvd2C1kyo6jz3ZSMPyyuR47OPdiKWlbYnZNyDWuyR175qDnAJLiCo5fBBqPb3RiXgWlkOQ==", + "dev": true, + "requires": { + "semver": "^7.0.0" + } + }, + "byte-size": { + "version": "7.0.1", + "resolved": "https://registry.npmjs.org/byte-size/-/byte-size-7.0.1.tgz", + "integrity": "sha512-crQdqyCwhokxwV1UyDzLZanhkugAgft7vt0qbbdt60C6Zf3CAiGmtUCylbtYwrU6loOUw3euGrNtW1J651ot1A==", + "dev": true + }, + "c8": { + "version": "7.12.0", + "resolved": "https://registry.npmjs.org/c8/-/c8-7.12.0.tgz", + "integrity": "sha512-CtgQrHOkyxr5koX1wEUmN/5cfDa2ckbHRA4Gy5LAL0zaCFtVWJS5++n+w4/sr2GWGerBxgTjpKeDclk/Qk6W/A==", + "dev": true, + "requires": { + "@bcoe/v8-coverage": "^0.2.3", + "@istanbuljs/schema": "^0.1.3", + "find-up": "^5.0.0", + "foreground-child": "^2.0.0", + "istanbul-lib-coverage": "^3.2.0", + "istanbul-lib-report": "^3.0.0", + "istanbul-reports": "^3.1.4", + "rimraf": "^3.0.2", + "test-exclude": "^6.0.0", + "v8-to-istanbul": "^9.0.0", + "yargs": "^16.2.0", + "yargs-parser": "^20.2.9" + } + }, + "cacache": { + "version": "16.1.3", + "resolved": "https://registry.npmjs.org/cacache/-/cacache-16.1.3.tgz", + "integrity": "sha512-/+Emcj9DAXxX4cwlLmRI9c166RuL3w30zp4R7Joiv2cQTtTtA+jeuCAjH3ZlGnYS3tKENSrKhAzVVP9GVyzeYQ==", + "dev": true, + "requires": { + "@npmcli/fs": "^2.1.0", + "@npmcli/move-file": "^2.0.0", + "chownr": "^2.0.0", + "fs-minipass": "^2.1.0", + "glob": "^8.0.1", + "infer-owner": "^1.0.4", + "lru-cache": "^7.7.1", + "minipass": "^3.1.6", + "minipass-collect": "^1.0.2", + "minipass-flush": "^1.0.5", + "minipass-pipeline": "^1.2.4", + "mkdirp": "^1.0.4", + "p-map": "^4.0.0", + "promise-inflight": "^1.0.1", + "rimraf": "^3.0.2", + "ssri": "^9.0.0", + "tar": "^6.1.11", + "unique-filename": "^2.0.0" + } + }, + "cacheable-lookup": { + "version": "7.0.0", + "resolved": "https://registry.npmjs.org/cacheable-lookup/-/cacheable-lookup-7.0.0.tgz", + "integrity": "sha512-+qJyx4xiKra8mZrcwhjMRMUhD5NR1R8esPkzIYxX96JiecFoxAXFuz/GpR3+ev4PE1WamHip78wV0vcmPQtp8w==", + "dev": true + }, + "cacheable-request": { + "version": "10.2.1", + "resolved": "https://registry.npmjs.org/cacheable-request/-/cacheable-request-10.2.1.tgz", + "integrity": "sha512-3tLJyBjGuXw1s5gpKFSG3iS4kaKT4id04dZi98wzHQp/8cqZNweBnrF9J+rrlvrf4M53OdtDGNctNHFias8BEA==", + "dev": true, + "requires": { + "@types/http-cache-semantics": "^4.0.1", + "get-stream": "^6.0.1", + "http-cache-semantics": "^4.1.0", + "keyv": "^4.5.0", + "mimic-response": "^4.0.0", + "normalize-url": "^7.1.0", + "responselike": "^3.0.0" + } + }, + "callsites": { + "version": "3.1.0", + "resolved": "https://registry.npmjs.org/callsites/-/callsites-3.1.0.tgz", + "integrity": "sha512-P8BjAsXvZS+VIDUI11hHCQEv74YT67YUi5JJFNWIqL235sBmjX4+qx9Muvls5ivyNENctx46xQLQ3aTuE7ssaQ==", + "dev": true + }, + "camelcase": { + "version": "5.3.1", + "resolved": "https://registry.npmjs.org/camelcase/-/camelcase-5.3.1.tgz", + "integrity": "sha512-L28STB170nwWS63UjtlEOE3dldQApaJXZkOI1uMFfzf3rRuPegHaHesyee+YxQ+W6SvRDQV6UrdOdRiR153wJg==", + "dev": true + }, + "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, + "requires": { + "camelcase": "^5.3.1", + "map-obj": "^4.0.0", + "quick-lru": "^4.0.1" + } + }, + "chalk": { + "version": "4.1.2", + "resolved": "https://registry.npmjs.org/chalk/-/chalk-4.1.2.tgz", + "integrity": "sha512-oKnbhFyRIXpUuez8iBMmyEa4nbj4IOQyuhc/wy9kY7/WVPcwIO9VA668Pu8RkO7+0G76SLROeyw9CpQ061i4mA==", + "dev": true, + "requires": { + "ansi-styles": "^4.1.0", + "supports-color": "^7.1.0" + } + }, + "chardet": { + "version": "0.7.0", + "resolved": "https://registry.npmjs.org/chardet/-/chardet-0.7.0.tgz", + "integrity": "sha512-mT8iDcrh03qDGRRmoA2hmBJnxpllMR+0/0qlzjqZES6NdiWDcZkCNAk4rPFZ9Q85r27unkiNNg8ZOiwZXBHwcA==", + "dev": true + }, + "chokidar": { + "version": "3.5.3", + "resolved": "https://registry.npmjs.org/chokidar/-/chokidar-3.5.3.tgz", + "integrity": "sha512-Dr3sfKRP6oTcjf2JmUmFJfeVMvXBdegxB0iVQ5eb2V10uFJUCAS8OByZdVAyVb8xXNz3GjjTgj9kLWsZTqE6kw==", + "dev": true, + "requires": { + "anymatch": "~3.1.2", + "braces": "~3.0.2", + "fsevents": "~2.3.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" + }, + "dependencies": { + "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, + "requires": { + "is-glob": "^4.0.1" + } + } + } + }, + "chownr": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/chownr/-/chownr-2.0.0.tgz", + "integrity": "sha512-bIomtDF5KGpdogkLd9VspvFzk9KfpyyGlS8YFVZl7TGPBHL5snIOnxeshwVgPteQ9b4Eydl+pVbIyE1DcvCWgQ==", + "dev": true + }, + "ci-info": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/ci-info/-/ci-info-2.0.0.tgz", + "integrity": "sha512-5tK7EtrZ0N+OLFMthtqOj4fI2Jeb88C4CAZPu25LDVUgXJ0A3Js4PMGqrn0JU1W0Mh1/Z8wZzYPxqUrXeBboCQ==", + "dev": true + }, + "clean-stack": { + "version": "2.2.0", + "resolved": "https://registry.npmjs.org/clean-stack/-/clean-stack-2.2.0.tgz", + "integrity": "sha512-4diC9HaTE+KRAMWhDhrGOECgWZxoevMc5TlkObMqNSsVU62PYzXZ/SMTjzyGAFF1YusgxGcSWTEXBhp0CPwQ1A==", + "dev": true + }, + "cli-boxes": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/cli-boxes/-/cli-boxes-3.0.0.tgz", + "integrity": "sha512-/lzGpEWL/8PfI0BmBOPRwp0c/wFNX1RdUML3jK/RcSBA9T8mZDdQpqYBKtCFTOfQbwPqWEOpjqW+Fnayc0969g==", + "dev": true + }, + "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, + "requires": { + "restore-cursor": "^3.1.0" + } + }, + "cli-spinners": { + "version": "2.6.1", + "resolved": "https://registry.npmjs.org/cli-spinners/-/cli-spinners-2.6.1.tgz", + "integrity": "sha512-x/5fWmGMnbKQAaNwN+UZlV79qBLM9JFnJuJ03gIi5whrob0xV0ofNVHy9DhwGdsMJQc2OKv0oGmLzvaqvAVv+g==", + "dev": true + }, + "cli-table": { + "version": "0.3.11", + "resolved": "https://registry.npmjs.org/cli-table/-/cli-table-0.3.11.tgz", + "integrity": "sha512-IqLQi4lO0nIB4tcdTpN4LCB9FI3uqrJZK7RC515EnhZ6qBaglkIgICb1wjeAqpdoOabm1+SuQtkXIPdYC93jhQ==", + "dev": true, + "requires": { + "colors": "1.0.3" + } + }, + "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 + }, + "cliui": { + "version": "7.0.4", + "resolved": "https://registry.npmjs.org/cliui/-/cliui-7.0.4.tgz", + "integrity": "sha512-OcRE68cOsVMXp1Yvonl/fzkQOyjLSu/8bhPDfQt0e0/Eb283TKP20Fs2MqoPsr9SwA595rRCA+QMzYc9nBP+JQ==", + "dev": true, + "requires": { + "string-width": "^4.2.0", + "strip-ansi": "^6.0.0", + "wrap-ansi": "^7.0.0" + } + }, + "clone": { + "version": "1.0.4", + "resolved": "https://registry.npmjs.org/clone/-/clone-1.0.4.tgz", + "integrity": "sha512-JQHZ2QMW6l3aH/j6xCqQThY/9OH4D/9ls34cgkUBiEeocRTU04tHfKPBsUK1PqZCUQM7GiA0IIXJSuXHI64Kbg==", + "dev": true + }, + "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, + "requires": { + "is-plain-object": "^2.0.4", + "kind-of": "^6.0.2", + "shallow-clone": "^3.0.0" + }, + "dependencies": { + "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, + "requires": { + "isobject": "^3.0.1" + } + } + } + }, + "cmd-shim": { + "version": "5.0.0", + "resolved": "https://registry.npmjs.org/cmd-shim/-/cmd-shim-5.0.0.tgz", + "integrity": "sha512-qkCtZ59BidfEwHltnJwkyVZn+XQojdAySM1D1gSeh11Z4pW1Kpolkyo53L5noc0nrxmIvyFwTmJRo4xs7FFLPw==", + "dev": true, + "requires": { + "mkdirp-infer-owner": "^2.0.0" + } + }, + "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, + "requires": { + "color-name": "~1.1.4" + } + }, + "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 + }, + "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==", + "dev": true + }, + "colors": { + "version": "1.0.3", + "resolved": "https://registry.npmjs.org/colors/-/colors-1.0.3.tgz", + "integrity": "sha512-pFGrxThWcWQ2MsAz6RtgeWe4NK2kUE1WfsrvvlctdII745EW9I0yflqhe7++M5LEc7bV2c/9/5zc8sFcpL0Drw==", + "dev": true + }, + "columnify": { + "version": "1.6.0", + "resolved": "https://registry.npmjs.org/columnify/-/columnify-1.6.0.tgz", + "integrity": "sha512-lomjuFZKfM6MSAnV9aCZC9sc0qGbmZdfygNv+nCpqVkSKdCxCklLtd16O0EILGkImHw9ZpHkAnHaB+8Zxq5W6Q==", + "dev": true, + "requires": { + "strip-ansi": "^6.0.1", + "wcwidth": "^1.0.0" + } + }, + "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, + "requires": { + "delayed-stream": "~1.0.0" + } + }, + "commander": { + "version": "9.4.1", + "resolved": "https://registry.npmjs.org/commander/-/commander-9.4.1.tgz", + "integrity": "sha512-5EEkTNyHNGFPD2H+c/dXXfQZYa/scCKasxWcXJaWnNJ99pnQN9Vnmqow+p+PlFPE63Q6mThaZws1T+HxfpgtPw==", + "dev": true + }, + "common-ancestor-path": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/common-ancestor-path/-/common-ancestor-path-1.0.1.tgz", + "integrity": "sha512-L3sHRo1pXXEqX8VU28kfgUY+YGsk09hPqZiZmLacNib6XNTCM8ubYeT7ryXQw8asB1sKgcU5lkB7ONug08aB8w==", + "dev": true + }, + "compare-func": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/compare-func/-/compare-func-2.0.0.tgz", + "integrity": "sha512-zHig5N+tPWARooBnb0Zx1MFcdfpyJrfTJ3Y5L+IFvUm8rM74hHz66z0gw0x4tijh5CorKkKUCnW82R2vmpeCRA==", + "dev": true, + "requires": { + "array-ify": "^1.0.0", + "dot-prop": "^5.1.0" + }, + "dependencies": { + "dot-prop": { + "version": "5.3.0", + "resolved": "https://registry.npmjs.org/dot-prop/-/dot-prop-5.3.0.tgz", + "integrity": "sha512-QM8q3zDe58hqUqjraQOmzZ1LIH9SWQJTlEKCH4kJ2oQvLZk7RbQXvtDM2XEq3fwkV9CCvvH4LA0AV+ogFsBM2Q==", + "dev": true, + "requires": { + "is-obj": "^2.0.0" + } + } + } + }, + "concat-map": { + "version": "0.0.1", + "resolved": "https://registry.npmjs.org/concat-map/-/concat-map-0.0.1.tgz", + "integrity": "sha512-/Srv4dswyQNBfohGpz9o6Yb3Gz3SrUDqBH5rTuhGR7ahtlbYKnVxw2bCFMRljaA7EXHaXZ8wsHdodFvbkhKmqg==", + "dev": true + }, + "concat-stream": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/concat-stream/-/concat-stream-2.0.0.tgz", + "integrity": "sha512-MWufYdFw53ccGjCA+Ol7XJYpAlW6/prSMzuPOTRnJGcGzuhLn4Scrz7qf6o8bROZ514ltazcIFJZevcfbo0x7A==", + "dev": true, + "requires": { + "buffer-from": "^1.0.0", + "inherits": "^2.0.3", + "readable-stream": "^3.0.2", + "typedarray": "^0.0.6" + } + }, + "config-chain": { + "version": "1.1.13", + "resolved": "https://registry.npmjs.org/config-chain/-/config-chain-1.1.13.tgz", + "integrity": "sha512-qj+f8APARXHrM0hraqXYb2/bOVSV4PvJQlNZ/DVj0QrmNM2q2euizkeuVckQ57J+W0mRH6Hvi+k50M4Jul2VRQ==", + "dev": true, + "requires": { + "ini": "^1.3.4", + "proto-list": "~1.2.1" + } + }, + "configstore": { + "version": "6.0.0", + "resolved": "https://registry.npmjs.org/configstore/-/configstore-6.0.0.tgz", + "integrity": "sha512-cD31W1v3GqUlQvbBCGcXmd2Nj9SvLDOP1oQ0YFuLETufzSPaKp11rYBsSOm7rCsW3OnIRAFM3OxRhceaXNYHkA==", + "dev": true, + "requires": { + "dot-prop": "^6.0.1", + "graceful-fs": "^4.2.6", + "unique-string": "^3.0.0", + "write-file-atomic": "^3.0.3", + "xdg-basedir": "^5.0.1" + }, + "dependencies": { + "write-file-atomic": { + "version": "3.0.3", + "resolved": "https://registry.npmjs.org/write-file-atomic/-/write-file-atomic-3.0.3.tgz", + "integrity": "sha512-AvHcyZ5JnSfq3ioSyjrBkH9yW4m7Ayk8/9My/DD9onKeu/94fwrMocemO2QAJFAlnnDN+ZDS+ZjAR5ua1/PV/Q==", + "dev": true, + "requires": { + "imurmurhash": "^0.1.4", + "is-typedarray": "^1.0.0", + "signal-exit": "^3.0.2", + "typedarray-to-buffer": "^3.1.5" + } + } + } + }, + "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==", + "dev": true + }, + "conventional-changelog-angular": { + "version": "5.0.13", + "resolved": "https://registry.npmjs.org/conventional-changelog-angular/-/conventional-changelog-angular-5.0.13.tgz", + "integrity": "sha512-i/gipMxs7s8L/QeuavPF2hLnJgH6pEZAttySB6aiQLWcX3puWDL3ACVmvBhJGxnAy52Qc15ua26BufY6KpmrVA==", + "dev": true, + "requires": { + "compare-func": "^2.0.0", + "q": "^1.5.1" + } + }, + "conventional-changelog-core": { + "version": "4.2.4", + "resolved": "https://registry.npmjs.org/conventional-changelog-core/-/conventional-changelog-core-4.2.4.tgz", + "integrity": "sha512-gDVS+zVJHE2v4SLc6B0sLsPiloR0ygU7HaDW14aNJE1v4SlqJPILPl/aJC7YdtRE4CybBf8gDwObBvKha8Xlyg==", + "dev": true, + "requires": { + "add-stream": "^1.0.0", + "conventional-changelog-writer": "^5.0.0", + "conventional-commits-parser": "^3.2.0", + "dateformat": "^3.0.0", + "get-pkg-repo": "^4.0.0", + "git-raw-commits": "^2.0.8", + "git-remote-origin-url": "^2.0.0", + "git-semver-tags": "^4.1.1", + "lodash": "^4.17.15", + "normalize-package-data": "^3.0.0", + "q": "^1.5.1", + "read-pkg": "^3.0.0", + "read-pkg-up": "^3.0.0", + "through2": "^4.0.0" + } + }, + "conventional-changelog-preset-loader": { + "version": "2.3.4", + "resolved": "https://registry.npmjs.org/conventional-changelog-preset-loader/-/conventional-changelog-preset-loader-2.3.4.tgz", + "integrity": "sha512-GEKRWkrSAZeTq5+YjUZOYxdHq+ci4dNwHvpaBC3+ENalzFWuCWa9EZXSuZBpkr72sMdKB+1fyDV4takK1Lf58g==", + "dev": true + }, + "conventional-changelog-writer": { + "version": "5.0.1", + "resolved": "https://registry.npmjs.org/conventional-changelog-writer/-/conventional-changelog-writer-5.0.1.tgz", + "integrity": "sha512-5WsuKUfxW7suLblAbFnxAcrvf6r+0b7GvNaWUwUIk0bXMnENP/PEieGKVUQrjPqwPT4o3EPAASBXiY6iHooLOQ==", + "dev": true, + "requires": { + "conventional-commits-filter": "^2.0.7", + "dateformat": "^3.0.0", + "handlebars": "^4.7.7", + "json-stringify-safe": "^5.0.1", + "lodash": "^4.17.15", + "meow": "^8.0.0", + "semver": "^6.0.0", + "split": "^1.0.0", + "through2": "^4.0.0" + }, + "dependencies": { + "semver": { + "version": "6.3.0", + "resolved": "https://registry.npmjs.org/semver/-/semver-6.3.0.tgz", + "integrity": "sha512-b39TBaTSfV6yBrapU89p5fKekE2m/NwnDocOVruQFS1/veMgdzuPcnOM34M6CwxW8jH/lxEa5rBoDeUwu5HHTw==", + "dev": true + } + } + }, + "conventional-commits-filter": { + "version": "2.0.7", + "resolved": "https://registry.npmjs.org/conventional-commits-filter/-/conventional-commits-filter-2.0.7.tgz", + "integrity": "sha512-ASS9SamOP4TbCClsRHxIHXRfcGCnIoQqkvAzCSbZzTFLfcTqJVugB0agRgsEELsqaeWgsXv513eS116wnlSSPA==", + "dev": true, + "requires": { + "lodash.ismatch": "^4.4.0", + "modify-values": "^1.0.0" + } + }, + "conventional-commits-parser": { + "version": "3.2.4", + "resolved": "https://registry.npmjs.org/conventional-commits-parser/-/conventional-commits-parser-3.2.4.tgz", + "integrity": "sha512-nK7sAtfi+QXbxHCYfhpZsfRtaitZLIA6889kFIouLvz6repszQDgxBu7wf2WbU+Dco7sAnNCJYERCwt54WPC2Q==", + "dev": true, + "requires": { + "is-text-path": "^1.0.1", + "JSONStream": "^1.0.4", + "lodash": "^4.17.15", + "meow": "^8.0.0", + "split2": "^3.0.0", + "through2": "^4.0.0" + } + }, + "conventional-recommended-bump": { + "version": "6.1.0", + "resolved": "https://registry.npmjs.org/conventional-recommended-bump/-/conventional-recommended-bump-6.1.0.tgz", + "integrity": "sha512-uiApbSiNGM/kkdL9GTOLAqC4hbptObFo4wW2QRyHsKciGAfQuLU1ShZ1BIVI/+K2BE/W1AWYQMCXAsv4dyKPaw==", + "dev": true, + "requires": { + "concat-stream": "^2.0.0", + "conventional-changelog-preset-loader": "^2.3.4", + "conventional-commits-filter": "^2.0.7", + "conventional-commits-parser": "^3.2.0", + "git-raw-commits": "^2.0.8", + "git-semver-tags": "^4.1.1", + "meow": "^8.0.0", + "q": "^1.5.1" + } + }, + "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 + }, + "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 + }, + "cosmiconfig": { + "version": "7.0.1", + "resolved": "https://registry.npmjs.org/cosmiconfig/-/cosmiconfig-7.0.1.tgz", + "integrity": "sha512-a1YWNUV2HwGimB7dU2s1wUMurNKjpx60HxBB6xUM8Re+2s1g1IIfJvFR0/iCF+XHdE0GMTKTuLR32UQff4TEyQ==", + "dev": true, + "requires": { + "@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" + } + }, + "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, + "requires": { + "path-key": "^3.1.0", + "shebang-command": "^2.0.0", + "which": "^2.0.1" + } + }, + "crypto-random-string": { + "version": "4.0.0", + "resolved": "https://registry.npmjs.org/crypto-random-string/-/crypto-random-string-4.0.0.tgz", + "integrity": "sha512-x8dy3RnvYdlUcPOjkEHqozhiwzKNSq7GcPuXFbnyMOCHxX8V3OgIg/pYuabl2sbUPfIJaeAQB7PMOK8DFIdoRA==", + "dev": true, + "requires": { + "type-fest": "^1.0.1" + }, + "dependencies": { + "type-fest": { + "version": "1.4.0", + "resolved": "https://registry.npmjs.org/type-fest/-/type-fest-1.4.0.tgz", + "integrity": "sha512-yGSza74xk0UG8k+pLh5oeoYirvIiWo5t0/o3zHHAO2tRDiZcxWP7fywNlXhqb6/r6sWvwi+RsyQMWhVLe4BVuA==", + "dev": true + } + } + }, + "dargs": { + "version": "7.0.0", + "resolved": "https://registry.npmjs.org/dargs/-/dargs-7.0.0.tgz", + "integrity": "sha512-2iy1EkLdlBzQGvbweYRFxmFath8+K7+AKB0TlhHWkNuH+TmovaMH/Wp7V7R4u7f4SnX3OgLsU9t1NI9ioDnUpg==", + "dev": true + }, + "dateformat": { + "version": "3.0.3", + "resolved": "https://registry.npmjs.org/dateformat/-/dateformat-3.0.3.tgz", + "integrity": "sha512-jyCETtSl3VMZMWeRo7iY1FL19ges1t55hMo5yaam4Jrsm5EPL89UQkoQRyiI+Yf4k8r2ZpdngkV8hr1lIdjb3Q==", + "dev": true + }, + "debug": { + "version": "4.3.4", + "resolved": "https://registry.npmjs.org/debug/-/debug-4.3.4.tgz", + "integrity": "sha512-PRWFHuSU3eDtQJPvnNY7Jcket1j0t5OuOsFzPPzsekD52Zl8qUfFIPEiswXqIvHWGVHOgX+7G/vCNNhehwxfkQ==", + "dev": true, + "requires": { + "ms": "2.1.2" + } + }, + "debuglog": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/debuglog/-/debuglog-1.0.1.tgz", + "integrity": "sha512-syBZ+rnAK3EgMsH2aYEOLUW7mZSY9Gb+0wUMCFsZvcmiz+HigA0LOcq/HoQqVuGG+EKykunc7QG2bzrponfaSw==", + "dev": true + }, + "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 + }, + "decamelize-keys": { + "version": "1.1.0", + "resolved": "https://registry.npmjs.org/decamelize-keys/-/decamelize-keys-1.1.0.tgz", + "integrity": "sha512-ocLWuYzRPoS9bfiSdDd3cxvrzovVMZnRDVEzAs+hWIVXGDbHxWMECij2OBuyB/An0FFW/nLuq6Kv1i/YC5Qfzg==", + "dev": true, + "requires": { + "decamelize": "^1.1.0", + "map-obj": "^1.0.0" + }, + "dependencies": { + "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 + } + } + }, + "decompress-response": { + "version": "6.0.0", + "resolved": "https://registry.npmjs.org/decompress-response/-/decompress-response-6.0.0.tgz", + "integrity": "sha512-aW35yZM6Bb/4oJlZncMH2LCoZtJXTRxES17vE3hoRiowU2kWHaJKFkSBDnDR+cm9J+9QhXmREyIfv0pji9ejCQ==", + "dev": true, + "requires": { + "mimic-response": "^3.1.0" + }, + "dependencies": { + "mimic-response": { + "version": "3.1.0", + "resolved": "https://registry.npmjs.org/mimic-response/-/mimic-response-3.1.0.tgz", + "integrity": "sha512-z0yWI+4FDrrweS8Zmt4Ej5HdJmky15+L2e6Wgn3+iK5fWzb6T3fhNFq2+MeTRb064c6Wr4N/wv0DzQTjNzHNGQ==", + "dev": true + } + } + }, + "dedent": { + "version": "0.7.0", + "resolved": "https://registry.npmjs.org/dedent/-/dedent-0.7.0.tgz", + "integrity": "sha512-Q6fKUPqnAHAyhiUgFU7BUzLiv0kd8saH9al7tnu5Q/okj6dnupxyTgFIBjVzJATdfIAm9NAsvXNzjaKa+bxVyA==", + "dev": true + }, + "deep-extend": { + "version": "0.6.0", + "resolved": "https://registry.npmjs.org/deep-extend/-/deep-extend-0.6.0.tgz", + "integrity": "sha512-LOHxIOaPYdHlJRtCQfDIVZtfw/ufM8+rVj649RIHzcm/vGwQRXFt6OPqIFWsm2XEMrNIEtWR64sY1LEKD2vAOA==", + "dev": true + }, + "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 + }, + "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, + "requires": { + "clone": "^1.0.2" + } + }, + "defer-to-connect": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/defer-to-connect/-/defer-to-connect-2.0.1.tgz", + "integrity": "sha512-4tvttepXG1VaYGrRibk5EwJd1t4udunSOVMdLSAL6mId1ix438oPwPZMALY41FCijukO1L0twNcGsdzS7dHgDg==", + "dev": true + }, + "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 + }, + "delayed-stream": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/delayed-stream/-/delayed-stream-1.0.0.tgz", + "integrity": "sha512-ZySD7Nf91aLB0RxL4KGrKHBXl7Eds1DAmEdcoVawXnLD7SDhpNgtuII2aAkg7a7QS41jxPSZ17p4VdGnMHk3MQ==", + "dev": true + }, + "delegates": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/delegates/-/delegates-1.0.0.tgz", + "integrity": "sha512-bd2L678uiWATM6m5Z1VzNCErI3jiGzt6HGY8OVICs40JQq/HALfbyNJmp0UDakEY4pMMaN0Ly5om/B1VI/+xfQ==", + "dev": true + }, + "depd": { + "version": "1.1.2", + "resolved": "https://registry.npmjs.org/depd/-/depd-1.1.2.tgz", + "integrity": "sha512-7emPTl6Dpo6JRXOXjLRxck+FlLRX5847cLKEn00PLAgc3g2hTZZgr+e4c2v6QpSmLeFP3n5yUo7ft6avBK/5jQ==", + "dev": true + }, + "deprecation": { + "version": "2.3.1", + "resolved": "https://registry.npmjs.org/deprecation/-/deprecation-2.3.1.tgz", + "integrity": "sha512-xmHIy4F3scKVwMsQ4WnVaS8bHOx0DmVwRywosKhaILI0ywMDWPtBSku2HNxRvF7jtwDRsoEwYQSfbxj8b7RlJQ==", + "dev": true + }, + "detect-indent": { + "version": "6.1.0", + "resolved": "https://registry.npmjs.org/detect-indent/-/detect-indent-6.1.0.tgz", + "integrity": "sha512-reYkTUJAZb9gUuZ2RvVCNhVHdg62RHnJ7WJl8ftMi4diZ6NWlciOzQN88pUhSELEwflJht4oQDv0F0BMlwaYtA==", + "dev": true + }, + "dezalgo": { + "version": "1.0.4", + "resolved": "https://registry.npmjs.org/dezalgo/-/dezalgo-1.0.4.tgz", + "integrity": "sha512-rXSP0bf+5n0Qonsb+SVVfNfIsimO4HEtmnIpPHY8Q1UCzKlQrDMfdobr8nJOOsRgWCyMRqeSBQzmWUMq7zvVig==", + "dev": true, + "requires": { + "asap": "^2.0.0", + "wrappy": "1" + } + }, + "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, + "requires": { + "path-type": "^4.0.0" + } + }, + "doctrine": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/doctrine/-/doctrine-3.0.0.tgz", + "integrity": "sha512-yS+Q5i3hBf7GBkd4KG8a7eBNNWNGLTaEwwYWUijIYM7zrlYDM0BFXHjjPWlWZ1Rg7UaddZeIDmi9jF3HmqiQ2w==", + "dev": true, + "requires": { + "esutils": "^2.0.2" + } + }, + "dot-prop": { + "version": "6.0.1", + "resolved": "https://registry.npmjs.org/dot-prop/-/dot-prop-6.0.1.tgz", + "integrity": "sha512-tE7ztYzXHIeyvc7N+hR3oi7FIbf/NIjVP9hmAt3yMXzrQ072/fpjGLx2GxNxGxUl5V73MEqYzioOMoVhGMJ5cA==", + "dev": true, + "requires": { + "is-obj": "^2.0.0" + } + }, + "dotenv": { + "version": "10.0.0", + "resolved": "https://registry.npmjs.org/dotenv/-/dotenv-10.0.0.tgz", + "integrity": "sha512-rlBi9d8jpv9Sf1klPjNfFAuWDjKLwTIJJ/VxtoTwIR6hnZxcEOQCZg2oIL3MWBYw5GpUDKOEnND7LXTbIpQ03Q==", + "dev": true + }, + "duplexer": { + "version": "0.1.2", + "resolved": "https://registry.npmjs.org/duplexer/-/duplexer-0.1.2.tgz", + "integrity": "sha512-jtD6YG370ZCIi/9GTaJKQxWTZD045+4R4hTk/x1UyoqadyJ9x9CgSi1RlVDQF8U2sxLLSnFkCaMihqljHIWgMg==", + "dev": true + }, + "eastasianwidth": { + "version": "0.2.0", + "resolved": "https://registry.npmjs.org/eastasianwidth/-/eastasianwidth-0.2.0.tgz", + "integrity": "sha512-I88TYZWc9XiYHRQ4/3c5rjjfgkjhLyW2luGIheGERbNQ6OY7yTybanSpDXZa8y7VUP9YmDcYa+eyq4ca7iLqWA==", + "dev": true + }, + "ejs": { + "version": "3.1.8", + "resolved": "https://registry.npmjs.org/ejs/-/ejs-3.1.8.tgz", + "integrity": "sha512-/sXZeMlhS0ArkfX2Aw780gJzXSMPnKjtspYZv+f3NiKLlubezAHDU5+9xz6gd3/NhG3txQCo6xlglmTS+oTGEQ==", + "dev": true, + "requires": { + "jake": "^10.8.5" + } + }, + "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 + }, + "encoding": { + "version": "0.1.13", + "resolved": "https://registry.npmjs.org/encoding/-/encoding-0.1.13.tgz", + "integrity": "sha512-ETBauow1T35Y/WZMkio9jiM0Z5xjHHmJ4XmjZOq1l/dXz3lr2sRn87nJy20RupqSh1F2m3HHPSp8ShIPQJrJ3A==", + "dev": true, + "optional": true, + "requires": { + "iconv-lite": "^0.6.2" + }, + "dependencies": { + "iconv-lite": { + "version": "0.6.3", + "resolved": "https://registry.npmjs.org/iconv-lite/-/iconv-lite-0.6.3.tgz", + "integrity": "sha512-4fCk79wshMdzMp2rH06qWrJE4iolqLhCUH+OiuIgU++RB0+94NlDL81atO7GX55uUKueo0txHNtvEyI6D7WdMw==", + "dev": true, + "optional": true, + "requires": { + "safer-buffer": ">= 2.1.2 < 3.0.0" + } + } + } + }, + "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, + "requires": { + "once": "^1.4.0" + } + }, + "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, + "requires": { + "ansi-colors": "^4.1.1" + } + }, + "env-paths": { + "version": "2.2.1", + "resolved": "https://registry.npmjs.org/env-paths/-/env-paths-2.2.1.tgz", + "integrity": "sha512-+h1lkLKhZMTYjog1VEpJNG7NZJWcuc2DDk/qsqSTRRCOXiLjeQ1d1/udrUGhqMxUgAlwKNZ0cf2uqan5GLuS2A==", + "dev": true + }, + "envinfo": { + "version": "7.8.1", + "resolved": "https://registry.npmjs.org/envinfo/-/envinfo-7.8.1.tgz", + "integrity": "sha512-/o+BXHmB7ocbHEAs6F2EnG0ogybVVUdkRunTT2glZU9XAaGmhqskrvKwqXuDfNjEO0LZKWdejEEpnq8aM0tOaw==", + "dev": true + }, + "err-code": { + "version": "2.0.3", + "resolved": "https://registry.npmjs.org/err-code/-/err-code-2.0.3.tgz", + "integrity": "sha512-2bmlRpNKBxT/CRmPOlyISQpNj+qSeYvcym/uT0Jx2bMOlKLtSy1ZmLuVxSEKKyor/N5yhvp/ZiG1oE3DEYMSFA==", + "dev": true + }, + "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, + "requires": { + "is-arrayish": "^0.2.1" + } + }, + "escalade": { + "version": "3.1.1", + "resolved": "https://registry.npmjs.org/escalade/-/escalade-3.1.1.tgz", + "integrity": "sha512-k0er2gUkLf8O0zKJiAhmkTnJlTvINGv7ygDNPbeIsX/TJjGJZHuh9B2UxbsaEkmlEo9MfhrSzmhIlhRlI2GXnw==", + "dev": true + }, + "escape-goat": { + "version": "4.0.0", + "resolved": "https://registry.npmjs.org/escape-goat/-/escape-goat-4.0.0.tgz", + "integrity": "sha512-2Sd4ShcWxbx6OY1IHyla/CVNwvg7XwZVoXZHcSu9w9SReNP1EzzD5T8NWKIR38fIqEns9kDWKUQTXXAmlDrdPg==", + "dev": true + }, + "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 + }, + "eslint": { + "version": "8.25.0", + "resolved": "https://registry.npmjs.org/eslint/-/eslint-8.25.0.tgz", + "integrity": "sha512-DVlJOZ4Pn50zcKW5bYH7GQK/9MsoQG2d5eDH0ebEkE8PbgzTTmtt/VTH9GGJ4BfeZCpBLqFfvsjX35UacUL83A==", + "dev": true, + "requires": { + "@eslint/eslintrc": "^1.3.3", + "@humanwhocodes/config-array": "^0.10.5", + "@humanwhocodes/module-importer": "^1.0.1", + "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.1", + "globals": "^13.15.0", + "globby": "^11.1.0", + "grapheme-splitter": "^1.0.4", + "ignore": "^5.2.0", + "import-fresh": "^3.0.0", + "imurmurhash": "^0.1.4", + "is-glob": "^4.0.0", + "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" + }, + "dependencies": { + "ajv": { + "version": "6.12.6", + "resolved": "https://registry.npmjs.org/ajv/-/ajv-6.12.6.tgz", + "integrity": "sha512-j3fVLgvTo527anyYyJOGTYJbG+vnnQYvE0m5mmkc1TK+nxAppkCLMIL0aZ4dblVCNoGShhm+kzE4ZUykBoMg4g==", + "dev": true, + "requires": { + "fast-deep-equal": "^3.1.1", + "fast-json-stable-stringify": "^2.0.0", + "json-schema-traverse": "^0.4.1", + "uri-js": "^4.2.2" + } + }, + "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, + "requires": { + "esrecurse": "^4.3.0", + "estraverse": "^5.2.0" + } + }, + "estraverse": { + "version": "5.3.0", + "resolved": "https://registry.npmjs.org/estraverse/-/estraverse-5.3.0.tgz", + "integrity": "sha512-MMdARuVEQziNTeJD8DgMqmhwR11BRQ/cBP+pLtYdSTnf3MIO8fFeiINEbX36ZdNlfU/7A9f3gUw49B3oQsvwBA==", + "dev": true + }, + "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 + } + } + }, + "eslint-config-prettier": { + "version": "8.5.0", + "resolved": "https://registry.npmjs.org/eslint-config-prettier/-/eslint-config-prettier-8.5.0.tgz", + "integrity": "sha512-obmWKLUNCnhtQRKc+tmnYuQl0pFU1ibYJQ5BGhTVB08bHe9wC8qUeG7c08dj9XX+AuPj1YSGSQIHl1pnDHZR0Q==", + "dev": true, + "requires": {} + }, + "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, + "requires": { + "prettier-linter-helpers": "^1.0.0" + } + }, + "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, + "requires": { + "esrecurse": "^4.3.0", + "estraverse": "^4.1.1" + } + }, + "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, + "requires": { + "eslint-visitor-keys": "^2.0.0" + }, + "dependencies": { + "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 + } + } + }, + "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 + }, + "espree": { + "version": "9.4.0", + "resolved": "https://registry.npmjs.org/espree/-/espree-9.4.0.tgz", + "integrity": "sha512-DQmnRpLj7f6TgN/NYb0MTzJXL+vJF9h3pHy4JhCIs3zwcgez8xmGg3sXHcEO97BrmO2OSvCwMdfdlyl+E9KjOw==", + "dev": true, + "requires": { + "acorn": "^8.8.0", + "acorn-jsx": "^5.3.2", + "eslint-visitor-keys": "^3.3.0" + } + }, + "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 + }, + "esquery": { + "version": "1.4.0", + "resolved": "https://registry.npmjs.org/esquery/-/esquery-1.4.0.tgz", + "integrity": "sha512-cCDispWt5vHHtwMY2YrAQ4ibFkAL8RbH5YGBnZBc90MolvvfkkQcJro/aZiAQUlQ3qgrYS6D6v8Gc5G5CQsc9w==", + "dev": true, + "requires": { + "estraverse": "^5.1.0" + }, + "dependencies": { + "estraverse": { + "version": "5.3.0", + "resolved": "https://registry.npmjs.org/estraverse/-/estraverse-5.3.0.tgz", + "integrity": "sha512-MMdARuVEQziNTeJD8DgMqmhwR11BRQ/cBP+pLtYdSTnf3MIO8fFeiINEbX36ZdNlfU/7A9f3gUw49B3oQsvwBA==", + "dev": true + } + } + }, + "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, + "requires": { + "estraverse": "^5.2.0" + }, + "dependencies": { + "estraverse": { + "version": "5.3.0", + "resolved": "https://registry.npmjs.org/estraverse/-/estraverse-5.3.0.tgz", + "integrity": "sha512-MMdARuVEQziNTeJD8DgMqmhwR11BRQ/cBP+pLtYdSTnf3MIO8fFeiINEbX36ZdNlfU/7A9f3gUw49B3oQsvwBA==", + "dev": true + } + } + }, + "estraverse": { + "version": "4.3.0", + "resolved": "https://registry.npmjs.org/estraverse/-/estraverse-4.3.0.tgz", + "integrity": "sha512-39nnKffWz8xN1BU/2c79n9nB9HDzo0niYUqx6xyqUnyoAnQyyWpOTdZEeiCch8BBu515t4wp9ZmgVfVhn9EBpw==", + "dev": true + }, + "esutils": { + "version": "2.0.3", + "resolved": "https://registry.npmjs.org/esutils/-/esutils-2.0.3.tgz", + "integrity": "sha512-kVscqXk4OCp68SZ0dkgEKVi6/8ij300KBWTJq32P/dYeWTSwK41WyTxalN1eRmA5Z9UU/LX9D7FWSmV9SAYx6g==", + "dev": true + }, + "eventemitter3": { + "version": "4.0.7", + "resolved": "https://registry.npmjs.org/eventemitter3/-/eventemitter3-4.0.7.tgz", + "integrity": "sha512-8guHBZCwKnFhYdHr2ysuRWErTwhoN2X8XELRlrRwpmfeY2jjuUN4taQMsULKUVo1K4DvZl+0pgfyoysHxvmvEw==", + "dev": true + }, + "execa": { + "version": "5.1.1", + "resolved": "https://registry.npmjs.org/execa/-/execa-5.1.1.tgz", + "integrity": "sha512-8uSpZZocAZRBAPIEINJj3Lo9HyGitllczc27Eh5YYojjMFMn8yHMDMaUHE2Jqfq05D/wucwI4JGURyXt1vchyg==", + "dev": true, + "requires": { + "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" + } + }, + "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, + "requires": { + "chardet": "^0.7.0", + "iconv-lite": "^0.4.24", + "tmp": "^0.0.33" + } + }, + "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 + }, + "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 + }, + "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, + "requires": { + "@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" + }, + "dependencies": { + "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, + "requires": { + "is-glob": "^4.0.1" + } + } + } + }, + "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 + }, + "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 + }, + "fast-memoize": { + "version": "2.5.2", + "resolved": "https://registry.npmjs.org/fast-memoize/-/fast-memoize-2.5.2.tgz", + "integrity": "sha512-Ue0LwpDYErFbmNnZSF0UH6eImUwDmogUO1jyE+JbN2gsQz/jICm1Ve7t9QT0rNSsfJt+Hs4/S3GnsDVjL4HVrw==", + "dev": true + }, + "fastq": { + "version": "1.13.0", + "resolved": "https://registry.npmjs.org/fastq/-/fastq-1.13.0.tgz", + "integrity": "sha512-YpkpUnK8od0o1hmeSc7UUs/eB/vIPWJYjKck2QKIzAf71Vm1AAQ3EbuZB3g2JIy+pg+ERD0vqI79KyZiB2e2Nw==", + "dev": true, + "requires": { + "reusify": "^1.0.4" + } + }, + "figures": { + "version": "3.2.0", + "resolved": "https://registry.npmjs.org/figures/-/figures-3.2.0.tgz", + "integrity": "sha512-yaduQFRKLXYOGgEn6AZau90j3ggSOyiqXU0F9JZfeXYhNa+Jk4X+s45A2zg5jns87GAFa34BBm2kXw4XpNcbdg==", + "dev": true, + "requires": { + "escape-string-regexp": "^1.0.5" + }, + "dependencies": { + "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 + } + } + }, + "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, + "requires": { + "flat-cache": "^3.0.4" + } + }, + "filelist": { + "version": "1.0.4", + "resolved": "https://registry.npmjs.org/filelist/-/filelist-1.0.4.tgz", + "integrity": "sha512-w1cEuf3S+DrLCQL7ET6kz+gmlJdbq9J7yXCSjK/OZCPA+qEN1WyF4ZAf0YYJa4/shHJra2t/d/r8SV4Ji+x+8Q==", + "dev": true, + "requires": { + "minimatch": "^5.0.1" + }, + "dependencies": { + "brace-expansion": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/brace-expansion/-/brace-expansion-2.0.1.tgz", + "integrity": "sha512-XnAIvQ8eM+kC6aULx6wuQiwVsnzsi9d3WxzV3FpWTGA19F621kwdbsAcFKXgKUHZWsy+mY6iL1sHTxWEFCytDA==", + "dev": true, + "requires": { + "balanced-match": "^1.0.0" + } + }, + "minimatch": { + "version": "5.1.0", + "resolved": "https://registry.npmjs.org/minimatch/-/minimatch-5.1.0.tgz", + "integrity": "sha512-9TPBGGak4nHfGZsPBohm9AWg6NoT7QTCehS3BIJABslyZbzxfV78QM2Y6+i741OPZIafFAaiiEMh5OyIrJPgtg==", + "dev": true, + "requires": { + "brace-expansion": "^2.0.1" + } + } + } + }, + "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, + "requires": { + "to-regex-range": "^5.0.1" + } + }, + "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, + "requires": { + "locate-path": "^6.0.0", + "path-exists": "^4.0.0" + } + }, + "flat": { + "version": "5.0.2", + "resolved": "https://registry.npmjs.org/flat/-/flat-5.0.2.tgz", + "integrity": "sha512-b6suED+5/3rTpUBdG1gupIl8MPFCAMA0QXwmljLhvCUKcUvdE4gWky9zpuGCcXHOsz4J9wPGNWq6OKpmIzz3hQ==", + "dev": true + }, + "flat-cache": { + "version": "3.0.4", + "resolved": "https://registry.npmjs.org/flat-cache/-/flat-cache-3.0.4.tgz", + "integrity": "sha512-dm9s5Pw7Jc0GvMYbshN6zchCA9RgQlzzEZX3vylR9IqFfS8XciblUXOKfW6SiuJ0e13eDYZoZV5wdrev7P3Nwg==", + "dev": true, + "requires": { + "flatted": "^3.1.0", + "rimraf": "^3.0.2" + } + }, + "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 + }, + "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 + }, + "foreground-child": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/foreground-child/-/foreground-child-2.0.0.tgz", + "integrity": "sha512-dCIq9FpEcyQyXKCkyzmlPTFNgrCzPudOe+mhvJU5zAtlBnGVy2yKxtfsxK2tQBThwq225jcvBjpw1Gr40uzZCA==", + "dev": true, + "requires": { + "cross-spawn": "^7.0.0", + "signal-exit": "^3.0.2" + } + }, + "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, + "requires": { + "asynckit": "^0.4.0", + "combined-stream": "^1.0.8", + "mime-types": "^2.1.12" + } + }, + "form-data-encoder": { + "version": "2.1.3", + "resolved": "https://registry.npmjs.org/form-data-encoder/-/form-data-encoder-2.1.3.tgz", + "integrity": "sha512-KqU0nnPMgIJcCOFTNJFEA8epcseEaoox4XZffTgy8jlI6pL/5EFyR54NRG7CnCJN0biY7q52DO3MH6/sJ/TKlQ==", + "dev": true + }, + "fp-and-or": { + "version": "0.1.3", + "resolved": "https://registry.npmjs.org/fp-and-or/-/fp-and-or-0.1.3.tgz", + "integrity": "sha512-wJaE62fLaB3jCYvY2ZHjZvmKK2iiLiiehX38rz5QZxtdN8fVPJDeZUiVvJrHStdTc+23LHlyZuSEKgFc0pxi2g==", + "dev": true + }, + "fs-constants": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/fs-constants/-/fs-constants-1.0.0.tgz", + "integrity": "sha512-y6OAwoSIf7FyjMIv94u+b5rdheZEjzR63GTyZJm5qh4Bi+2YgwLCcI/fPFZkL5PSixOt6ZNKm+w+Hfp/Bciwow==", + "dev": true + }, + "fs-extra": { + "version": "9.1.0", + "resolved": "https://registry.npmjs.org/fs-extra/-/fs-extra-9.1.0.tgz", + "integrity": "sha512-hcg3ZmepS30/7BSFqRvoo3DOMQu7IjqxO5nCDt+zM9XWjb33Wg7ziNT+Qvqbuc3+gWpzO02JubVyk2G4Zvo1OQ==", + "dev": true, + "requires": { + "at-least-node": "^1.0.0", + "graceful-fs": "^4.2.0", + "jsonfile": "^6.0.1", + "universalify": "^2.0.0" + } + }, + "fs-minipass": { + "version": "2.1.0", + "resolved": "https://registry.npmjs.org/fs-minipass/-/fs-minipass-2.1.0.tgz", + "integrity": "sha512-V/JgOLFCS+R6Vcq0slCuaeWEdNC3ouDlJMNIsacH2VtALiu9mV4LPrHc5cDl8k5aw6J8jwgWWpiTo5RYhmIzvg==", + "dev": true, + "requires": { + "minipass": "^3.0.0" + } + }, + "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 + }, + "fsevents": { + "version": "2.3.2", + "resolved": "https://registry.npmjs.org/fsevents/-/fsevents-2.3.2.tgz", + "integrity": "sha512-xiqMQR4xAeHTuB9uWm+fFRcIOgKBMiOBP+eXiyT7jsgVCq1bkVygt00oASowB7EdtpOHaaPgKt812P9ab+DDKA==", + "dev": true, + "optional": true + }, + "function-bind": { + "version": "1.1.1", + "resolved": "https://registry.npmjs.org/function-bind/-/function-bind-1.1.1.tgz", + "integrity": "sha512-yIovAzMX49sF8Yl58fSCWJ5svSLuaibPxXQJFLmBObTuCr0Mf1KiPopGM9NiFjiYBCbfaa2Fh6breQ6ANVTI0A==", + "dev": true + }, + "gauge": { + "version": "4.0.4", + "resolved": "https://registry.npmjs.org/gauge/-/gauge-4.0.4.tgz", + "integrity": "sha512-f9m+BEN5jkg6a0fZjleidjN51VE1X+mPFQ2DJ0uv1V39oCLCbsGe6yjbBnp7eK7z/+GAon99a3nHuqbuuthyPg==", + "dev": true, + "requires": { + "aproba": "^1.0.3 || ^2.0.0", + "color-support": "^1.1.3", + "console-control-strings": "^1.1.0", + "has-unicode": "^2.0.1", + "signal-exit": "^3.0.7", + "string-width": "^4.2.3", + "strip-ansi": "^6.0.1", + "wide-align": "^1.1.5" + } + }, + "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 + }, + "get-pkg-repo": { + "version": "4.2.1", + "resolved": "https://registry.npmjs.org/get-pkg-repo/-/get-pkg-repo-4.2.1.tgz", + "integrity": "sha512-2+QbHjFRfGB74v/pYWjd5OhU3TDIC2Gv/YKUTk/tCvAz0pkn/Mz6P3uByuBimLOcPvN2jYdScl3xGFSrx0jEcA==", + "dev": true, + "requires": { + "@hutson/parse-repository-url": "^3.0.0", + "hosted-git-info": "^4.0.0", + "through2": "^2.0.0", + "yargs": "^16.2.0" + }, + "dependencies": { + "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, + "requires": { + "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" + } + }, + "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 + }, + "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, + "requires": { + "safe-buffer": "~5.1.0" + } + }, + "through2": { + "version": "2.0.5", + "resolved": "https://registry.npmjs.org/through2/-/through2-2.0.5.tgz", + "integrity": "sha512-/mrRod8xqpA+IHSLyGCQ2s8SPHiCDEeQJSep1jqLYeEUClOFG2Qsh+4FU6G9VeqpZnGW/Su8LQGc4YKni5rYSQ==", + "dev": true, + "requires": { + "readable-stream": "~2.3.6", + "xtend": "~4.0.1" + } + } + } + }, + "get-port": { + "version": "5.1.1", + "resolved": "https://registry.npmjs.org/get-port/-/get-port-5.1.1.tgz", + "integrity": "sha512-g/Q1aTSDOxFpchXC4i8ZWvxA1lnPqx/JHqcpIw0/LX9T8x/GBbi6YnlN5nhaKIFkT8oFsscUKgDJYxfwfS6QsQ==", + "dev": true + }, + "get-stdin": { + "version": "8.0.0", + "resolved": "https://registry.npmjs.org/get-stdin/-/get-stdin-8.0.0.tgz", + "integrity": "sha512-sY22aA6xchAzprjyqmSEQv4UbAAzRN0L2dQB0NlN5acTTK9Don6nhoc3eAbUnpZiCANAMfd/+40kVdKfFygohg==", + "dev": true + }, + "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 + }, + "git-raw-commits": { + "version": "2.0.11", + "resolved": "https://registry.npmjs.org/git-raw-commits/-/git-raw-commits-2.0.11.tgz", + "integrity": "sha512-VnctFhw+xfj8Va1xtfEqCUD2XDrbAPSJx+hSrE5K7fGdjZruW7XV+QOrN7LF/RJyvspRiD2I0asWsxFp0ya26A==", + "dev": true, + "requires": { + "dargs": "^7.0.0", + "lodash": "^4.17.15", + "meow": "^8.0.0", + "split2": "^3.0.0", + "through2": "^4.0.0" + } + }, + "git-remote-origin-url": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/git-remote-origin-url/-/git-remote-origin-url-2.0.0.tgz", + "integrity": "sha512-eU+GGrZgccNJcsDH5LkXR3PB9M958hxc7sbA8DFJjrv9j4L2P/eZfKhM+QD6wyzpiv+b1BpK0XrYCxkovtjSLw==", + "dev": true, + "requires": { + "gitconfiglocal": "^1.0.0", + "pify": "^2.3.0" + }, + "dependencies": { + "pify": { + "version": "2.3.0", + "resolved": "https://registry.npmjs.org/pify/-/pify-2.3.0.tgz", + "integrity": "sha512-udgsAY+fTnvv7kI7aaxbqwWNb0AHiB0qBO89PZKPkoTmGOgdbrHDKD+0B2X4uTfJ/FT1R09r9gTsjUjNJotuog==", + "dev": true + } + } + }, + "git-semver-tags": { + "version": "4.1.1", + "resolved": "https://registry.npmjs.org/git-semver-tags/-/git-semver-tags-4.1.1.tgz", + "integrity": "sha512-OWyMt5zBe7xFs8vglMmhM9lRQzCWL3WjHtxNNfJTMngGym7pC1kh8sP6jevfydJ6LP3ZvGxfb6ABYgPUM0mtsA==", + "dev": true, + "requires": { + "meow": "^8.0.0", + "semver": "^6.0.0" + }, + "dependencies": { + "semver": { + "version": "6.3.0", + "resolved": "https://registry.npmjs.org/semver/-/semver-6.3.0.tgz", + "integrity": "sha512-b39TBaTSfV6yBrapU89p5fKekE2m/NwnDocOVruQFS1/veMgdzuPcnOM34M6CwxW8jH/lxEa5rBoDeUwu5HHTw==", + "dev": true + } + } + }, + "git-up": { + "version": "7.0.0", + "resolved": "https://registry.npmjs.org/git-up/-/git-up-7.0.0.tgz", + "integrity": "sha512-ONdIrbBCFusq1Oy0sC71F5azx8bVkvtZtMJAsv+a6lz5YAmbNnLD6HAB4gptHZVLPR8S2/kVN6Gab7lryq5+lQ==", + "dev": true, + "requires": { + "is-ssh": "^1.4.0", + "parse-url": "^8.1.0" + } + }, + "git-url-parse": { + "version": "13.1.0", + "resolved": "https://registry.npmjs.org/git-url-parse/-/git-url-parse-13.1.0.tgz", + "integrity": "sha512-5FvPJP/70WkIprlUZ33bm4UAaFdjcLkJLpWft1BeZKqwR0uhhNGoKwlUaPtVb4LxCSQ++erHapRak9kWGj+FCA==", + "dev": true, + "requires": { + "git-up": "^7.0.0" + } + }, + "gitconfiglocal": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/gitconfiglocal/-/gitconfiglocal-1.0.0.tgz", + "integrity": "sha512-spLUXeTAVHxDtKsJc8FkFVgFtMdEN9qPGpL23VfSHx4fP4+Ds097IXLvymbnDH8FnmxX5Nr9bPw3A+AQ6mWEaQ==", + "dev": true, + "requires": { + "ini": "^1.3.2" + } + }, + "glob": { + "version": "8.0.3", + "resolved": "https://registry.npmjs.org/glob/-/glob-8.0.3.tgz", + "integrity": "sha512-ull455NHSHI/Y1FqGaaYFaLGkNMMJbavMrEGFXG/PGrg6y7sutWHUHrz6gy6WEBH6akM1M414dWKCNs+IhKdiQ==", + "dev": true, + "requires": { + "fs.realpath": "^1.0.0", + "inflight": "^1.0.4", + "inherits": "2", + "minimatch": "^5.0.1", + "once": "^1.3.0" + }, + "dependencies": { + "brace-expansion": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/brace-expansion/-/brace-expansion-2.0.1.tgz", + "integrity": "sha512-XnAIvQ8eM+kC6aULx6wuQiwVsnzsi9d3WxzV3FpWTGA19F621kwdbsAcFKXgKUHZWsy+mY6iL1sHTxWEFCytDA==", + "dev": true, + "requires": { + "balanced-match": "^1.0.0" + } + }, + "minimatch": { + "version": "5.1.0", + "resolved": "https://registry.npmjs.org/minimatch/-/minimatch-5.1.0.tgz", + "integrity": "sha512-9TPBGGak4nHfGZsPBohm9AWg6NoT7QTCehS3BIJABslyZbzxfV78QM2Y6+i741OPZIafFAaiiEMh5OyIrJPgtg==", + "dev": true, + "requires": { + "brace-expansion": "^2.0.1" + } + } + } + }, + "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, + "requires": { + "is-glob": "^4.0.3" + } + }, + "global-dirs": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/global-dirs/-/global-dirs-3.0.0.tgz", + "integrity": "sha512-v8ho2DS5RiCjftj1nD9NmnfaOzTdud7RRnVd9kFNOjqZbISlx5DQ+OrTkywgd0dIt7oFCvKetZSHoHcP3sDdiA==", + "dev": true, + "requires": { + "ini": "2.0.0" + }, + "dependencies": { + "ini": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/ini/-/ini-2.0.0.tgz", + "integrity": "sha512-7PnF4oN3CvZF23ADhA5wRaYEQpJ8qygSkbtTXWBeXWXmEVRXK+1ITciHWwHhsjv1TmW0MgacIv6hEi5pX5NQdA==", + "dev": true + } + } + }, + "globals": { + "version": "13.17.0", + "resolved": "https://registry.npmjs.org/globals/-/globals-13.17.0.tgz", + "integrity": "sha512-1C+6nQRb1GwGMKm2dH/E7enFAMxGTmGI7/dEdhy/DNelv85w9B72t3uc5frtMNXIbzrarJJ/lTCjcaZwbLJmyw==", + "dev": true, + "requires": { + "type-fest": "^0.20.2" + }, + "dependencies": { + "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 + } + } + }, + "globby": { + "version": "11.1.0", + "resolved": "https://registry.npmjs.org/globby/-/globby-11.1.0.tgz", + "integrity": "sha512-jhIXaOzy1sb8IyocaruWSn1TjmnBVs8Ayhcy83rmxNJ8q2uWKCAj3CnJY+KpGSXCueAPc0i05kVvVKtP1t9S3g==", + "dev": true, + "requires": { + "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" + } + }, + "got": { + "version": "12.5.1", + "resolved": "https://registry.npmjs.org/got/-/got-12.5.1.tgz", + "integrity": "sha512-sD16AK8cCyUoPtKr/NMvLTFFa+T3i3S+zoiuvhq0HP2YiqBZA9AtlBjAdsQBsLBK7slPuvmfE0OxhGi7N5dD4w==", + "dev": true, + "requires": { + "@sindresorhus/is": "^5.2.0", + "@szmarczak/http-timer": "^5.0.1", + "cacheable-lookup": "^7.0.0", + "cacheable-request": "^10.2.1", + "decompress-response": "^6.0.0", + "form-data-encoder": "^2.1.2", + "get-stream": "^6.0.1", + "http2-wrapper": "^2.1.10", + "lowercase-keys": "^3.0.0", + "p-cancelable": "^3.0.0", + "responselike": "^3.0.0" + } + }, + "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 + }, + "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 + }, + "handlebars": { + "version": "4.7.7", + "resolved": "https://registry.npmjs.org/handlebars/-/handlebars-4.7.7.tgz", + "integrity": "sha512-aAcXm5OAfE/8IXkcZvCepKU3VzW1/39Fb5ZuqMtgI/hT8X2YgoMvBY5dLhq/cpOvw7Lk1nK/UF71aLG/ZnVYRA==", + "dev": true, + "requires": { + "minimist": "^1.2.5", + "neo-async": "^2.6.0", + "source-map": "^0.6.1", + "uglify-js": "^3.1.4", + "wordwrap": "^1.0.0" + } + }, + "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 + }, + "has": { + "version": "1.0.3", + "resolved": "https://registry.npmjs.org/has/-/has-1.0.3.tgz", + "integrity": "sha512-f2dvO0VU6Oej7RkWJGrehjbzMAjFp5/VKPp5tTpWIV4JHHZK1/BxbFRtf/siA2SWTe09caDmVtYYzWEIbBS4zw==", + "dev": true, + "requires": { + "function-bind": "^1.1.1" + } + }, + "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 + }, + "has-unicode": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/has-unicode/-/has-unicode-2.0.1.tgz", + "integrity": "sha512-8Rf9Y83NBReMnx0gFzA8JImQACstCYWUplepDa9xprwwtmgEZUF0h/i5xSA625zB/I37EtrswSST6OXxwaaIJQ==", + "dev": true + }, + "has-yarn": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/has-yarn/-/has-yarn-3.0.0.tgz", + "integrity": "sha512-IrsVwUHhEULx3R8f/aA8AHuEzAorplsab/v8HBzEiIukwq5i/EC+xmOW+HfP1OaDP+2JkgT1yILHN2O3UFIbcA==", + "dev": true + }, + "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, + "requires": { + "lru-cache": "^6.0.0" + }, + "dependencies": { + "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, + "requires": { + "yallist": "^4.0.0" + } + } + } + }, + "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 + }, + "http-cache-semantics": { + "version": "4.1.0", + "resolved": "https://registry.npmjs.org/http-cache-semantics/-/http-cache-semantics-4.1.0.tgz", + "integrity": "sha512-carPklcUh7ROWRK7Cv27RPtdhYhUsela/ue5/jKzjegVvXDqM2ILE9Q2BGn9JZJh1g87cp56su/FgQSzcWS8cQ==", + "dev": true + }, + "http-proxy-agent": { + "version": "5.0.0", + "resolved": "https://registry.npmjs.org/http-proxy-agent/-/http-proxy-agent-5.0.0.tgz", + "integrity": "sha512-n2hY8YdoRE1i7r6M0w9DIw5GgZN0G25P8zLCRQ8rjXtTU3vsNFBI/vWK/UIeE6g5MUUz6avwAPXmL6Fy9D/90w==", + "dev": true, + "requires": { + "@tootallnate/once": "2", + "agent-base": "6", + "debug": "4" + } + }, + "http2-wrapper": { + "version": "2.1.11", + "resolved": "https://registry.npmjs.org/http2-wrapper/-/http2-wrapper-2.1.11.tgz", + "integrity": "sha512-aNAk5JzLturWEUiuhAN73Jcbq96R7rTitAoXV54FYMatvihnpD2+6PUgU4ce3D/m5VDbw+F5CsyKSF176ptitQ==", + "dev": true, + "requires": { + "quick-lru": "^5.1.1", + "resolve-alpn": "^1.2.0" + }, + "dependencies": { + "quick-lru": { + "version": "5.1.1", + "resolved": "https://registry.npmjs.org/quick-lru/-/quick-lru-5.1.1.tgz", + "integrity": "sha512-WuyALRjWPDGtt/wzJiadO5AXY+8hZ80hVpe6MyivgraREW751X3SbhRvG3eLKOYN+8VEvqLcf3wdnt44Z4S4SA==", + "dev": true + } + } + }, + "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==", + "dev": true, + "requires": { + "agent-base": "6", + "debug": "4" + } + }, + "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 + }, + "humanize-ms": { + "version": "1.2.1", + "resolved": "https://registry.npmjs.org/humanize-ms/-/humanize-ms-1.2.1.tgz", + "integrity": "sha512-Fl70vYtsAFb/C06PTS9dZBo7ihau+Tu/DNCk/OyHhea07S+aeMWpFFkUaXRa8fI+ScZbEI8dfSxwY7gxZ9SAVQ==", + "dev": true, + "requires": { + "ms": "^2.0.0" + } + }, + "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, + "requires": { + "safer-buffer": ">= 2.1.2 < 3" + } + }, + "ieee754": { + "version": "1.2.1", + "resolved": "https://registry.npmjs.org/ieee754/-/ieee754-1.2.1.tgz", + "integrity": "sha512-dcyqhDvX1C46lXZcVqCpK+FtMRQVdIMN6/Df5js2zouUsqG7I6sFxitIC+7KYK29KdXOLHdu9zL4sFnoVQnqaA==", + "dev": true + }, + "ignore": { + "version": "5.2.0", + "resolved": "https://registry.npmjs.org/ignore/-/ignore-5.2.0.tgz", + "integrity": "sha512-CmxgYGiEPCLhfLnpPp1MoRmifwEIOgjcHXxOBjv7mY96c+eWScsOP9c112ZyLdWHi0FxHjI+4uVhKYp/gcdRmQ==", + "dev": true + }, + "ignore-walk": { + "version": "5.0.1", + "resolved": "https://registry.npmjs.org/ignore-walk/-/ignore-walk-5.0.1.tgz", + "integrity": "sha512-yemi4pMf51WKT7khInJqAvsIGzoqYXblnsz0ql8tM+yi1EKYTY1evX4NAbJrLL/Aanr2HyZeluqU+Oi7MGHokw==", + "dev": true, + "requires": { + "minimatch": "^5.0.1" + }, + "dependencies": { + "brace-expansion": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/brace-expansion/-/brace-expansion-2.0.1.tgz", + "integrity": "sha512-XnAIvQ8eM+kC6aULx6wuQiwVsnzsi9d3WxzV3FpWTGA19F621kwdbsAcFKXgKUHZWsy+mY6iL1sHTxWEFCytDA==", + "dev": true, + "requires": { + "balanced-match": "^1.0.0" + } + }, + "minimatch": { + "version": "5.1.0", + "resolved": "https://registry.npmjs.org/minimatch/-/minimatch-5.1.0.tgz", + "integrity": "sha512-9TPBGGak4nHfGZsPBohm9AWg6NoT7QTCehS3BIJABslyZbzxfV78QM2Y6+i741OPZIafFAaiiEMh5OyIrJPgtg==", + "dev": true, + "requires": { + "brace-expansion": "^2.0.1" + } + } + } + }, + "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, + "requires": { + "parent-module": "^1.0.0", + "resolve-from": "^4.0.0" + } + }, + "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 + }, + "import-local": { + "version": "3.1.0", + "resolved": "https://registry.npmjs.org/import-local/-/import-local-3.1.0.tgz", + "integrity": "sha512-ASB07uLtnDs1o6EHjKpX34BKYDSqnFerfTOJL2HvMqF70LnxpjkzDB8J44oT9pu4AMPkQwf8jl6szgvNd2tRIg==", + "dev": true, + "requires": { + "pkg-dir": "^4.2.0", + "resolve-cwd": "^3.0.0" + } + }, + "imurmurhash": { + "version": "0.1.4", + "resolved": "https://registry.npmjs.org/imurmurhash/-/imurmurhash-0.1.4.tgz", + "integrity": "sha512-JmXMZ6wuvDmLiHEml9ykzqO6lwFbof0GG4IkcGaENdCRDDmMVnny7s5HsIgHCbaq0w2MyPhDqkhTUgS2LU2PHA==", + "dev": true + }, + "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 + }, + "infer-owner": { + "version": "1.0.4", + "resolved": "https://registry.npmjs.org/infer-owner/-/infer-owner-1.0.4.tgz", + "integrity": "sha512-IClj+Xz94+d7irH5qRyfJonOdfTzuDaifE6ZPWfx0N0+/ATZCbuTPq2prFl526urkQd90WyUKIh1DfBQ2hMz9A==", + "dev": true + }, + "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, + "requires": { + "once": "^1.3.0", + "wrappy": "1" + } + }, + "inherits": { + "version": "2.0.4", + "resolved": "https://registry.npmjs.org/inherits/-/inherits-2.0.4.tgz", + "integrity": "sha512-k/vGaX4/Yla3WzyMCvTQOXYeIHvqOKtnqBduzTHpzpQZzAskKMhZ2K+EnBiSM9zGSoIFeMpXKxa4dYeZIQqewQ==", + "dev": true + }, + "ini": { + "version": "1.3.8", + "resolved": "https://registry.npmjs.org/ini/-/ini-1.3.8.tgz", + "integrity": "sha512-JV/yugV2uzW5iMRSiZAyDtQd+nxtUnjeLt0acNdw98kKLrvuRVyB80tsREOE7yvGVgalhZ6RNXCmEHkUKBKxew==", + "dev": true + }, + "init-package-json": { + "version": "3.0.2", + "resolved": "https://registry.npmjs.org/init-package-json/-/init-package-json-3.0.2.tgz", + "integrity": "sha512-YhlQPEjNFqlGdzrBfDNRLhvoSgX7iQRgSxgsNknRQ9ITXFT7UMfVMWhBTOh2Y+25lRnGrv5Xz8yZwQ3ACR6T3A==", + "dev": true, + "requires": { + "npm-package-arg": "^9.0.1", + "promzard": "^0.3.0", + "read": "^1.0.7", + "read-package-json": "^5.0.0", + "semver": "^7.3.5", + "validate-npm-package-license": "^3.0.4", + "validate-npm-package-name": "^4.0.0" + }, + "dependencies": { + "hosted-git-info": { + "version": "5.1.0", + "resolved": "https://registry.npmjs.org/hosted-git-info/-/hosted-git-info-5.1.0.tgz", + "integrity": "sha512-Ek+QmMEqZF8XrbFdwoDjSbm7rT23pCgEMOJmz6GPk/s4yH//RQfNPArhIxbguNxROq/+5lNBwCDHMhA903Kx1Q==", + "dev": true, + "requires": { + "lru-cache": "^7.5.1" + } + }, + "npm-package-arg": { + "version": "9.1.2", + "resolved": "https://registry.npmjs.org/npm-package-arg/-/npm-package-arg-9.1.2.tgz", + "integrity": "sha512-pzd9rLEx4TfNJkovvlBSLGhq31gGu2QDexFPWT19yCDh0JgnRhlBLNo5759N0AJmBk+kQ9Y/hXoLnlgFD+ukmg==", + "dev": true, + "requires": { + "hosted-git-info": "^5.0.0", + "proc-log": "^2.0.1", + "semver": "^7.3.5", + "validate-npm-package-name": "^4.0.0" + } + } + } + }, + "inquirer": { + "version": "8.2.4", + "resolved": "https://registry.npmjs.org/inquirer/-/inquirer-8.2.4.tgz", + "integrity": "sha512-nn4F01dxU8VeKfq192IjLsxu0/OmMZ4Lg3xKAns148rCaXP6ntAoEkVYZThWjwON8AlzdZZi6oqnhNbxUG9hVg==", + "dev": true, + "requires": { + "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" + } + }, + "ip": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/ip/-/ip-2.0.0.tgz", + "integrity": "sha512-WKa+XuLG1A1R0UWhl2+1XQSi+fZWMsYKffMZTTYsiZaUD8k2yDAj5atimTUD2TZkyCkNEeYE5NhFZmupOGtjYQ==", + "dev": true + }, + "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 + }, + "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, + "requires": { + "binary-extensions": "^2.0.0" + } + }, + "is-ci": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/is-ci/-/is-ci-2.0.0.tgz", + "integrity": "sha512-YfJT7rkpQB0updsdHLGWrvhBJfcfzNNawYDNIyQXJz0IViGf75O8EBPKSdvw2rF+LGCsX4FZ8tcr3b19LcZq4w==", + "dev": true, + "requires": { + "ci-info": "^2.0.0" + } + }, + "is-core-module": { + "version": "2.10.0", + "resolved": "https://registry.npmjs.org/is-core-module/-/is-core-module-2.10.0.tgz", + "integrity": "sha512-Erxj2n/LDAZ7H8WNJXd9tw38GYM3dv8rk8Zcs+jJuxYTW7sozH+SS8NtrSjVL1/vpLvWi1hxy96IzjJ3EHTJJg==", + "dev": true, + "requires": { + "has": "^1.0.3" + } + }, + "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 + }, + "is-extglob": { + "version": "2.1.1", + "resolved": "https://registry.npmjs.org/is-extglob/-/is-extglob-2.1.1.tgz", + "integrity": "sha512-SbKbANkN603Vi4jEZv49LeVJMn4yGwsbzZworEoyEiutsN3nJYdbO36zfhGJ6QEDpOZIFkDtnq5JRxmvl3jsoQ==", + "dev": true + }, + "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 + }, + "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, + "requires": { + "is-extglob": "^2.1.1" + } + }, + "is-installed-globally": { + "version": "0.4.0", + "resolved": "https://registry.npmjs.org/is-installed-globally/-/is-installed-globally-0.4.0.tgz", + "integrity": "sha512-iwGqO3J21aaSkC7jWnHP/difazwS7SFeIqxv6wEtLU8Y5KlzFTjyqcSIT0d8s4+dDhKytsk9PJZ2BkS5eZwQRQ==", + "dev": true, + "requires": { + "global-dirs": "^3.0.0", + "is-path-inside": "^3.0.2" + } + }, + "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 + }, + "is-lambda": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/is-lambda/-/is-lambda-1.0.1.tgz", + "integrity": "sha512-z7CMFGNrENq5iFB9Bqo64Xk6Y9sg+epq1myIcdHaGnbMTYOxvzsEtdYqQUylB7LxfkvgrrjP32T6Ywciio9UIQ==", + "dev": true + }, + "is-npm": { + "version": "6.0.0", + "resolved": "https://registry.npmjs.org/is-npm/-/is-npm-6.0.0.tgz", + "integrity": "sha512-JEjxbSmtPSt1c8XTkVrlujcXdKV1/tvuQ7GwKcAlyiVLeYFQ2VHat8xfrDJsIkhCdF/tZ7CiIR3sy141c6+gPQ==", + "dev": true + }, + "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 + }, + "is-obj": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/is-obj/-/is-obj-2.0.0.tgz", + "integrity": "sha512-drqDG3cbczxxEJRoOXcOjtdp1J/lyp1mNn0xaznRs8+muBhgQcrnbspox5X5fOw0HnMnbfDzvnEMEtqDEJEo8w==", + "dev": true + }, + "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 + }, + "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 + }, + "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 + }, + "is-ssh": { + "version": "1.4.0", + "resolved": "https://registry.npmjs.org/is-ssh/-/is-ssh-1.4.0.tgz", + "integrity": "sha512-x7+VxdxOdlV3CYpjvRLBv5Lo9OJerlYanjwFrPR9fuGPjCiNiCzFgAWpiLAohSbsnH4ZAys3SBh+hq5rJosxUQ==", + "dev": true, + "requires": { + "protocols": "^2.0.1" + } + }, + "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 + }, + "is-text-path": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/is-text-path/-/is-text-path-1.0.1.tgz", + "integrity": "sha512-xFuJpne9oFz5qDaodwmmG08e3CawH/2ZV8Qqza1Ko7Sk8POWbkRdwIoAWVhqvq0XeUzANEhKo2n0IXUGBm7A/w==", + "dev": true, + "requires": { + "text-extensions": "^1.0.0" + } + }, + "is-typedarray": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/is-typedarray/-/is-typedarray-1.0.0.tgz", + "integrity": "sha512-cyA56iCMHAh5CdzjJIa4aohJyeO1YbwLi3Jc35MmRU6poroFjIGZzUzupGiRPOjgHg9TLu43xbpwXk523fMxKA==", + "dev": true + }, + "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 + }, + "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, + "requires": { + "is-docker": "^2.0.0" + } + }, + "is-yarn-global": { + "version": "0.4.0", + "resolved": "https://registry.npmjs.org/is-yarn-global/-/is-yarn-global-0.4.0.tgz", + "integrity": "sha512-HneQBCrXGBy15QnaDfcn6OLoU8AQPAa0Qn0IeJR/QCo4E8dNZaGGwxpCwWyEBQC5QvFonP8d6t60iGpAHVAfNA==", + "dev": true + }, + "isarray": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/isarray/-/isarray-1.0.0.tgz", + "integrity": "sha512-VLghIWNM6ELQzo7zwmcg0NmTVyWKYjvIeM83yjp0wRDTmUnrM678fQbcKBo6n2CJEF0szoG//ytg+TKla89ALQ==", + "dev": true + }, + "isexe": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/isexe/-/isexe-2.0.0.tgz", + "integrity": "sha512-RHxMLp9lnKHGHRng9QFhRCMbYAcVpn69smSGcq3f36xjgVVWThj4qqLbTLlq7Ssj8B+fIQ1EuCEGI2lKsyQeIw==", + "dev": true + }, + "isobject": { + "version": "3.0.1", + "resolved": "https://registry.npmjs.org/isobject/-/isobject-3.0.1.tgz", + "integrity": "sha512-WhB9zCku7EGTj/HQQRz5aUQEUeoQZH2bWcltRErOpymJ4boYE6wL9Tbr23krRPSZ+C5zqNSrSw+Cc7sZZ4b7vg==", + "dev": true + }, + "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 + }, + "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, + "requires": { + "istanbul-lib-coverage": "^3.0.0", + "make-dir": "^3.0.0", + "supports-color": "^7.1.0" + } + }, + "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, + "requires": { + "html-escaper": "^2.0.0", + "istanbul-lib-report": "^3.0.0" + } + }, + "jake": { + "version": "10.8.5", + "resolved": "https://registry.npmjs.org/jake/-/jake-10.8.5.tgz", + "integrity": "sha512-sVpxYeuAhWt0OTWITwT98oyV0GsXyMlXCF+3L1SuafBVUIr/uILGRB+NqwkzhgXKvoJpDIpQvqkUALgdmQsQxw==", + "dev": true, + "requires": { + "async": "^3.2.3", + "chalk": "^4.0.2", + "filelist": "^1.0.1", + "minimatch": "^3.0.4" + } + }, + "jju": { + "version": "1.4.0", + "resolved": "https://registry.npmjs.org/jju/-/jju-1.4.0.tgz", + "integrity": "sha512-8wb9Yw966OSxApiCt0K3yNJL8pnNeIv+OEq2YMidz4FKP6nonSRoOXc80iXY4JaN2FC11B9qsNmDsm+ZOfMROA==", + "dev": true + }, + "js-sdsl": { + "version": "4.1.5", + "resolved": "https://registry.npmjs.org/js-sdsl/-/js-sdsl-4.1.5.tgz", + "integrity": "sha512-08bOAKweV2NUC1wqTtf3qZlnpOX/R2DU9ikpjOHs0H+ibQv3zpncVQg6um4uYtRtrwIX8M4Nh3ytK4HGlYAq7Q==", + "dev": true + }, + "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 + }, + "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, + "requires": { + "argparse": "^2.0.1" + } + }, + "json-buffer": { + "version": "3.0.1", + "resolved": "https://registry.npmjs.org/json-buffer/-/json-buffer-3.0.1.tgz", + "integrity": "sha512-4bV5BfR2mqfQTJm+V5tPPdf+ZpuhiIvTuAB5g8kcrXOZpTT/QwwVRWBywX1ozr6lEuPdbHxwaJlm9G6mI2sfSQ==", + "dev": true + }, + "json-parse-better-errors": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/json-parse-better-errors/-/json-parse-better-errors-1.0.2.tgz", + "integrity": "sha512-mrqyZKfX5EhL7hvqcV6WG1yYjnjeuYDzDhhcAAUrq8Po85NBQBJP+ZDUT75qZQ98IkUoBqdkExkukOU7Ts2wrw==", + "dev": true + }, + "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 + }, + "json-parse-helpfulerror": { + "version": "1.0.3", + "resolved": "https://registry.npmjs.org/json-parse-helpfulerror/-/json-parse-helpfulerror-1.0.3.tgz", + "integrity": "sha512-XgP0FGR77+QhUxjXkwOMkC94k3WtqEBfcnjWqhRd82qTat4SWKRE+9kUnynz/shm3I4ea2+qISvTIeGTNU7kJg==", + "dev": true, + "requires": { + "jju": "^1.1.0" + } + }, + "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 + }, + "json-stringify-nice": { + "version": "1.1.4", + "resolved": "https://registry.npmjs.org/json-stringify-nice/-/json-stringify-nice-1.1.4.tgz", + "integrity": "sha512-5Z5RFW63yxReJ7vANgW6eZFGWaQvnPE3WNmZoOJrSkGju2etKA2L5rrOa1sm877TVTFt57A80BH1bArcmlLfPw==", + "dev": true + }, + "json-stringify-safe": { + "version": "5.0.1", + "resolved": "https://registry.npmjs.org/json-stringify-safe/-/json-stringify-safe-5.0.1.tgz", + "integrity": "sha512-ZClg6AaYvamvYEE82d3Iyd3vSSIjQ+odgjaTzRuO3s7toCdFKczob2i0zCh7JE8kWn17yvAWhUVxvqGwUalsRA==", + "dev": true + }, + "json5": { + "version": "2.2.1", + "resolved": "https://registry.npmjs.org/json5/-/json5-2.2.1.tgz", + "integrity": "sha512-1hqLFMSrGHRHxav9q9gNjJ5EXznIxGVO09xQRrwplcS8qs28pZ8s8hupZAmqDwZUmVZ2Qb2jnyPOWcDH8m8dlA==", + "dev": true + }, + "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 + }, + "jsonfile": { + "version": "6.1.0", + "resolved": "https://registry.npmjs.org/jsonfile/-/jsonfile-6.1.0.tgz", + "integrity": "sha512-5dgndWOriYSm5cnYaJNhalLNDKOqFwyDB/rr1E9ZsGciGvKPs8R2xYGCacuf3z6K1YKDz182fd+fY3cn3pMqXQ==", + "dev": true, + "requires": { + "graceful-fs": "^4.1.6", + "universalify": "^2.0.0" + } + }, + "jsonlines": { + "version": "0.1.1", + "resolved": "https://registry.npmjs.org/jsonlines/-/jsonlines-0.1.1.tgz", + "integrity": "sha512-ekDrAGso79Cvf+dtm+mL8OBI2bmAOt3gssYs833De/C9NmIpWDWyUO4zPgB5x2/OhY366dkhgfPMYfwZF7yOZA==", + "dev": true + }, + "jsonparse": { + "version": "1.3.1", + "resolved": "https://registry.npmjs.org/jsonparse/-/jsonparse-1.3.1.tgz", + "integrity": "sha512-POQXvpdL69+CluYsillJ7SUhKvytYjW9vG/GKpnf+xP8UWgYEM/RaMzHHofbALDiKbbP1W8UEYmgGl39WkPZsg==", + "dev": true + }, + "JSONStream": { + "version": "1.3.5", + "resolved": "https://registry.npmjs.org/JSONStream/-/JSONStream-1.3.5.tgz", + "integrity": "sha512-E+iruNOY8VV9s4JEbe1aNEm6MiszPRr/UfcHMz0TQh1BXSxHK+ASV1R6W4HpjBhSeS+54PIsAMCBmwD06LLsqQ==", + "dev": true, + "requires": { + "jsonparse": "^1.2.0", + "through": ">=2.2.7 <3" + } + }, + "just-diff": { + "version": "5.1.1", + "resolved": "https://registry.npmjs.org/just-diff/-/just-diff-5.1.1.tgz", + "integrity": "sha512-u8HXJ3HlNrTzY7zrYYKjNEfBlyjqhdBkoyTVdjtn7p02RJD5NvR8rIClzeGA7t+UYP1/7eAkWNLU0+P3QrEqKQ==", + "dev": true + }, + "just-diff-apply": { + "version": "5.4.1", + "resolved": "https://registry.npmjs.org/just-diff-apply/-/just-diff-apply-5.4.1.tgz", + "integrity": "sha512-AAV5Jw7tsniWwih8Ly3fXxEZ06y+6p5TwQMsw0dzZ/wPKilzyDgdAnL0Ug4NNIquPUOh1vfFWEHbmXUqM5+o8g==", + "dev": true + }, + "keyv": { + "version": "4.5.0", + "resolved": "https://registry.npmjs.org/keyv/-/keyv-4.5.0.tgz", + "integrity": "sha512-2YvuMsA+jnFGtBareKqgANOEKe1mk3HKiXu2fRmAfyxG0MJAywNhi5ttWA3PMjl4NmpyjZNbFifR2vNjW1znfA==", + "dev": true, + "requires": { + "json-buffer": "3.0.1" + } + }, + "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 + }, + "kleur": { + "version": "4.1.5", + "resolved": "https://registry.npmjs.org/kleur/-/kleur-4.1.5.tgz", + "integrity": "sha512-o+NO+8WrRiQEE4/7nwRJhN1HWpVmJm511pBHUxPLtp0BUISzlBplORYSmTclCnJvQq2tKu/sgl3xVpkc7ZWuQQ==", + "dev": true + }, + "latest-version": { + "version": "7.0.0", + "resolved": "https://registry.npmjs.org/latest-version/-/latest-version-7.0.0.tgz", + "integrity": "sha512-KvNT4XqAMzdcL6ka6Tl3i2lYeFDgXNCuIX+xNx6ZMVR1dFq+idXd9FLKNMOIx0t9mJ9/HudyX4oZWXZQ0UJHeg==", + "dev": true, + "requires": { + "package-json": "^8.1.0" + } + }, + "lerna": { + "version": "5.6.2", + "resolved": "https://registry.npmjs.org/lerna/-/lerna-5.6.2.tgz", + "integrity": "sha512-Y0yMPslvnBnTZi7Nrs/gDyYZYauNf61xWNCehISHIORxZmmpoluNkcWTfcyb47is5uJQCv5QJX5xKKubbs+a6w==", + "dev": true, + "requires": { + "@lerna/add": "5.6.2", + "@lerna/bootstrap": "5.6.2", + "@lerna/changed": "5.6.2", + "@lerna/clean": "5.6.2", + "@lerna/cli": "5.6.2", + "@lerna/command": "5.6.2", + "@lerna/create": "5.6.2", + "@lerna/diff": "5.6.2", + "@lerna/exec": "5.6.2", + "@lerna/import": "5.6.2", + "@lerna/info": "5.6.2", + "@lerna/init": "5.6.2", + "@lerna/link": "5.6.2", + "@lerna/list": "5.6.2", + "@lerna/publish": "5.6.2", + "@lerna/run": "5.6.2", + "@lerna/version": "5.6.2", + "@nrwl/devkit": ">=14.8.1 < 16", + "import-local": "^3.0.2", + "inquirer": "^8.2.4", + "npmlog": "^6.0.2", + "nx": ">=14.8.1 < 16", + "typescript": "^3 || ^4" + } + }, + "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, + "requires": { + "prelude-ls": "^1.2.1", + "type-check": "~0.4.0" + } + }, + "libnpmaccess": { + "version": "6.0.4", + "resolved": "https://registry.npmjs.org/libnpmaccess/-/libnpmaccess-6.0.4.tgz", + "integrity": "sha512-qZ3wcfIyUoW0+qSFkMBovcTrSGJ3ZeyvpR7d5N9pEYv/kXs8sHP2wiqEIXBKLFrZlmM0kR0RJD7mtfLngtlLag==", + "dev": true, + "requires": { + "aproba": "^2.0.0", + "minipass": "^3.1.1", + "npm-package-arg": "^9.0.1", + "npm-registry-fetch": "^13.0.0" + }, + "dependencies": { + "hosted-git-info": { + "version": "5.1.0", + "resolved": "https://registry.npmjs.org/hosted-git-info/-/hosted-git-info-5.1.0.tgz", + "integrity": "sha512-Ek+QmMEqZF8XrbFdwoDjSbm7rT23pCgEMOJmz6GPk/s4yH//RQfNPArhIxbguNxROq/+5lNBwCDHMhA903Kx1Q==", + "dev": true, + "requires": { + "lru-cache": "^7.5.1" + } + }, + "npm-package-arg": { + "version": "9.1.2", + "resolved": "https://registry.npmjs.org/npm-package-arg/-/npm-package-arg-9.1.2.tgz", + "integrity": "sha512-pzd9rLEx4TfNJkovvlBSLGhq31gGu2QDexFPWT19yCDh0JgnRhlBLNo5759N0AJmBk+kQ9Y/hXoLnlgFD+ukmg==", + "dev": true, + "requires": { + "hosted-git-info": "^5.0.0", + "proc-log": "^2.0.1", + "semver": "^7.3.5", + "validate-npm-package-name": "^4.0.0" + } + } + } + }, + "libnpmpublish": { + "version": "6.0.5", + "resolved": "https://registry.npmjs.org/libnpmpublish/-/libnpmpublish-6.0.5.tgz", + "integrity": "sha512-LUR08JKSviZiqrYTDfywvtnsnxr+tOvBU0BF8H+9frt7HMvc6Qn6F8Ubm72g5hDTHbq8qupKfDvDAln2TVPvFg==", + "dev": true, + "requires": { + "normalize-package-data": "^4.0.0", + "npm-package-arg": "^9.0.1", + "npm-registry-fetch": "^13.0.0", + "semver": "^7.3.7", + "ssri": "^9.0.0" + }, + "dependencies": { + "hosted-git-info": { + "version": "5.1.0", + "resolved": "https://registry.npmjs.org/hosted-git-info/-/hosted-git-info-5.1.0.tgz", + "integrity": "sha512-Ek+QmMEqZF8XrbFdwoDjSbm7rT23pCgEMOJmz6GPk/s4yH//RQfNPArhIxbguNxROq/+5lNBwCDHMhA903Kx1Q==", + "dev": true, + "requires": { + "lru-cache": "^7.5.1" + } + }, + "normalize-package-data": { + "version": "4.0.1", + "resolved": "https://registry.npmjs.org/normalize-package-data/-/normalize-package-data-4.0.1.tgz", + "integrity": "sha512-EBk5QKKuocMJhB3BILuKhmaPjI8vNRSpIfO9woLC6NyHVkKKdVEdAO1mrT0ZfxNR1lKwCcTkuZfmGIFdizZ8Pg==", + "dev": true, + "requires": { + "hosted-git-info": "^5.0.0", + "is-core-module": "^2.8.1", + "semver": "^7.3.5", + "validate-npm-package-license": "^3.0.4" + } + }, + "npm-package-arg": { + "version": "9.1.2", + "resolved": "https://registry.npmjs.org/npm-package-arg/-/npm-package-arg-9.1.2.tgz", + "integrity": "sha512-pzd9rLEx4TfNJkovvlBSLGhq31gGu2QDexFPWT19yCDh0JgnRhlBLNo5759N0AJmBk+kQ9Y/hXoLnlgFD+ukmg==", + "dev": true, + "requires": { + "hosted-git-info": "^5.0.0", + "proc-log": "^2.0.1", + "semver": "^7.3.5", + "validate-npm-package-name": "^4.0.0" + } + } + } + }, + "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 + }, + "load-json-file": { + "version": "6.2.0", + "resolved": "https://registry.npmjs.org/load-json-file/-/load-json-file-6.2.0.tgz", + "integrity": "sha512-gUD/epcRms75Cw8RT1pUdHugZYM5ce64ucs2GEISABwkRsOQr0q2wm/MV2TKThycIe5e0ytRweW2RZxclogCdQ==", + "dev": true, + "requires": { + "graceful-fs": "^4.1.15", + "parse-json": "^5.0.0", + "strip-bom": "^4.0.0", + "type-fest": "^0.6.0" + }, + "dependencies": { + "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 + } + } + }, + "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, + "requires": { + "p-locate": "^5.0.0" + } + }, + "lodash": { + "version": "4.17.21", + "resolved": "https://registry.npmjs.org/lodash/-/lodash-4.17.21.tgz", + "integrity": "sha512-v2kDEe57lecTulaDIuNTPy3Ry4gLGJ6Z1O3vE1krgXZNrsQ+LFTGHVxVjcXPs17LhbZVGedAJv8XZ1tvj5FvSg==", + "dev": true + }, + "lodash.ismatch": { + "version": "4.4.0", + "resolved": "https://registry.npmjs.org/lodash.ismatch/-/lodash.ismatch-4.4.0.tgz", + "integrity": "sha512-fPMfXjGQEV9Xsq/8MTSgUf255gawYRbjwMyDbcvDhXgV7enSZA0hynz6vMPnpAb5iONEzBHBPsT+0zes5Z301g==", + "dev": true + }, + "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 + }, + "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, + "requires": { + "chalk": "^4.1.0", + "is-unicode-supported": "^0.1.0" + } + }, + "lowercase-keys": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/lowercase-keys/-/lowercase-keys-3.0.0.tgz", + "integrity": "sha512-ozCC6gdQ+glXOQsveKD0YsDy8DSQFjDTz4zyzEHNV5+JP5D62LmfDZ6o1cycFx9ouG940M5dE8C8CTewdj2YWQ==", + "dev": true + }, + "lru-cache": { + "version": "7.14.0", + "resolved": "https://registry.npmjs.org/lru-cache/-/lru-cache-7.14.0.tgz", + "integrity": "sha512-EIRtP1GrSJny0dqb50QXRUNBxHJhcpxHC++M5tD7RYbvLLn5KVWKsbyswSSqDuU15UFi3bgTQIY8nhDMeF6aDQ==", + "dev": true + }, + "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, + "requires": { + "semver": "^6.0.0" + }, + "dependencies": { + "semver": { + "version": "6.3.0", + "resolved": "https://registry.npmjs.org/semver/-/semver-6.3.0.tgz", + "integrity": "sha512-b39TBaTSfV6yBrapU89p5fKekE2m/NwnDocOVruQFS1/veMgdzuPcnOM34M6CwxW8jH/lxEa5rBoDeUwu5HHTw==", + "dev": true + } + } + }, + "make-fetch-happen": { + "version": "10.2.1", + "resolved": "https://registry.npmjs.org/make-fetch-happen/-/make-fetch-happen-10.2.1.tgz", + "integrity": "sha512-NgOPbRiaQM10DYXvN3/hhGVI2M5MtITFryzBGxHM5p4wnFxsVCbxkrBrDsk+EZ5OB4jEOT7AjDxtdF+KVEFT7w==", + "dev": true, + "requires": { + "agentkeepalive": "^4.2.1", + "cacache": "^16.1.0", + "http-cache-semantics": "^4.1.0", + "http-proxy-agent": "^5.0.0", + "https-proxy-agent": "^5.0.0", + "is-lambda": "^1.0.1", + "lru-cache": "^7.7.1", + "minipass": "^3.1.6", + "minipass-collect": "^1.0.2", + "minipass-fetch": "^2.0.3", + "minipass-flush": "^1.0.5", + "minipass-pipeline": "^1.2.4", + "negotiator": "^0.6.3", + "promise-retry": "^2.0.1", + "socks-proxy-agent": "^7.0.0", + "ssri": "^9.0.0" + } + }, + "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 + }, + "meow": { + "version": "8.1.2", + "resolved": "https://registry.npmjs.org/meow/-/meow-8.1.2.tgz", + "integrity": "sha512-r85E3NdZ+mpYk1C6RjPFEMSE+s1iZMuHtsHAqY0DT3jZczl0diWUZ8g6oU7h0M9cD2EL+PzaYghhCLzR0ZNn5Q==", + "dev": true, + "requires": { + "@types/minimist": "^1.2.0", + "camelcase-keys": "^6.2.2", + "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" + }, + "dependencies": { + "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, + "requires": { + "locate-path": "^5.0.0", + "path-exists": "^4.0.0" + } + }, + "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 + }, + "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, + "requires": { + "p-locate": "^4.1.0" + } + }, + "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, + "requires": { + "p-try": "^2.0.0" + } + }, + "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, + "requires": { + "p-limit": "^2.2.0" + } + }, + "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, + "requires": { + "@types/normalize-package-data": "^2.4.0", + "normalize-package-data": "^2.5.0", + "parse-json": "^5.0.0", + "type-fest": "^0.6.0" + }, + "dependencies": { + "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, + "requires": { + "hosted-git-info": "^2.1.4", + "resolve": "^1.10.0", + "semver": "2 || 3 || 4 || 5", + "validate-npm-package-license": "^3.0.1" + } + }, + "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 + } + } + }, + "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, + "requires": { + "find-up": "^4.1.0", + "read-pkg": "^5.2.0", + "type-fest": "^0.8.1" + }, + "dependencies": { + "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 + } + } + }, + "semver": { + "version": "5.7.1", + "resolved": "https://registry.npmjs.org/semver/-/semver-5.7.1.tgz", + "integrity": "sha512-sauaDf/PZdVgrLTNYHRtpXa1iRiKcaebiKQ1BJdpQlWH2lCvexQdX55snPFyK7QzpudqbCI0qXFfOasHdyNDGQ==", + "dev": true + }, + "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 + } + } + }, + "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 + }, + "merge2": { + "version": "1.4.1", + "resolved": "https://registry.npmjs.org/merge2/-/merge2-1.4.1.tgz", + "integrity": "sha512-8q7VEgMJW4J8tcfVPy8g09NcQwZdbwFEqhe/WZkoIzjn/3TGDwtOCYtXGxA3O8tPzpczCCDgv+P2P5y00ZJOOg==", + "dev": true + }, + "micromatch": { + "version": "4.0.5", + "resolved": "https://registry.npmjs.org/micromatch/-/micromatch-4.0.5.tgz", + "integrity": "sha512-DMy+ERcEW2q8Z2Po+WNXuw3c5YaUSFjAO5GsJqfEl7UjvtIuFKO6ZrKvcItdy98dwFI2N1tg3zNIdKaQT+aNdA==", + "dev": true, + "requires": { + "braces": "^3.0.2", + "picomatch": "^2.3.1" + } + }, + "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 + }, + "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, + "requires": { + "mime-db": "1.52.0" + } + }, + "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 + }, + "mimic-response": { + "version": "4.0.0", + "resolved": "https://registry.npmjs.org/mimic-response/-/mimic-response-4.0.0.tgz", + "integrity": "sha512-e5ISH9xMYU0DzrT+jl8q2ze9D6eWBto+I8CNpe+VI+K2J/F/k3PdkdTdz4wvGVH4NTpo+NRYTVIuMQEMMcsLqg==", + "dev": true + }, + "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 + }, + "minimatch": { + "version": "3.1.2", + "resolved": "https://registry.npmjs.org/minimatch/-/minimatch-3.1.2.tgz", + "integrity": "sha512-J7p63hRiAjw1NDEww1W7i37+ByIrOWO5XQQAzZ3VOcL0PNybwpfmV/N05zFAzwQ9USyEcX6t3UO+K5aqBQOIHw==", + "dev": true, + "requires": { + "brace-expansion": "^1.1.7" + } + }, + "minimist": { + "version": "1.2.7", + "resolved": "https://registry.npmjs.org/minimist/-/minimist-1.2.7.tgz", + "integrity": "sha512-bzfL1YUZsP41gmu/qjrEk0Q6i2ix/cVeAhbCbqH9u3zYutS1cLg00qhrD0M2MVdCcx4Sc0UpP2eBWo9rotpq6g==", + "dev": true + }, + "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, + "requires": { + "arrify": "^1.0.1", + "is-plain-obj": "^1.1.0", + "kind-of": "^6.0.3" + } + }, + "minipass": { + "version": "3.3.4", + "resolved": "https://registry.npmjs.org/minipass/-/minipass-3.3.4.tgz", + "integrity": "sha512-I9WPbWHCGu8W+6k1ZiGpPu0GkoKBeorkfKNuAFBNS1HNFJvke82sxvI5bzcCNpWPorkOO5QQ+zomzzwRxejXiw==", + "dev": true, + "requires": { + "yallist": "^4.0.0" + } + }, + "minipass-collect": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/minipass-collect/-/minipass-collect-1.0.2.tgz", + "integrity": "sha512-6T6lH0H8OG9kITm/Jm6tdooIbogG9e0tLgpY6mphXSm/A9u8Nq1ryBG+Qspiub9LjWlBPsPS3tWQ/Botq4FdxA==", + "dev": true, + "requires": { + "minipass": "^3.0.0" + } + }, + "minipass-fetch": { + "version": "2.1.2", + "resolved": "https://registry.npmjs.org/minipass-fetch/-/minipass-fetch-2.1.2.tgz", + "integrity": "sha512-LT49Zi2/WMROHYoqGgdlQIZh8mLPZmOrN2NdJjMXxYe4nkN6FUyuPuOAOedNJDrx0IRGg9+4guZewtp8hE6TxA==", + "dev": true, + "requires": { + "encoding": "^0.1.13", + "minipass": "^3.1.6", + "minipass-sized": "^1.0.3", + "minizlib": "^2.1.2" + } + }, + "minipass-flush": { + "version": "1.0.5", + "resolved": "https://registry.npmjs.org/minipass-flush/-/minipass-flush-1.0.5.tgz", + "integrity": "sha512-JmQSYYpPUqX5Jyn1mXaRwOda1uQ8HP5KAT/oDSLCzt1BYRhQU0/hDtsB1ufZfEEzMZ9aAVmsBw8+FWsIXlClWw==", + "dev": true, + "requires": { + "minipass": "^3.0.0" + } + }, + "minipass-json-stream": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/minipass-json-stream/-/minipass-json-stream-1.0.1.tgz", + "integrity": "sha512-ODqY18UZt/I8k+b7rl2AENgbWE8IDYam+undIJONvigAz8KR5GWblsFTEfQs0WODsjbSXWlm+JHEv8Gr6Tfdbg==", + "dev": true, + "requires": { + "jsonparse": "^1.3.1", + "minipass": "^3.0.0" + } + }, + "minipass-pipeline": { + "version": "1.2.4", + "resolved": "https://registry.npmjs.org/minipass-pipeline/-/minipass-pipeline-1.2.4.tgz", + "integrity": "sha512-xuIq7cIOt09RPRJ19gdi4b+RiNvDFYe5JH+ggNvBqGqpQXcru3PcRmOZuHBKWK1Txf9+cQ+HMVN4d6z46LZP7A==", + "dev": true, + "requires": { + "minipass": "^3.0.0" + } + }, + "minipass-sized": { + "version": "1.0.3", + "resolved": "https://registry.npmjs.org/minipass-sized/-/minipass-sized-1.0.3.tgz", + "integrity": "sha512-MbkQQ2CTiBMlA2Dm/5cY+9SWFEN8pzzOXi6rlM5Xxq0Yqbda5ZQy9sU75a673FE9ZK0Zsbr6Y5iP6u9nktfg2g==", + "dev": true, + "requires": { + "minipass": "^3.0.0" + } + }, + "minizlib": { + "version": "2.1.2", + "resolved": "https://registry.npmjs.org/minizlib/-/minizlib-2.1.2.tgz", + "integrity": "sha512-bAxsR8BVfj60DWXHE3u30oHzfl4G7khkSuPW+qvpd7jFRHm7dLxOjUk1EHACJ/hxLY8phGJ0YhYHZo7jil7Qdg==", + "dev": true, + "requires": { + "minipass": "^3.0.0", + "yallist": "^4.0.0" + } + }, + "mkdirp": { + "version": "1.0.4", + "resolved": "https://registry.npmjs.org/mkdirp/-/mkdirp-1.0.4.tgz", + "integrity": "sha512-vVqVZQyf3WLx2Shd0qJ9xuvqgAyKPLAiqITEtqW0oIUjzo3PePDd6fW9iFz30ef7Ysp/oiWqbhszeGWW2T6Gzw==", + "dev": true + }, + "mkdirp-infer-owner": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/mkdirp-infer-owner/-/mkdirp-infer-owner-2.0.0.tgz", + "integrity": "sha512-sdqtiFt3lkOaYvTXSRIUjkIdPTcxgv5+fgqYE/5qgwdw12cOrAuzzgzvVExIkH/ul1oeHN3bCLOWSG3XOqbKKw==", + "dev": true, + "requires": { + "chownr": "^2.0.0", + "infer-owner": "^1.0.4", + "mkdirp": "^1.0.3" + } + }, + "modify-values": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/modify-values/-/modify-values-1.0.1.tgz", + "integrity": "sha512-xV2bxeN6F7oYjZWTe/YPAy6MN2M+sL4u/Rlm2AHCIVGfo2p1yGmBHQ6vHehl4bRTZBdHu3TSkWdYgkwpYzAGSw==", + "dev": true + }, + "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 + }, + "multimatch": { + "version": "5.0.0", + "resolved": "https://registry.npmjs.org/multimatch/-/multimatch-5.0.0.tgz", + "integrity": "sha512-ypMKuglUrZUD99Tk2bUQ+xNQj43lPEfAeX2o9cTteAmShXy2VHDJpuwu1o0xqoKCt9jLVAvwyFKdLTPXKAfJyA==", + "dev": true, + "requires": { + "@types/minimatch": "^3.0.3", + "array-differ": "^3.0.0", + "array-union": "^2.1.0", + "arrify": "^2.0.1", + "minimatch": "^3.0.4" + }, + "dependencies": { + "arrify": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/arrify/-/arrify-2.0.1.tgz", + "integrity": "sha512-3duEwti880xqi4eAMN8AyR4a0ByT90zoYdLlevfrvU43vb0YZwZVfxOgxWrLXXXpyugL0hNZc9G6BiB5B3nUug==", + "dev": true + } + } + }, + "mute-stream": { + "version": "0.0.8", + "resolved": "https://registry.npmjs.org/mute-stream/-/mute-stream-0.0.8.tgz", + "integrity": "sha512-nnbWWOkoWyUsTjKrhgD0dcz22mdkSnpYqbEjIm2nhwhuxlSkpywJmBo8h0ZqJdkp73mb90SssHkN4rsRaBAfAA==", + "dev": true + }, + "natural-compare": { + "version": "1.4.0", + "resolved": "https://registry.npmjs.org/natural-compare/-/natural-compare-1.4.0.tgz", + "integrity": "sha512-OWND8ei3VtNC9h7V60qff3SVobHr996CTwgxubgyQYEpg290h9J0buyECNNJexkFm5sOajh5G116RYA1c8ZMSw==", + "dev": true + }, + "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 + }, + "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-addon-api": { + "version": "3.2.1", + "resolved": "https://registry.npmjs.org/node-addon-api/-/node-addon-api-3.2.1.tgz", + "integrity": "sha512-mmcei9JghVNDYydghQmeDX8KoAm0FAiYyIcUt/N4nhyAipB17pllZQDOJD2fotxABnt4Mdz+dKTO7eftLg4d0A==", + "dev": true + }, + "node-fetch": { + "version": "2.6.7", + "resolved": "https://registry.npmjs.org/node-fetch/-/node-fetch-2.6.7.tgz", + "integrity": "sha512-ZjMPFEfVx5j+y2yF35Kzx5sF7kDzxuDj6ziH4FFbOp87zKDZNx8yExJIb05OGF4Nlt9IHFIMBkRl41VdvcNdbQ==", + "dev": true, + "requires": { + "whatwg-url": "^5.0.0" + } + }, + "node-gyp": { + "version": "9.3.0", + "resolved": "https://registry.npmjs.org/node-gyp/-/node-gyp-9.3.0.tgz", + "integrity": "sha512-A6rJWfXFz7TQNjpldJ915WFb1LnhO4lIve3ANPbWreuEoLoKlFT3sxIepPBkLhM27crW8YmN+pjlgbasH6cH/Q==", + "dev": true, + "requires": { + "env-paths": "^2.2.0", + "glob": "^7.1.4", + "graceful-fs": "^4.2.6", + "make-fetch-happen": "^10.0.3", + "nopt": "^6.0.0", + "npmlog": "^6.0.0", + "rimraf": "^3.0.2", + "semver": "^7.3.5", + "tar": "^6.1.2", + "which": "^2.0.2" + }, + "dependencies": { + "glob": { + "version": "7.2.3", + "resolved": "https://registry.npmjs.org/glob/-/glob-7.2.3.tgz", + "integrity": "sha512-nFR0zLpU2YCaRxwoCJvL6UvCH2JFyFVIvwTLsIf21AuHlMskA1hhTdk+LlYJtOlYt9v6dvszD2BGRqBL+iQK9Q==", + "dev": true, + "requires": { + "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" + } + }, + "nopt": { + "version": "6.0.0", + "resolved": "https://registry.npmjs.org/nopt/-/nopt-6.0.0.tgz", + "integrity": "sha512-ZwLpbTgdhuZUnZzjd7nb1ZV+4DoiC6/sfiVKok72ym/4Tlf+DFdlHYmT2JPmcNNWV6Pi3SDf1kT+A4r9RTuT9g==", + "dev": true, + "requires": { + "abbrev": "^1.0.0" + } + } + } + }, + "node-gyp-build": { + "version": "4.5.0", + "resolved": "https://registry.npmjs.org/node-gyp-build/-/node-gyp-build-4.5.0.tgz", + "integrity": "sha512-2iGbaQBV+ITgCz76ZEjmhUKAKVf7xfY1sRl4UiKQspfZMH2h06SyhNsnSVy50cwkFQDGLyif6m/6uFXHkOZ6rg==", + "dev": true + }, + "nopt": { + "version": "5.0.0", + "resolved": "https://registry.npmjs.org/nopt/-/nopt-5.0.0.tgz", + "integrity": "sha512-Tbj67rffqceeLpcRXrT7vKAN8CwfPeIBgM7E6iBkmKLV7bEMwpGgYLGv0jACUsECaa/vuxP0IjEont6umdMgtQ==", + "dev": true, + "requires": { + "abbrev": "1" + } + }, + "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, + "requires": { + "hosted-git-info": "^4.0.1", + "is-core-module": "^2.5.0", + "semver": "^7.3.4", + "validate-npm-package-license": "^3.0.1" + } + }, + "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 + }, + "normalize-url": { + "version": "7.2.0", + "resolved": "https://registry.npmjs.org/normalize-url/-/normalize-url-7.2.0.tgz", + "integrity": "sha512-uhXOdZry0L6M2UIo9BTt7FdpBDiAGN/7oItedQwPKh8jh31ZlvC8U9Xl/EJ3aijDHaywXTW3QbZ6LuCocur1YA==", + "dev": true + }, + "npm-bundled": { + "version": "1.1.2", + "resolved": "https://registry.npmjs.org/npm-bundled/-/npm-bundled-1.1.2.tgz", + "integrity": "sha512-x5DHup0SuyQcmL3s7Rx/YQ8sbw/Hzg0rj48eN0dV7hf5cmQq5PXIeioroH3raV1QC1yh3uTYuMThvEQF3iKgGQ==", + "dev": true, + "requires": { + "npm-normalize-package-bin": "^1.0.1" + } + }, + "npm-check-updates": { + "version": "16.3.11", + "resolved": "https://registry.npmjs.org/npm-check-updates/-/npm-check-updates-16.3.11.tgz", + "integrity": "sha512-MxdqS3kXAJasoEaz5BLqTR1Dak+Dm6PoK2N4KdKcQGUEhdVwt0ggfJ0R0Yym8sWc48CYqEl02HBkUAZFUCufHA==", + "dev": true, + "requires": { + "chalk": "^5.0.1", + "cli-table": "^0.3.11", + "commander": "^9.4.1", + "fast-memoize": "^2.5.2", + "find-up": "5.0.0", + "fp-and-or": "^0.1.3", + "get-stdin": "^8.0.0", + "globby": "^11.0.4", + "hosted-git-info": "^5.1.0", + "json-parse-helpfulerror": "^1.0.3", + "jsonlines": "^0.1.1", + "lodash": "^4.17.21", + "minimatch": "^5.1.0", + "p-map": "^4.0.0", + "pacote": "^13.6.2", + "parse-github-url": "^1.0.2", + "progress": "^2.0.3", + "prompts-ncu": "^2.5.1", + "rc-config-loader": "^4.1.0", + "remote-git-tags": "^3.0.0", + "rimraf": "^3.0.2", + "semver": "^7.3.7", + "semver-utils": "^1.1.4", + "source-map-support": "^0.5.21", + "spawn-please": "^1.0.0", + "untildify": "^4.0.0", + "update-notifier": "^6.0.2", + "yaml": "^2.1.1" + }, + "dependencies": { + "brace-expansion": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/brace-expansion/-/brace-expansion-2.0.1.tgz", + "integrity": "sha512-XnAIvQ8eM+kC6aULx6wuQiwVsnzsi9d3WxzV3FpWTGA19F621kwdbsAcFKXgKUHZWsy+mY6iL1sHTxWEFCytDA==", + "dev": true, + "requires": { + "balanced-match": "^1.0.0" + } + }, + "chalk": { + "version": "5.1.0", + "resolved": "https://registry.npmjs.org/chalk/-/chalk-5.1.0.tgz", + "integrity": "sha512-56zD4khRTBoIyzUYAFgDDaPhUMN/fC/rySe6aZGqbj/VWiU2eI3l6ZLOtYGFZAV5v02mwPjtpzlrOveJiz5eZQ==", + "dev": true + }, + "hosted-git-info": { + "version": "5.1.0", + "resolved": "https://registry.npmjs.org/hosted-git-info/-/hosted-git-info-5.1.0.tgz", + "integrity": "sha512-Ek+QmMEqZF8XrbFdwoDjSbm7rT23pCgEMOJmz6GPk/s4yH//RQfNPArhIxbguNxROq/+5lNBwCDHMhA903Kx1Q==", + "dev": true, + "requires": { + "lru-cache": "^7.5.1" + } + }, + "minimatch": { + "version": "5.1.0", + "resolved": "https://registry.npmjs.org/minimatch/-/minimatch-5.1.0.tgz", + "integrity": "sha512-9TPBGGak4nHfGZsPBohm9AWg6NoT7QTCehS3BIJABslyZbzxfV78QM2Y6+i741OPZIafFAaiiEMh5OyIrJPgtg==", + "dev": true, + "requires": { + "brace-expansion": "^2.0.1" + } + }, + "yaml": { + "version": "2.1.3", + "resolved": "https://registry.npmjs.org/yaml/-/yaml-2.1.3.tgz", + "integrity": "sha512-AacA8nRULjKMX2DvWvOAdBZMOfQlypSFkjcOcu9FalllIDJ1kvlREzcdIZmidQUqqeMv7jorHjq2HlLv/+c2lg==", + "dev": true + } + } + }, + "npm-install-checks": { + "version": "5.0.0", + "resolved": "https://registry.npmjs.org/npm-install-checks/-/npm-install-checks-5.0.0.tgz", + "integrity": "sha512-65lUsMI8ztHCxFz5ckCEC44DRvEGdZX5usQFriauxHEwt7upv1FKaQEmAtU0YnOAdwuNWCmk64xYiQABNrEyLA==", + "dev": true, + "requires": { + "semver": "^7.1.1" + } + }, + "npm-normalize-package-bin": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/npm-normalize-package-bin/-/npm-normalize-package-bin-1.0.1.tgz", + "integrity": "sha512-EPfafl6JL5/rU+ot6P3gRSCpPDW5VmIzX959Ob1+ySFUuuYHWHekXpwdUZcKP5C+DS4GEtdJluwBjnsNDl+fSA==", + "dev": true + }, + "npm-package-arg": { + "version": "8.1.1", + "resolved": "https://registry.npmjs.org/npm-package-arg/-/npm-package-arg-8.1.1.tgz", + "integrity": "sha512-CsP95FhWQDwNqiYS+Q0mZ7FAEDytDZAkNxQqea6IaAFJTAY9Lhhqyl0irU/6PMc7BGfUmnsbHcqxJD7XuVM/rg==", + "dev": true, + "requires": { + "hosted-git-info": "^3.0.6", + "semver": "^7.0.0", + "validate-npm-package-name": "^3.0.0" + }, + "dependencies": { + "builtins": { + "version": "1.0.3", + "resolved": "https://registry.npmjs.org/builtins/-/builtins-1.0.3.tgz", + "integrity": "sha512-uYBjakWipfaO/bXI7E8rq6kpwHRZK5cNYrUv2OzZSI/FvmdMyXJ2tG9dKcjEC5YHmHpUAwsargWIZNWdxb/bnQ==", + "dev": true + }, + "hosted-git-info": { + "version": "3.0.8", + "resolved": "https://registry.npmjs.org/hosted-git-info/-/hosted-git-info-3.0.8.tgz", + "integrity": "sha512-aXpmwoOhRBrw6X3j0h5RloK4x1OzsxMPyxqIHyNfSe2pypkVTZFpEiRoSipPEPlMrh0HW/XsjkJ5WgnCirpNUw==", + "dev": true, + "requires": { + "lru-cache": "^6.0.0" + } + }, + "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, + "requires": { + "yallist": "^4.0.0" + } + }, + "validate-npm-package-name": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/validate-npm-package-name/-/validate-npm-package-name-3.0.0.tgz", + "integrity": "sha512-M6w37eVCMMouJ9V/sdPGnC5H4uDr73/+xdq0FBLO3TFFX1+7wiUY6Es328NN+y43tmY+doUdN9g9J21vqB7iLw==", + "dev": true, + "requires": { + "builtins": "^1.0.3" + } + } + } + }, + "npm-packlist": { + "version": "5.1.3", + "resolved": "https://registry.npmjs.org/npm-packlist/-/npm-packlist-5.1.3.tgz", + "integrity": "sha512-263/0NGrn32YFYi4J533qzrQ/krmmrWwhKkzwTuM4f/07ug51odoaNjUexxO4vxlzURHcmYMH1QjvHjsNDKLVg==", + "dev": true, + "requires": { + "glob": "^8.0.1", + "ignore-walk": "^5.0.1", + "npm-bundled": "^2.0.0", + "npm-normalize-package-bin": "^2.0.0" + }, + "dependencies": { + "npm-bundled": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/npm-bundled/-/npm-bundled-2.0.1.tgz", + "integrity": "sha512-gZLxXdjEzE/+mOstGDqR6b0EkhJ+kM6fxM6vUuckuctuVPh80Q6pw/rSZj9s4Gex9GxWtIicO1pc8DB9KZWudw==", + "dev": true, + "requires": { + "npm-normalize-package-bin": "^2.0.0" + } + }, + "npm-normalize-package-bin": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/npm-normalize-package-bin/-/npm-normalize-package-bin-2.0.0.tgz", + "integrity": "sha512-awzfKUO7v0FscrSpRoogyNm0sajikhBWpU0QMrW09AMi9n1PoKU6WaIqUzuJSQnpciZZmJ/jMZ2Egfmb/9LiWQ==", + "dev": true + } + } + }, + "npm-pick-manifest": { + "version": "7.0.2", + "resolved": "https://registry.npmjs.org/npm-pick-manifest/-/npm-pick-manifest-7.0.2.tgz", + "integrity": "sha512-gk37SyRmlIjvTfcYl6RzDbSmS9Y4TOBXfsPnoYqTHARNgWbyDiCSMLUpmALDj4jjcTZpURiEfsSHJj9k7EV4Rw==", + "dev": true, + "requires": { + "npm-install-checks": "^5.0.0", + "npm-normalize-package-bin": "^2.0.0", + "npm-package-arg": "^9.0.0", + "semver": "^7.3.5" + }, + "dependencies": { + "hosted-git-info": { + "version": "5.1.0", + "resolved": "https://registry.npmjs.org/hosted-git-info/-/hosted-git-info-5.1.0.tgz", + "integrity": "sha512-Ek+QmMEqZF8XrbFdwoDjSbm7rT23pCgEMOJmz6GPk/s4yH//RQfNPArhIxbguNxROq/+5lNBwCDHMhA903Kx1Q==", + "dev": true, + "requires": { + "lru-cache": "^7.5.1" + } + }, + "npm-normalize-package-bin": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/npm-normalize-package-bin/-/npm-normalize-package-bin-2.0.0.tgz", + "integrity": "sha512-awzfKUO7v0FscrSpRoogyNm0sajikhBWpU0QMrW09AMi9n1PoKU6WaIqUzuJSQnpciZZmJ/jMZ2Egfmb/9LiWQ==", + "dev": true + }, + "npm-package-arg": { + "version": "9.1.2", + "resolved": "https://registry.npmjs.org/npm-package-arg/-/npm-package-arg-9.1.2.tgz", + "integrity": "sha512-pzd9rLEx4TfNJkovvlBSLGhq31gGu2QDexFPWT19yCDh0JgnRhlBLNo5759N0AJmBk+kQ9Y/hXoLnlgFD+ukmg==", + "dev": true, + "requires": { + "hosted-git-info": "^5.0.0", + "proc-log": "^2.0.1", + "semver": "^7.3.5", + "validate-npm-package-name": "^4.0.0" + } + } + } + }, + "npm-registry-fetch": { + "version": "13.3.1", + "resolved": "https://registry.npmjs.org/npm-registry-fetch/-/npm-registry-fetch-13.3.1.tgz", + "integrity": "sha512-eukJPi++DKRTjSBRcDZSDDsGqRK3ehbxfFUcgaRd0Yp6kRwOwh2WVn0r+8rMB4nnuzvAk6rQVzl6K5CkYOmnvw==", + "dev": true, + "requires": { + "make-fetch-happen": "^10.0.6", + "minipass": "^3.1.6", + "minipass-fetch": "^2.0.3", + "minipass-json-stream": "^1.0.1", + "minizlib": "^2.1.2", + "npm-package-arg": "^9.0.1", + "proc-log": "^2.0.0" + }, + "dependencies": { + "hosted-git-info": { + "version": "5.1.0", + "resolved": "https://registry.npmjs.org/hosted-git-info/-/hosted-git-info-5.1.0.tgz", + "integrity": "sha512-Ek+QmMEqZF8XrbFdwoDjSbm7rT23pCgEMOJmz6GPk/s4yH//RQfNPArhIxbguNxROq/+5lNBwCDHMhA903Kx1Q==", + "dev": true, + "requires": { + "lru-cache": "^7.5.1" + } + }, + "npm-package-arg": { + "version": "9.1.2", + "resolved": "https://registry.npmjs.org/npm-package-arg/-/npm-package-arg-9.1.2.tgz", + "integrity": "sha512-pzd9rLEx4TfNJkovvlBSLGhq31gGu2QDexFPWT19yCDh0JgnRhlBLNo5759N0AJmBk+kQ9Y/hXoLnlgFD+ukmg==", + "dev": true, + "requires": { + "hosted-git-info": "^5.0.0", + "proc-log": "^2.0.1", + "semver": "^7.3.5", + "validate-npm-package-name": "^4.0.0" + } + } + } + }, + "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, + "requires": { + "path-key": "^3.0.0" + } + }, + "npmlog": { + "version": "6.0.2", + "resolved": "https://registry.npmjs.org/npmlog/-/npmlog-6.0.2.tgz", + "integrity": "sha512-/vBvz5Jfr9dT/aFWd0FIRf+T/Q2WBsLENygUaFUqstqsycmZAP/t5BvFJTK0viFmSUxiUKTUplWy5vt+rvKIxg==", + "dev": true, + "requires": { + "are-we-there-yet": "^3.0.0", + "console-control-strings": "^1.1.0", + "gauge": "^4.0.3", + "set-blocking": "^2.0.0" + } + }, + "nx": { + "version": "14.8.4", + "resolved": "https://registry.npmjs.org/nx/-/nx-14.8.4.tgz", + "integrity": "sha512-J7QlmG6rsdR+1Ry0pohPZXHpPN1lzE70lvuCXveyU61VX8HsrbZBzgLif07BUT8lHbs7ORaOJSZd4BCqZBJSSw==", + "dev": true, + "requires": { + "@nrwl/cli": "14.8.4", + "@nrwl/tao": "14.8.4", + "@parcel/watcher": "2.0.4", + "@yarnpkg/lockfile": "^1.1.0", + "@yarnpkg/parsers": "^3.0.0-rc.18", + "@zkochan/js-yaml": "0.0.6", + "axios": "^1.0.0", + "chalk": "4.1.0", + "chokidar": "^3.5.1", + "cli-cursor": "3.1.0", + "cli-spinners": "2.6.1", + "cliui": "^7.0.2", + "dotenv": "~10.0.0", + "enquirer": "~2.3.6", + "fast-glob": "3.2.7", + "figures": "3.2.0", + "flat": "^5.0.2", + "fs-extra": "^10.1.0", + "glob": "7.1.4", + "ignore": "^5.0.4", + "js-yaml": "4.1.0", + "jsonc-parser": "3.2.0", + "minimatch": "3.0.5", + "npm-run-path": "^4.0.1", + "open": "^8.4.0", + "semver": "7.3.4", + "string-width": "^4.2.3", + "strong-log-transformer": "^2.1.0", + "tar-stream": "~2.2.0", + "tmp": "~0.2.1", + "tsconfig-paths": "^3.9.0", + "tslib": "^2.3.0", + "v8-compile-cache": "2.3.0", + "yargs": "^17.4.0", + "yargs-parser": "21.0.1" + }, + "dependencies": { + "axios": { + "version": "1.1.2", + "resolved": "https://registry.npmjs.org/axios/-/axios-1.1.2.tgz", + "integrity": "sha512-bznQyETwElsXl2RK7HLLwb5GPpOLlycxHCtrpDR/4RqqBzjARaOTo3jz4IgtntWUYee7Ne4S8UHd92VCuzPaWA==", + "dev": true, + "requires": { + "follow-redirects": "^1.15.0", + "form-data": "^4.0.0", + "proxy-from-env": "^1.1.0" + } + }, + "chalk": { + "version": "4.1.0", + "resolved": "https://registry.npmjs.org/chalk/-/chalk-4.1.0.tgz", + "integrity": "sha512-qwx12AxXe2Q5xQ43Ac//I6v5aXTipYrSESdOgzrN+9XjgEpyjpKuvSGaN4qE93f7TQTlerQQ8S+EQ0EyDoVL1A==", + "dev": true, + "requires": { + "ansi-styles": "^4.1.0", + "supports-color": "^7.1.0" + } + }, + "fast-glob": { + "version": "3.2.7", + "resolved": "https://registry.npmjs.org/fast-glob/-/fast-glob-3.2.7.tgz", + "integrity": "sha512-rYGMRwip6lUMvYD3BTScMwT1HtAs2d71SMv66Vrxs0IekGZEjhM0pcMfjQPnknBt2zeCwQMEupiN02ZP4DiT1Q==", + "dev": true, + "requires": { + "@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" + } + }, + "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, + "requires": { + "graceful-fs": "^4.2.0", + "jsonfile": "^6.0.1", + "universalify": "^2.0.0" + } + }, + "glob": { + "version": "7.1.4", + "resolved": "https://registry.npmjs.org/glob/-/glob-7.1.4.tgz", + "integrity": "sha512-hkLPepehmnKk41pUGm3sYxoFs/umurYfYJCerbXEyFIWcAzvpipAgVkBqqT9RBKMGjnq6kMuyYwha6csxbiM1A==", + "dev": true, + "requires": { + "fs.realpath": "^1.0.0", + "inflight": "^1.0.4", + "inherits": "2", + "minimatch": "^3.0.4", + "once": "^1.3.0", + "path-is-absolute": "^1.0.0" + } + }, + "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, + "requires": { + "is-glob": "^4.0.1" + } + }, + "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, + "requires": { + "yallist": "^4.0.0" + } + }, + "minimatch": { + "version": "3.0.5", + "resolved": "https://registry.npmjs.org/minimatch/-/minimatch-3.0.5.tgz", + "integrity": "sha512-tUpxzX0VAzJHjLu0xUfFv1gwVp9ba3IOuRAVH2EGuRW8a5emA2FlACLqiT/lDVtS1W+TGNwqz3sWaNyLgDJWuw==", + "dev": true, + "requires": { + "brace-expansion": "^1.1.7" + } + }, + "semver": { + "version": "7.3.4", + "resolved": "https://registry.npmjs.org/semver/-/semver-7.3.4.tgz", + "integrity": "sha512-tCfb2WLjqFAtXn4KEdxIhalnRtoKFN7nAwj0B3ZXCbQloV2tq5eDbcTmT68JJD3nRJq24/XgxtQKFIpQdtvmVw==", + "dev": true, + "requires": { + "lru-cache": "^6.0.0" + } + }, + "tmp": { + "version": "0.2.1", + "resolved": "https://registry.npmjs.org/tmp/-/tmp-0.2.1.tgz", + "integrity": "sha512-76SUhtfqR2Ijn+xllcI5P1oyannHNHByD80W1q447gU3mp9G9PSpGdWmjUOHRDPiHYacIk66W7ubDTuPF3BEtQ==", + "dev": true, + "requires": { + "rimraf": "^3.0.0" + } + }, + "yargs": { + "version": "17.6.0", + "resolved": "https://registry.npmjs.org/yargs/-/yargs-17.6.0.tgz", + "integrity": "sha512-8H/wTDqlSwoSnScvV2N/JHfLWOKuh5MVla9hqLjK3nsfyy6Y4kDSYSvkU5YCUEPOSnRXfIyx3Sq+B/IWudTo4g==", + "dev": true, + "requires": { + "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.0.0" + }, + "dependencies": { + "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, + "requires": { + "string-width": "^4.2.0", + "strip-ansi": "^6.0.1", + "wrap-ansi": "^7.0.0" + } + } + } + }, + "yargs-parser": { + "version": "21.0.1", + "resolved": "https://registry.npmjs.org/yargs-parser/-/yargs-parser-21.0.1.tgz", + "integrity": "sha512-9BK1jFpLzJROCI5TzwZL/TU4gqjK5xiHV/RfWLOahrjAko/e4DJkRDZQXfvqAsiZzzYhgAzbgz6lg48jcm4GLg==", + "dev": true + } + } + }, + "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, + "requires": { + "wrappy": "1" + } + }, + "onetime": { + "version": "5.1.2", + "resolved": "https://registry.npmjs.org/onetime/-/onetime-5.1.2.tgz", + "integrity": "sha512-kbpaSSGJTWdAY5KPVeMOKXSrPtr8C8C7wodJbcsd51jRnmD+GZu8Y0VoU6Dm5Z4vWr0Ig/1NKuWRKf7j5aaYSg==", + "dev": true, + "requires": { + "mimic-fn": "^2.1.0" + } + }, + "open": { + "version": "8.4.0", + "resolved": "https://registry.npmjs.org/open/-/open-8.4.0.tgz", + "integrity": "sha512-XgFPPM+B28FtCCgSb9I+s9szOC1vZRSwgWsRUA5ylIxRTgKozqjOCrVOqGsYABPYK5qnfqClxZTFBa8PKt2v6Q==", + "dev": true, + "requires": { + "define-lazy-prop": "^2.0.0", + "is-docker": "^2.1.1", + "is-wsl": "^2.2.0" + } + }, + "optionator": { + "version": "0.9.1", + "resolved": "https://registry.npmjs.org/optionator/-/optionator-0.9.1.tgz", + "integrity": "sha512-74RlY5FCnhq4jRxVUPKDaRwrVNXMqsGsiW6AJw4XK8hmtm10wC0ypZBLw5IIp85NZMr91+qd1RvvENwg7jjRFw==", + "dev": true, + "requires": { + "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" + } + }, + "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, + "requires": { + "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" + } + }, + "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 + }, + "p-cancelable": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/p-cancelable/-/p-cancelable-3.0.0.tgz", + "integrity": "sha512-mlVgR3PGuzlo0MmTdk4cXqXWlwQDLnONTAg6sm62XkMJEiRxN3GL3SffkYvqwonbkJBcrI7Uvv5Zh9yjvn2iUw==", + "dev": true + }, + "p-finally": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/p-finally/-/p-finally-1.0.0.tgz", + "integrity": "sha512-LICb2p9CB7FS+0eR1oqWnHhp0FljGLZCWBE9aix0Uye9W8LTQPwMTYVGWQWIw9RdQiDg4+epXQODwIYJtSJaow==", + "dev": true + }, + "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, + "requires": { + "yocto-queue": "^0.1.0" + } + }, + "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, + "requires": { + "p-limit": "^3.0.2" + } + }, + "p-map": { + "version": "4.0.0", + "resolved": "https://registry.npmjs.org/p-map/-/p-map-4.0.0.tgz", + "integrity": "sha512-/bjOqmgETBYB5BoEeGVea8dmvHb2m9GLy1E9W43yeyfP6QQCZGFNa+XRceJEuDB6zqr+gKpIAmlLebMpykw/MQ==", + "dev": true, + "requires": { + "aggregate-error": "^3.0.0" + } + }, + "p-map-series": { + "version": "2.1.0", + "resolved": "https://registry.npmjs.org/p-map-series/-/p-map-series-2.1.0.tgz", + "integrity": "sha512-RpYIIK1zXSNEOdwxcfe7FdvGcs7+y5n8rifMhMNWvaxRNMPINJHF5GDeuVxWqnfrcHPSCnp7Oo5yNXHId9Av2Q==", + "dev": true + }, + "p-pipe": { + "version": "3.1.0", + "resolved": "https://registry.npmjs.org/p-pipe/-/p-pipe-3.1.0.tgz", + "integrity": "sha512-08pj8ATpzMR0Y80x50yJHn37NF6vjrqHutASaX5LiH5npS9XPvrUmscd9MF5R4fuYRHOxQR1FfMIlF7AzwoPqw==", + "dev": true + }, + "p-queue": { + "version": "6.6.2", + "resolved": "https://registry.npmjs.org/p-queue/-/p-queue-6.6.2.tgz", + "integrity": "sha512-RwFpb72c/BhQLEXIZ5K2e+AhgNVmIejGlTgiB9MzZ0e93GRvqZ7uSi0dvRF7/XIXDeNkra2fNHBxTyPDGySpjQ==", + "dev": true, + "requires": { + "eventemitter3": "^4.0.4", + "p-timeout": "^3.2.0" + } + }, + "p-reduce": { + "version": "2.1.0", + "resolved": "https://registry.npmjs.org/p-reduce/-/p-reduce-2.1.0.tgz", + "integrity": "sha512-2USApvnsutq8uoxZBGbbWM0JIYLiEMJ9RlaN7fAzVNb9OZN0SHjjTTfIcb667XynS5Y1VhwDJVDa72TnPzAYWw==", + "dev": true + }, + "p-timeout": { + "version": "3.2.0", + "resolved": "https://registry.npmjs.org/p-timeout/-/p-timeout-3.2.0.tgz", + "integrity": "sha512-rhIwUycgwwKcP9yTOOFK/AKsAopjjCakVqLHePO3CC6Mir1Z99xT+R63jZxAT5lFZLa2inS5h+ZS2GvR99/FBg==", + "dev": true, + "requires": { + "p-finally": "^1.0.0" + } + }, + "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 + }, + "p-waterfall": { + "version": "2.1.1", + "resolved": "https://registry.npmjs.org/p-waterfall/-/p-waterfall-2.1.1.tgz", + "integrity": "sha512-RRTnDb2TBG/epPRI2yYXsimO0v3BXC8Yd3ogr1545IaqKK17VGhbWVeGGN+XfCm/08OK8635nH31c8bATkHuSw==", + "dev": true, + "requires": { + "p-reduce": "^2.0.0" + } + }, + "package-json": { + "version": "8.1.0", + "resolved": "https://registry.npmjs.org/package-json/-/package-json-8.1.0.tgz", + "integrity": "sha512-hySwcV8RAWeAfPsXb9/HGSPn8lwDnv6fabH+obUZKX169QknRkRhPxd1yMubpKDskLFATkl3jHpNtVtDPFA0Wg==", + "dev": true, + "requires": { + "got": "^12.1.0", + "registry-auth-token": "^5.0.1", + "registry-url": "^6.0.0", + "semver": "^7.3.7" + } + }, + "pacote": { + "version": "13.6.2", + "resolved": "https://registry.npmjs.org/pacote/-/pacote-13.6.2.tgz", + "integrity": "sha512-Gu8fU3GsvOPkak2CkbojR7vjs3k3P9cA6uazKTHdsdV0gpCEQq2opelnEv30KRQWgVzP5Vd/5umjcedma3MKtg==", + "dev": true, + "requires": { + "@npmcli/git": "^3.0.0", + "@npmcli/installed-package-contents": "^1.0.7", + "@npmcli/promise-spawn": "^3.0.0", + "@npmcli/run-script": "^4.1.0", + "cacache": "^16.0.0", + "chownr": "^2.0.0", + "fs-minipass": "^2.1.0", + "infer-owner": "^1.0.4", + "minipass": "^3.1.6", + "mkdirp": "^1.0.4", + "npm-package-arg": "^9.0.0", + "npm-packlist": "^5.1.0", + "npm-pick-manifest": "^7.0.0", + "npm-registry-fetch": "^13.0.1", + "proc-log": "^2.0.0", + "promise-retry": "^2.0.1", + "read-package-json": "^5.0.0", + "read-package-json-fast": "^2.0.3", + "rimraf": "^3.0.2", + "ssri": "^9.0.0", + "tar": "^6.1.11" + }, + "dependencies": { + "hosted-git-info": { + "version": "5.1.0", + "resolved": "https://registry.npmjs.org/hosted-git-info/-/hosted-git-info-5.1.0.tgz", + "integrity": "sha512-Ek+QmMEqZF8XrbFdwoDjSbm7rT23pCgEMOJmz6GPk/s4yH//RQfNPArhIxbguNxROq/+5lNBwCDHMhA903Kx1Q==", + "dev": true, + "requires": { + "lru-cache": "^7.5.1" + } + }, + "npm-package-arg": { + "version": "9.1.2", + "resolved": "https://registry.npmjs.org/npm-package-arg/-/npm-package-arg-9.1.2.tgz", + "integrity": "sha512-pzd9rLEx4TfNJkovvlBSLGhq31gGu2QDexFPWT19yCDh0JgnRhlBLNo5759N0AJmBk+kQ9Y/hXoLnlgFD+ukmg==", + "dev": true, + "requires": { + "hosted-git-info": "^5.0.0", + "proc-log": "^2.0.1", + "semver": "^7.3.5", + "validate-npm-package-name": "^4.0.0" + } + } + } + }, + "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, + "requires": { + "callsites": "^3.0.0" + } + }, + "parse-conflict-json": { + "version": "2.0.2", + "resolved": "https://registry.npmjs.org/parse-conflict-json/-/parse-conflict-json-2.0.2.tgz", + "integrity": "sha512-jDbRGb00TAPFsKWCpZZOT93SxVP9nONOSgES3AevqRq/CHvavEBvKAjxX9p5Y5F0RZLxH9Ufd9+RwtCsa+lFDA==", + "dev": true, + "requires": { + "json-parse-even-better-errors": "^2.3.1", + "just-diff": "^5.0.1", + "just-diff-apply": "^5.2.0" + } + }, + "parse-github-url": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/parse-github-url/-/parse-github-url-1.0.2.tgz", + "integrity": "sha512-kgBf6avCbO3Cn6+RnzRGLkUsv4ZVqv/VfAYkRsyBcgkshNvVBkRn1FEZcW0Jb+npXQWm2vHPnnOqFteZxRRGNw==", + "dev": true + }, + "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, + "requires": { + "@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" + } + }, + "parse-path": { + "version": "7.0.0", + "resolved": "https://registry.npmjs.org/parse-path/-/parse-path-7.0.0.tgz", + "integrity": "sha512-Euf9GG8WT9CdqwuWJGdf3RkUcTBArppHABkO7Lm8IzRQp0e2r/kkFnmhu4TSK30Wcu5rVAZLmfPKSBBi9tWFog==", + "dev": true, + "requires": { + "protocols": "^2.0.0" + } + }, + "parse-url": { + "version": "8.1.0", + "resolved": "https://registry.npmjs.org/parse-url/-/parse-url-8.1.0.tgz", + "integrity": "sha512-xDvOoLU5XRrcOZvnI6b8zA6n9O9ejNk/GExuz1yBuWUGn9KA97GI6HTs6u02wKara1CeVmZhH+0TZFdWScR89w==", + "dev": true, + "requires": { + "parse-path": "^7.0.0" + } + }, + "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 + }, + "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 + }, + "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 + }, + "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 + }, + "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 + }, + "picomatch": { + "version": "2.3.1", + "resolved": "https://registry.npmjs.org/picomatch/-/picomatch-2.3.1.tgz", + "integrity": "sha512-JU3teHTNjmE2VCGFzuY8EXzCDVwEqB2a8fsIvwaStHhAWJEeVd1o1QD80CU6+ZdEXXSLbSsuLwJjkCBWqRQUVA==", + "dev": true + }, + "pify": { + "version": "5.0.0", + "resolved": "https://registry.npmjs.org/pify/-/pify-5.0.0.tgz", + "integrity": "sha512-eW/gHNMlxdSP6dmG6uJip6FXN0EQBwm2clYYd8Wul42Cwu/DK8HEftzsapcNdYe2MfLiIwZqsDk2RDEsTE79hA==", + "dev": true + }, + "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, + "requires": { + "find-up": "^4.0.0" + }, + "dependencies": { + "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, + "requires": { + "locate-path": "^5.0.0", + "path-exists": "^4.0.0" + } + }, + "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, + "requires": { + "p-locate": "^4.1.0" + } + }, + "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, + "requires": { + "p-try": "^2.0.0" + } + }, + "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, + "requires": { + "p-limit": "^2.2.0" + } + } + } + }, + "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 + }, + "prettier": { + "version": "2.7.1", + "resolved": "https://registry.npmjs.org/prettier/-/prettier-2.7.1.tgz", + "integrity": "sha512-ujppO+MkdPqoVINuDFDRLClm7D78qbDt0/NR+wp5FqEZOoTNAjPHWj17QRhu7geIHJfcNhRk1XVQmF8Bp3ye+g==", + "dev": true + }, + "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, + "requires": { + "fast-diff": "^1.1.2" + } + }, + "proc-log": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/proc-log/-/proc-log-2.0.1.tgz", + "integrity": "sha512-Kcmo2FhfDTXdcbfDH76N7uBYHINxc/8GW7UAVuVP9I+Va3uHSerrnKV6dLooga/gh7GlgzuCCr/eoldnL1muGw==", + "dev": true + }, + "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 + }, + "progress": { + "version": "2.0.3", + "resolved": "https://registry.npmjs.org/progress/-/progress-2.0.3.tgz", + "integrity": "sha512-7PiHtLll5LdnKIMw100I+8xJXR5gW2QwWYkT6iJva0bXitZKa/XMrSbdmg3r2Xnaidz9Qumd0VPaMrZlF9V9sA==", + "dev": true + }, + "promise-all-reject-late": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/promise-all-reject-late/-/promise-all-reject-late-1.0.1.tgz", + "integrity": "sha512-vuf0Lf0lOxyQREH7GDIOUMLS7kz+gs8i6B+Yi8dC68a2sychGrHTJYghMBD6k7eUcH0H5P73EckCA48xijWqXw==", + "dev": true + }, + "promise-call-limit": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/promise-call-limit/-/promise-call-limit-1.0.1.tgz", + "integrity": "sha512-3+hgaa19jzCGLuSCbieeRsu5C2joKfYn8pY6JAuXFRVfF4IO+L7UPpFWNTeWT9pM7uhskvbPPd/oEOktCn317Q==", + "dev": true + }, + "promise-inflight": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/promise-inflight/-/promise-inflight-1.0.1.tgz", + "integrity": "sha512-6zWPyEOFaQBJYcGMHBKTKJ3u6TBsnMFOIZSa6ce1e/ZrrsOlnHRHbabMjLiBYKp+n44X9eUI6VUPaukCXHuG4g==", + "dev": true + }, + "promise-retry": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/promise-retry/-/promise-retry-2.0.1.tgz", + "integrity": "sha512-y+WKFlBR8BGXnsNlIHFGPZmyDf3DFMoLhaflAnyZgV6rG6xu+JwesTo2Q9R6XwYmtmwAFCkAk3e35jEdoeh/3g==", + "dev": true, + "requires": { + "err-code": "^2.0.2", + "retry": "^0.12.0" + } + }, + "prompts-ncu": { + "version": "2.5.1", + "resolved": "https://registry.npmjs.org/prompts-ncu/-/prompts-ncu-2.5.1.tgz", + "integrity": "sha512-Hdd7GgV7b76Yh9FP9HL1D9xqtJCJdVPpiM2vDtuoc8W1KfweJe15gutFYmxkq83ViFaagFM8K0UcPCQ/tZq8bA==", + "dev": true, + "requires": { + "kleur": "^4.0.1", + "sisteransi": "^1.0.5" + } + }, + "promzard": { + "version": "0.3.0", + "resolved": "https://registry.npmjs.org/promzard/-/promzard-0.3.0.tgz", + "integrity": "sha512-JZeYqd7UAcHCwI+sTOeUDYkvEU+1bQ7iE0UT1MgB/tERkAPkesW46MrpIySzODi+owTjZtiF8Ay5j9m60KmMBw==", + "dev": true, + "requires": { + "read": "1" + } + }, + "proto-list": { + "version": "1.2.4", + "resolved": "https://registry.npmjs.org/proto-list/-/proto-list-1.2.4.tgz", + "integrity": "sha512-vtK/94akxsTMhe0/cbfpR+syPuszcuwhqVjJq26CuNDgFGj682oRBXOP5MJpv2r7JtE8MsiepGIqvvOTBwn2vA==", + "dev": true + }, + "protocols": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/protocols/-/protocols-2.0.1.tgz", + "integrity": "sha512-/XJ368cyBJ7fzLMwLKv1e4vLxOju2MNAIokcr7meSaNcVbWz/CPcW22cP04mwxOErdA5mwjA8Q6w/cdAQxVn7Q==", + "dev": true + }, + "proxy-from-env": { + "version": "1.1.0", + "resolved": "https://registry.npmjs.org/proxy-from-env/-/proxy-from-env-1.1.0.tgz", + "integrity": "sha512-D+zkORCbA9f1tdWRK0RaCR3GPv50cMxcrz4X8k5LTSUD1Dkw47mKJEZQNunItRTkWwgtaUSo1RVFRIG9ZXiFYg==", + "dev": true + }, + "punycode": { + "version": "2.1.1", + "resolved": "https://registry.npmjs.org/punycode/-/punycode-2.1.1.tgz", + "integrity": "sha512-XRsRjdf+j5ml+y/6GKHPZbrF/8p2Yga0JPtdqTIY2Xe5ohJPD9saDJJLPvp9+NSBprVvevdXZybnj2cv8OEd0A==", + "dev": true + }, + "pupa": { + "version": "3.1.0", + "resolved": "https://registry.npmjs.org/pupa/-/pupa-3.1.0.tgz", + "integrity": "sha512-FLpr4flz5xZTSJxSeaheeMKN/EDzMdK7b8PTOC6a5PYFKTucWbdqjgqaEyH0shFiSJrVB1+Qqi4Tk19ccU6Aug==", + "dev": true, + "requires": { + "escape-goat": "^4.0.0" + } + }, + "q": { + "version": "1.5.1", + "resolved": "https://registry.npmjs.org/q/-/q-1.5.1.tgz", + "integrity": "sha512-kV/CThkXo6xyFEZUugw/+pIOywXcDbFYgSct5cT3gqlbkBE1SJdwy6UQoZvodiWF/ckQLZyDE/Bu1M6gVu5lVw==", + "dev": true + }, + "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 + }, + "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 + }, + "rc": { + "version": "1.2.8", + "resolved": "https://registry.npmjs.org/rc/-/rc-1.2.8.tgz", + "integrity": "sha512-y3bGgqKj3QBdxLbLkomlohkvsA8gdAiUQlSBJnBhfn+BPxg4bc62d8TcBW15wavDfgexCgccckhcZvywyQYPOw==", + "dev": true, + "requires": { + "deep-extend": "^0.6.0", + "ini": "~1.3.0", + "minimist": "^1.2.0", + "strip-json-comments": "~2.0.1" + }, + "dependencies": { + "strip-json-comments": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/strip-json-comments/-/strip-json-comments-2.0.1.tgz", + "integrity": "sha512-4gB8na07fecVVkOI6Rs4e7T6NOTki5EmL7TUduTs6bu3EdnSycntVJ4re8kgZA+wx9IueI2Y11bfbgwtzuE0KQ==", + "dev": true + } + } + }, + "rc-config-loader": { + "version": "4.1.0", + "resolved": "https://registry.npmjs.org/rc-config-loader/-/rc-config-loader-4.1.0.tgz", + "integrity": "sha512-aW+kX4qy0CiM9L4fG4Us3oEOpIrOrXzWykAn+xldD07Y9PXWjTH744oHbv0Kc9ZwWaylw3jMjxaf14RgStrNrA==", + "dev": true, + "requires": { + "debug": "^4.1.1", + "js-yaml": "^4.0.0", + "json5": "^2.1.2", + "require-from-string": "^2.0.2" + } + }, + "read": { + "version": "1.0.7", + "resolved": "https://registry.npmjs.org/read/-/read-1.0.7.tgz", + "integrity": "sha512-rSOKNYUmaxy0om1BNjMN4ezNT6VKK+2xF4GBhc81mkH7L60i6dp8qPYrkndNLT3QPphoII3maL9PVC9XmhHwVQ==", + "dev": true, + "requires": { + "mute-stream": "~0.0.4" + } + }, + "read-cmd-shim": { + "version": "3.0.1", + "resolved": "https://registry.npmjs.org/read-cmd-shim/-/read-cmd-shim-3.0.1.tgz", + "integrity": "sha512-kEmDUoYf/CDy8yZbLTmhB1X9kkjf9Q80PCNsDMb7ufrGd6zZSQA1+UyjrO+pZm5K/S4OXCWJeiIt1JA8kAsa6g==", + "dev": true + }, + "read-package-json": { + "version": "5.0.2", + "resolved": "https://registry.npmjs.org/read-package-json/-/read-package-json-5.0.2.tgz", + "integrity": "sha512-BSzugrt4kQ/Z0krro8zhTwV1Kd79ue25IhNN/VtHFy1mG/6Tluyi+msc0UpwaoQzxSHa28mntAjIZY6kEgfR9Q==", + "dev": true, + "requires": { + "glob": "^8.0.1", + "json-parse-even-better-errors": "^2.3.1", + "normalize-package-data": "^4.0.0", + "npm-normalize-package-bin": "^2.0.0" + }, + "dependencies": { + "hosted-git-info": { + "version": "5.1.0", + "resolved": "https://registry.npmjs.org/hosted-git-info/-/hosted-git-info-5.1.0.tgz", + "integrity": "sha512-Ek+QmMEqZF8XrbFdwoDjSbm7rT23pCgEMOJmz6GPk/s4yH//RQfNPArhIxbguNxROq/+5lNBwCDHMhA903Kx1Q==", + "dev": true, + "requires": { + "lru-cache": "^7.5.1" + } + }, + "normalize-package-data": { + "version": "4.0.1", + "resolved": "https://registry.npmjs.org/normalize-package-data/-/normalize-package-data-4.0.1.tgz", + "integrity": "sha512-EBk5QKKuocMJhB3BILuKhmaPjI8vNRSpIfO9woLC6NyHVkKKdVEdAO1mrT0ZfxNR1lKwCcTkuZfmGIFdizZ8Pg==", + "dev": true, + "requires": { + "hosted-git-info": "^5.0.0", + "is-core-module": "^2.8.1", + "semver": "^7.3.5", + "validate-npm-package-license": "^3.0.4" + } + }, + "npm-normalize-package-bin": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/npm-normalize-package-bin/-/npm-normalize-package-bin-2.0.0.tgz", + "integrity": "sha512-awzfKUO7v0FscrSpRoogyNm0sajikhBWpU0QMrW09AMi9n1PoKU6WaIqUzuJSQnpciZZmJ/jMZ2Egfmb/9LiWQ==", + "dev": true + } + } + }, + "read-package-json-fast": { + "version": "2.0.3", + "resolved": "https://registry.npmjs.org/read-package-json-fast/-/read-package-json-fast-2.0.3.tgz", + "integrity": "sha512-W/BKtbL+dUjTuRL2vziuYhp76s5HZ9qQhd/dKfWIZveD0O40453QNyZhC0e63lqZrAQ4jiOapVoeJ7JrszenQQ==", + "dev": true, + "requires": { + "json-parse-even-better-errors": "^2.3.0", + "npm-normalize-package-bin": "^1.0.1" + } + }, + "read-pkg": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/read-pkg/-/read-pkg-3.0.0.tgz", + "integrity": "sha512-BLq/cCO9two+lBgiTYNqD6GdtK8s4NpaWrl6/rCO9w0TUS8oJl7cmToOZfRYllKTISY6nt1U7jQ53brmKqY6BA==", + "dev": true, + "requires": { + "load-json-file": "^4.0.0", + "normalize-package-data": "^2.3.2", + "path-type": "^3.0.0" + }, + "dependencies": { + "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 + }, + "load-json-file": { + "version": "4.0.0", + "resolved": "https://registry.npmjs.org/load-json-file/-/load-json-file-4.0.0.tgz", + "integrity": "sha512-Kx8hMakjX03tiGTLAIdJ+lL0htKnXjEZN6hk/tozf/WOuYGdZBJrZ+rCJRbVCugsjB3jMLn9746NsQIf5VjBMw==", + "dev": true, + "requires": { + "graceful-fs": "^4.1.2", + "parse-json": "^4.0.0", + "pify": "^3.0.0", + "strip-bom": "^3.0.0" + } + }, + "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, + "requires": { + "hosted-git-info": "^2.1.4", + "resolve": "^1.10.0", + "semver": "2 || 3 || 4 || 5", + "validate-npm-package-license": "^3.0.1" + } + }, + "parse-json": { + "version": "4.0.0", + "resolved": "https://registry.npmjs.org/parse-json/-/parse-json-4.0.0.tgz", + "integrity": "sha512-aOIos8bujGN93/8Ox/jPLh7RwVnPEysynVFE+fQZyg6jKELEHwzgKdLRFHUgXJL6kylijVSBC4BvN9OmsB48Rw==", + "dev": true, + "requires": { + "error-ex": "^1.3.1", + "json-parse-better-errors": "^1.0.1" + } + }, + "path-type": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/path-type/-/path-type-3.0.0.tgz", + "integrity": "sha512-T2ZUsdZFHgA3u4e5PfPbjd7HDDpxPnQb5jN0SrDsjNSuVXHJqtwTnWqG0B1jZrgmJ/7lj1EmVIByWt1gxGkWvg==", + "dev": true, + "requires": { + "pify": "^3.0.0" + } + }, + "pify": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/pify/-/pify-3.0.0.tgz", + "integrity": "sha512-C3FsVNH1udSEX48gGX1xfvwTWfsYWj5U+8/uK15BGzIGrKoUpghX8hWZwa/OFnakBiiVNmBvemTJR5mcy7iPcg==", + "dev": true + }, + "semver": { + "version": "5.7.1", + "resolved": "https://registry.npmjs.org/semver/-/semver-5.7.1.tgz", + "integrity": "sha512-sauaDf/PZdVgrLTNYHRtpXa1iRiKcaebiKQ1BJdpQlWH2lCvexQdX55snPFyK7QzpudqbCI0qXFfOasHdyNDGQ==", + "dev": true + }, + "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 + } + } + }, + "read-pkg-up": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/read-pkg-up/-/read-pkg-up-3.0.0.tgz", + "integrity": "sha512-YFzFrVvpC6frF1sz8psoHDBGF7fLPc+llq/8NB43oagqWkx8ar5zYtsTORtOjw9W2RHLpWP+zTWwBvf1bCmcSw==", + "dev": true, + "requires": { + "find-up": "^2.0.0", + "read-pkg": "^3.0.0" + }, + "dependencies": { + "find-up": { + "version": "2.1.0", + "resolved": "https://registry.npmjs.org/find-up/-/find-up-2.1.0.tgz", + "integrity": "sha512-NWzkk0jSJtTt08+FBFMvXoeZnOJD+jTtsRmBYbAIzJdX6l7dLgR7CTubCM5/eDdPUBvLCeVasP1brfVR/9/EZQ==", + "dev": true, + "requires": { + "locate-path": "^2.0.0" + } + }, + "locate-path": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/locate-path/-/locate-path-2.0.0.tgz", + "integrity": "sha512-NCI2kiDkyR7VeEKm27Kda/iQHyKJe1Bu0FlTbYp3CqJu+9IFe9bLyAjMxf5ZDDbEg+iMPzB5zYyUTSm8wVTKmA==", + "dev": true, + "requires": { + "p-locate": "^2.0.0", + "path-exists": "^3.0.0" + } + }, + "p-limit": { + "version": "1.3.0", + "resolved": "https://registry.npmjs.org/p-limit/-/p-limit-1.3.0.tgz", + "integrity": "sha512-vvcXsLAJ9Dr5rQOPk7toZQZJApBl2K4J6dANSsEuh6QI41JYcsS/qhTGa9ErIUUgK3WNQoJYvylxvjqmiqEA9Q==", + "dev": true, + "requires": { + "p-try": "^1.0.0" + } + }, + "p-locate": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/p-locate/-/p-locate-2.0.0.tgz", + "integrity": "sha512-nQja7m7gSKuewoVRen45CtVfODR3crN3goVQ0DDZ9N3yHxgpkuBhZqsaiotSQRrADUrne346peY7kT3TSACykg==", + "dev": true, + "requires": { + "p-limit": "^1.1.0" + } + }, + "p-try": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/p-try/-/p-try-1.0.0.tgz", + "integrity": "sha512-U1etNYuMJoIz3ZXSrrySFjsXQTWOx2/jdi86L+2pRvph/qMKL6sbcCYdH23fqsbm8TH2Gn0OybpT4eSFlCVHww==", + "dev": true + }, + "path-exists": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/path-exists/-/path-exists-3.0.0.tgz", + "integrity": "sha512-bpC7GYwiDYQ4wYLe+FA8lhRjhQCMcQGuSgGGqDkg/QerRWw9CmGRT0iSOVRSZJ29NMLZgIzqaljJ63oaL4NIJQ==", + "dev": true + } + } + }, + "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, + "requires": { + "inherits": "^2.0.3", + "string_decoder": "^1.1.1", + "util-deprecate": "^1.0.1" + } + }, + "readdir-scoped-modules": { + "version": "1.1.0", + "resolved": "https://registry.npmjs.org/readdir-scoped-modules/-/readdir-scoped-modules-1.1.0.tgz", + "integrity": "sha512-asaikDeqAQg7JifRsZn1NJZXo9E+VwlyCfbkZhwyISinqk5zNS6266HS5kah6P0SaQKGF6SkNnZVHUzHFYxYDw==", + "dev": true, + "requires": { + "debuglog": "^1.0.1", + "dezalgo": "^1.0.0", + "graceful-fs": "^4.1.2", + "once": "^1.3.0" + } + }, + "readdirp": { + "version": "3.6.0", + "resolved": "https://registry.npmjs.org/readdirp/-/readdirp-3.6.0.tgz", + "integrity": "sha512-hOS089on8RduqdbhvQ5Z37A0ESjsqz6qnRcffsMU3495FuTdqSm+7bhJ29JvIOsBDEEnan5DPu9t3To9VRlMzA==", + "dev": true, + "requires": { + "picomatch": "^2.2.1" + } + }, + "redent": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/redent/-/redent-3.0.0.tgz", + "integrity": "sha512-6tDA8g98We0zd0GvVeMT9arEOnTw9qM03L9cJXaCjrip1OO764RDBLBfrB4cwzNGDj5OA5ioymC9GkizgWJDUg==", + "dev": true, + "requires": { + "indent-string": "^4.0.0", + "strip-indent": "^3.0.0" + } + }, + "regexpp": { + "version": "3.2.0", + "resolved": "https://registry.npmjs.org/regexpp/-/regexpp-3.2.0.tgz", + "integrity": "sha512-pq2bWo9mVD43nbts2wGv17XLiNLya+GklZ8kaDLV2Z08gDCsGpnKn9BFMepvWuHCbyVvY7J5o5+BVvoQbmlJLg==", + "dev": true + }, + "registry-auth-token": { + "version": "5.0.1", + "resolved": "https://registry.npmjs.org/registry-auth-token/-/registry-auth-token-5.0.1.tgz", + "integrity": "sha512-UfxVOj8seK1yaIOiieV4FIP01vfBDLsY0H9sQzi9EbbUdJiuuBjJgLa1DpImXMNPnVkBD4eVxTEXcrZA6kfpJA==", + "dev": true, + "requires": { + "@pnpm/npm-conf": "^1.0.4" + } + }, + "registry-url": { + "version": "6.0.1", + "resolved": "https://registry.npmjs.org/registry-url/-/registry-url-6.0.1.tgz", + "integrity": "sha512-+crtS5QjFRqFCoQmvGduwYWEBng99ZvmFvF+cUJkGYF1L1BfU8C6Zp9T7f5vPAwyLkUExpvK+ANVZmGU49qi4Q==", + "dev": true, + "requires": { + "rc": "1.2.8" + } + }, + "remote-git-tags": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/remote-git-tags/-/remote-git-tags-3.0.0.tgz", + "integrity": "sha512-C9hAO4eoEsX+OXA4rla66pXZQ+TLQ8T9dttgQj18yuKlPMTVkIkdYXvlMC55IuUsIkV6DpmQYi10JKFLaU+l7w==", + "dev": true + }, + "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 + }, + "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 + }, + "resolve": { + "version": "1.22.1", + "resolved": "https://registry.npmjs.org/resolve/-/resolve-1.22.1.tgz", + "integrity": "sha512-nBpuuYuY5jFsli/JIs1oldw6fOQCBioohqWZg/2hiaOybXOft4lonv85uDOKXdf8rhyK159cxU5cDcK/NKk8zw==", + "dev": true, + "requires": { + "is-core-module": "^2.9.0", + "path-parse": "^1.0.7", + "supports-preserve-symlinks-flag": "^1.0.0" + } + }, + "resolve-alpn": { + "version": "1.2.1", + "resolved": "https://registry.npmjs.org/resolve-alpn/-/resolve-alpn-1.2.1.tgz", + "integrity": "sha512-0a1F4l73/ZFZOakJnQ3FvkJ2+gSTQWz/r2KE5OdDY0TxPm5h4GkqkWWfM47T7HsbnOtcJVEF4epCVy6u7Q3K+g==", + "dev": true + }, + "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, + "requires": { + "resolve-from": "^5.0.0" + }, + "dependencies": { + "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 + } + } + }, + "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 + }, + "responselike": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/responselike/-/responselike-3.0.0.tgz", + "integrity": "sha512-40yHxbNcl2+rzXvZuVkrYohathsSJlMTXKryG5y8uciHv1+xDLHQpgjG64JUO9nrEq2jGLH6IZ8BcZyw3wrweg==", + "dev": true, + "requires": { + "lowercase-keys": "^3.0.0" + } + }, + "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, + "requires": { + "onetime": "^5.1.0", + "signal-exit": "^3.0.2" + } + }, + "retry": { + "version": "0.12.0", + "resolved": "https://registry.npmjs.org/retry/-/retry-0.12.0.tgz", + "integrity": "sha512-9LkiTwjUh6rT555DtE9rTX+BKByPfrMzEAtnlEtdEwr3Nkffwiihqe2bWADg+OQRjt9gl6ICdmB/ZFDCGAtSow==", + "dev": true + }, + "reusify": { + "version": "1.0.4", + "resolved": "https://registry.npmjs.org/reusify/-/reusify-1.0.4.tgz", + "integrity": "sha512-U9nH88a3fc/ekCF1l0/UP1IosiuIjyTh7hBvXVMHYgVcfGvt897Xguj2UOLDeI5BG2m7/uwyaLVT6fbtCwTyzw==", + "dev": true + }, + "rimraf": { + "version": "3.0.2", + "resolved": "https://registry.npmjs.org/rimraf/-/rimraf-3.0.2.tgz", + "integrity": "sha512-JZkJMZkAGFFPP2YqXZXPbMlMBgsxzE8ILs4lMIX/2o0L9UBw9O/Y3o6wFw/i9YLapcUJWwqbi3kdxIPdC62TIA==", + "dev": true, + "requires": { + "glob": "^7.1.3" + }, + "dependencies": { + "glob": { + "version": "7.2.3", + "resolved": "https://registry.npmjs.org/glob/-/glob-7.2.3.tgz", + "integrity": "sha512-nFR0zLpU2YCaRxwoCJvL6UvCH2JFyFVIvwTLsIf21AuHlMskA1hhTdk+LlYJtOlYt9v6dvszD2BGRqBL+iQK9Q==", + "dev": true, + "requires": { + "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" + } + } + } + }, + "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 + }, + "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, + "requires": { + "queue-microtask": "^1.2.2" + } + }, + "rxjs": { + "version": "7.5.7", + "resolved": "https://registry.npmjs.org/rxjs/-/rxjs-7.5.7.tgz", + "integrity": "sha512-z9MzKh/UcOqB3i20H6rtrlaE/CgjLOvheWK/9ILrbhROGTweAi1BaFsTT9FbwZi5Trr1qNRs+MXkhmR06awzQA==", + "dev": true, + "requires": { + "tslib": "^2.1.0" + } + }, + "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 + }, + "safer-buffer": { + "version": "2.1.2", + "resolved": "https://registry.npmjs.org/safer-buffer/-/safer-buffer-2.1.2.tgz", + "integrity": "sha512-YZo3K82SD7Riyi0E1EQPojLz7kpepnSQI9IyPbHHg1XXXevb5dJI7tpyN2ADxGcQbHG7vcyRHk0cbwqcQriUtg==", + "dev": true + }, + "semver": { + "version": "7.3.8", + "resolved": "https://registry.npmjs.org/semver/-/semver-7.3.8.tgz", + "integrity": "sha512-NB1ctGL5rlHrPJtFDVIVzTyQylMLu9N9VICA6HSFJo8MCGVTMW6gfpicwKmmK/dAjTOrqu5l63JJOpDSrAis3A==", + "dev": true, + "requires": { + "lru-cache": "^6.0.0" + }, + "dependencies": { + "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, + "requires": { + "yallist": "^4.0.0" + } + } + } + }, + "semver-diff": { + "version": "4.0.0", + "resolved": "https://registry.npmjs.org/semver-diff/-/semver-diff-4.0.0.tgz", + "integrity": "sha512-0Ju4+6A8iOnpL/Thra7dZsSlOHYAHIeMxfhWQRI1/VLcT3WDBZKKtQt/QkBOsiIN9ZpuvHE6cGZ0x4glCMmfiA==", + "dev": true, + "requires": { + "semver": "^7.3.5" + } + }, + "semver-utils": { + "version": "1.1.4", + "resolved": "https://registry.npmjs.org/semver-utils/-/semver-utils-1.1.4.tgz", + "integrity": "sha512-EjnoLE5OGmDAVV/8YDoN5KiajNadjzIp9BAHOhYeQHt7j0UWxjmgsx4YD48wp4Ue1Qogq38F1GNUJNqF1kKKxA==", + "dev": true + }, + "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==", + "dev": true + }, + "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, + "requires": { + "kind-of": "^6.0.2" + } + }, + "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, + "requires": { + "shebang-regex": "^3.0.0" + } + }, + "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 + }, + "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 + }, + "sisteransi": { + "version": "1.0.5", + "resolved": "https://registry.npmjs.org/sisteransi/-/sisteransi-1.0.5.tgz", + "integrity": "sha512-bLGGlR1QxBcynn2d5YmDX4MGjlZvy2MRBDRNHLJ8VI6l6+9FUiyTFNJ0IveOSP0bcXgVDPRcfGqA0pjaqUpfVg==", + "dev": true + }, + "slash": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/slash/-/slash-3.0.0.tgz", + "integrity": "sha512-g9Q1haeby36OSStwb4ntCGGGaKsaVSjQ68fBxoQcutl5fS1vuY18H3wSt3jFyFtrkx+Kz0V1G85A4MyAdDMi2Q==", + "dev": true + }, + "smart-buffer": { + "version": "4.2.0", + "resolved": "https://registry.npmjs.org/smart-buffer/-/smart-buffer-4.2.0.tgz", + "integrity": "sha512-94hK0Hh8rPqQl2xXc3HsaBoOXKV20MToPkcXvwbISWLEs+64sBq5kFgn2kJDHb1Pry9yrP0dxrCI9RRci7RXKg==", + "dev": true + }, + "socks": { + "version": "2.7.1", + "resolved": "https://registry.npmjs.org/socks/-/socks-2.7.1.tgz", + "integrity": "sha512-7maUZy1N7uo6+WVEX6psASxtNlKaNVMlGQKkG/63nEDdLOWNbiUMoLK7X4uYoLhQstau72mLgfEWcXcwsaHbYQ==", + "dev": true, + "requires": { + "ip": "^2.0.0", + "smart-buffer": "^4.2.0" + } + }, + "socks-proxy-agent": { + "version": "7.0.0", + "resolved": "https://registry.npmjs.org/socks-proxy-agent/-/socks-proxy-agent-7.0.0.tgz", + "integrity": "sha512-Fgl0YPZ902wEsAyiQ+idGd1A7rSFx/ayC1CQVMw5P+EQx2V0SgpGtf6OKFhVjPflPUl9YMmEOnmfjCdMUsygww==", + "dev": true, + "requires": { + "agent-base": "^6.0.2", + "debug": "^4.3.3", + "socks": "^2.6.2" + } + }, + "sort-keys": { + "version": "4.2.0", + "resolved": "https://registry.npmjs.org/sort-keys/-/sort-keys-4.2.0.tgz", + "integrity": "sha512-aUYIEU/UviqPgc8mHR6IW1EGxkAXpeRETYcrzg8cLAvUPZcpAlleSXHV2mY7G12GphSH6Gzv+4MMVSSkbdteHg==", + "dev": true, + "requires": { + "is-plain-obj": "^2.0.0" + }, + "dependencies": { + "is-plain-obj": { + "version": "2.1.0", + "resolved": "https://registry.npmjs.org/is-plain-obj/-/is-plain-obj-2.1.0.tgz", + "integrity": "sha512-YWnfyRwxL/+SsrWYfOpUtz5b3YD+nyfkHvjbcanzk8zgyO4ASD67uVMRt8k5bM4lLMDnXfriRhOpemw+NfT1eA==", + "dev": true + } + } + }, + "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 + }, + "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, + "requires": { + "buffer-from": "^1.0.0", + "source-map": "^0.6.0" + } + }, + "spawn-please": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/spawn-please/-/spawn-please-1.0.0.tgz", + "integrity": "sha512-Kz33ip6NRNKuyTRo3aDWyWxeGeM0ORDO552Fs6E1nj4pLWPkl37SrRtTnq+MEopVaqgmaO6bAvVS+v64BJ5M/A==", + "dev": true + }, + "spdx-correct": { + "version": "3.1.1", + "resolved": "https://registry.npmjs.org/spdx-correct/-/spdx-correct-3.1.1.tgz", + "integrity": "sha512-cOYcUWwhCuHCXi49RhFRCyJEK3iPj1Ziz9DpViV3tbZOwXD49QzIN3MpOLJNxh2qwq2lJJZaKMVw9qNi4jTC0w==", + "dev": true, + "requires": { + "spdx-expression-parse": "^3.0.0", + "spdx-license-ids": "^3.0.0" + } + }, + "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 + }, + "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, + "requires": { + "spdx-exceptions": "^2.1.0", + "spdx-license-ids": "^3.0.0" + } + }, + "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 + }, + "split": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/split/-/split-1.0.1.tgz", + "integrity": "sha512-mTyOoPbrivtXnwnIxZRFYRrPNtEFKlpB2fvjSnCQUiAA6qAZzqwna5envK4uk6OIeP17CsdF3rSBGYVBsU0Tkg==", + "dev": true, + "requires": { + "through": "2" + } + }, + "split2": { + "version": "3.2.2", + "resolved": "https://registry.npmjs.org/split2/-/split2-3.2.2.tgz", + "integrity": "sha512-9NThjpgZnifTkJpzTZ7Eue85S49QwpNhZTq6GRJwObb6jnLFNGB7Qm73V5HewTROPyxD0C29xqmaI68bQtV+hg==", + "dev": true, + "requires": { + "readable-stream": "^3.0.0" + } + }, + "sprintf-js": { + "version": "1.0.3", + "resolved": "https://registry.npmjs.org/sprintf-js/-/sprintf-js-1.0.3.tgz", + "integrity": "sha512-D9cPgkvLlV3t3IzL0D0YLvGA9Ahk4PcvVwUbN0dSGr1aP0Nrt4AEnTUbuGvquEC0mA64Gqt1fzirlRs5ibXx8g==", + "dev": true + }, + "ssri": { + "version": "9.0.1", + "resolved": "https://registry.npmjs.org/ssri/-/ssri-9.0.1.tgz", + "integrity": "sha512-o57Wcn66jMQvfHG1FlYbWeZWW/dHZhJXjpIcTfXldXEk5nz5lStPo3mK0OJQfGR3RbZUlbISexbljkJzuEj/8Q==", + "dev": true, + "requires": { + "minipass": "^3.1.1" + } + }, + "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, + "requires": { + "safe-buffer": "~5.2.0" + } + }, + "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, + "requires": { + "emoji-regex": "^8.0.0", + "is-fullwidth-code-point": "^3.0.0", + "strip-ansi": "^6.0.1" + } + }, + "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, + "requires": { + "ansi-regex": "^5.0.1" + } + }, + "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 + }, + "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 + }, + "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, + "requires": { + "min-indent": "^1.0.0" + } + }, + "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 + }, + "strong-log-transformer": { + "version": "2.1.0", + "resolved": "https://registry.npmjs.org/strong-log-transformer/-/strong-log-transformer-2.1.0.tgz", + "integrity": "sha512-B3Hgul+z0L9a236FAUC9iZsL+nVHgoCJnqCbN588DjYxvGXaXaaFbfmQ/JhvKjZwsOukuR72XbHv71Qkug0HxA==", + "dev": true, + "requires": { + "duplexer": "^0.1.1", + "minimist": "^1.2.0", + "through": "^2.3.4" + } + }, + "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, + "requires": { + "has-flag": "^4.0.0" + } + }, + "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 + }, + "tar": { + "version": "6.1.11", + "resolved": "https://registry.npmjs.org/tar/-/tar-6.1.11.tgz", + "integrity": "sha512-an/KZQzQUkZCkuoAA64hM92X0Urb6VpRhAFllDzz44U2mcD5scmT3zBc4VgVpkugF580+DQn8eAFSyoQt0tznA==", + "dev": true, + "requires": { + "chownr": "^2.0.0", + "fs-minipass": "^2.0.0", + "minipass": "^3.0.0", + "minizlib": "^2.1.1", + "mkdirp": "^1.0.3", + "yallist": "^4.0.0" + } + }, + "tar-stream": { + "version": "2.2.0", + "resolved": "https://registry.npmjs.org/tar-stream/-/tar-stream-2.2.0.tgz", + "integrity": "sha512-ujeqbceABgwMZxEJnk2HDY2DlnUZ+9oEcb1KzTVfYHio0UE6dG71n60d8D2I4qNvleWrrXpmjpt7vZeF1LnMZQ==", + "dev": true, + "requires": { + "bl": "^4.0.3", + "end-of-stream": "^1.4.1", + "fs-constants": "^1.0.0", + "inherits": "^2.0.3", + "readable-stream": "^3.1.1" + } + }, + "temp-dir": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/temp-dir/-/temp-dir-1.0.0.tgz", + "integrity": "sha512-xZFXEGbG7SNC3itwBzI3RYjq/cEhBkx2hJuKGIUOcEULmkQExXiHat2z/qkISYsuR+IKumhEfKKbV5qXmhICFQ==", + "dev": true + }, + "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, + "requires": { + "@istanbuljs/schema": "^0.1.2", + "glob": "^7.1.4", + "minimatch": "^3.0.4" + }, + "dependencies": { + "glob": { + "version": "7.2.3", + "resolved": "https://registry.npmjs.org/glob/-/glob-7.2.3.tgz", + "integrity": "sha512-nFR0zLpU2YCaRxwoCJvL6UvCH2JFyFVIvwTLsIf21AuHlMskA1hhTdk+LlYJtOlYt9v6dvszD2BGRqBL+iQK9Q==", + "dev": true, + "requires": { + "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" + } + } + } + }, + "text-extensions": { + "version": "1.9.0", + "resolved": "https://registry.npmjs.org/text-extensions/-/text-extensions-1.9.0.tgz", + "integrity": "sha512-wiBrwC1EhBelW12Zy26JeOUkQ5mRu+5o8rpsJk5+2t+Y5vE7e842qtZDQ2g1NpX/29HdyFeJ4nSIhI47ENSxlQ==", + "dev": true + }, + "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 + }, + "through": { + "version": "2.3.8", + "resolved": "https://registry.npmjs.org/through/-/through-2.3.8.tgz", + "integrity": "sha512-w89qg7PI8wAdvX60bMDP+bFoD5Dvhm9oLheFp5O4a2QF0cSBGsBX4qZmadPMvVqlLJBBci+WqGGOAPvcDeNSVg==", + "dev": true + }, + "through2": { + "version": "4.0.2", + "resolved": "https://registry.npmjs.org/through2/-/through2-4.0.2.tgz", + "integrity": "sha512-iOqSav00cVxEEICeD7TjLB1sueEL+81Wpzp2bY17uZjZN0pWZPuo4suZ/61VujxmqSGFfgOcNuTZ85QJwNZQpw==", + "dev": true, + "requires": { + "readable-stream": "3" + } + }, + "tmp": { + "version": "0.0.33", + "resolved": "https://registry.npmjs.org/tmp/-/tmp-0.0.33.tgz", + "integrity": "sha512-jRCJlojKnZ3addtTOjdIqoRuPEKBvNXcGYqzO6zWZX8KfKEpnGY5jfggJQ3EjKuu8D4bJRr0y+cYJFmYbImXGw==", + "dev": true, + "requires": { + "os-tmpdir": "~1.0.2" + } + }, + "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, + "requires": { + "is-number": "^7.0.0" + } + }, + "tr46": { + "version": "0.0.3", + "resolved": "https://registry.npmjs.org/tr46/-/tr46-0.0.3.tgz", + "integrity": "sha512-N3WMsuqV66lT30CrXNbEjx4GEwlow3v6rr4mCcv6prnfwhS01rkgyFdjPNBYd9br7LpXV1+Emh01fHnq2Gdgrw==", + "dev": true + }, + "treeverse": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/treeverse/-/treeverse-2.0.0.tgz", + "integrity": "sha512-N5gJCkLu1aXccpOTtqV6ddSEi6ZmGkh3hjmbu1IjcavJK4qyOVQmi0myQKM7z5jVGmD68SJoliaVrMmVObhj6A==", + "dev": true + }, + "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 + }, + "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, + "requires": { + "@types/json5": "^0.0.29", + "json5": "^1.0.1", + "minimist": "^1.2.6", + "strip-bom": "^3.0.0" + }, + "dependencies": { + "json5": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/json5/-/json5-1.0.1.tgz", + "integrity": "sha512-aKS4WQjPenRxiQsC93MNfjx+nbF4PAdYzmd/1JIj8HYzqfbu86beTuNgXDzPknWk0n0uARlyewZo4s++ES36Ow==", + "dev": true, + "requires": { + "minimist": "^1.2.0" + } + }, + "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 + } + } + }, + "tslib": { + "version": "2.4.0", + "resolved": "https://registry.npmjs.org/tslib/-/tslib-2.4.0.tgz", + "integrity": "sha512-d6xOpEDfsi2CZVlPQzGeux8XMwLT9hssAsaPYExaQMuYskwb+x1x7J371tWlbBdWHroy99KnVB6qIkUbs5X3UQ==", + "dev": true + }, + "tsutils": { + "version": "3.21.0", + "resolved": "https://registry.npmjs.org/tsutils/-/tsutils-3.21.0.tgz", + "integrity": "sha512-mHKK3iUXL+3UF6xL5k0PEhKRUBKPBCv/+RkEOpjRWxxx27KKRBmmA60A9pgOUvMi8GKhRMPEmjBRPzs2W7O1OA==", + "dev": true, + "requires": { + "tslib": "^1.8.1" + }, + "dependencies": { + "tslib": { + "version": "1.14.1", + "resolved": "https://registry.npmjs.org/tslib/-/tslib-1.14.1.tgz", + "integrity": "sha512-Xni35NKzjgMrwevysHTCArtLDpPvye8zV/0E4EyYn43P7/7qvQwPh9BGkHewbMulVntbigmcT7rdX3BNo9wRJg==", + "dev": true + } + } + }, + "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, + "requires": { + "prelude-ls": "^1.2.1" + } + }, + "typedarray": { + "version": "0.0.6", + "resolved": "https://registry.npmjs.org/typedarray/-/typedarray-0.0.6.tgz", + "integrity": "sha512-/aCDEGatGvZ2BIk+HmLf4ifCJFwvKFNb9/JeZPMulfgFracn9QFcAf5GO8B/mweUjSoblS5In0cWhqpfs/5PQA==", + "dev": true + }, + "typedarray-to-buffer": { + "version": "3.1.5", + "resolved": "https://registry.npmjs.org/typedarray-to-buffer/-/typedarray-to-buffer-3.1.5.tgz", + "integrity": "sha512-zdu8XMNEDepKKR+XYOXAVPtWui0ly0NtohUscw+UmaHiAWT8hrV1rr//H6V+0DvJ3OQ19S979M0laLfX8rm82Q==", + "dev": true, + "requires": { + "is-typedarray": "^1.0.0" + } + }, + "typescript": { + "version": "4.8.4", + "resolved": "https://registry.npmjs.org/typescript/-/typescript-4.8.4.tgz", + "integrity": "sha512-QCh+85mCy+h0IGff8r5XWzOVSbBO+KfeYrMQh7NJ58QujwcE22u+NUSmUxqF+un70P9GXKxa2HCNiTTMJknyjQ==", + "dev": true + }, + "uglify-js": { + "version": "3.17.3", + "resolved": "https://registry.npmjs.org/uglify-js/-/uglify-js-3.17.3.tgz", + "integrity": "sha512-JmMFDME3iufZnBpyKL+uS78LRiC+mK55zWfM5f/pWBJfpOttXAqYfdDGRukYhJuyRinvPVAtUhvy7rlDybNtFg==", + "dev": true, + "optional": true + }, + "unique-filename": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/unique-filename/-/unique-filename-2.0.1.tgz", + "integrity": "sha512-ODWHtkkdx3IAR+veKxFV+VBkUMcN+FaqzUUd7IZzt+0zhDZFPFxhlqwPF3YQvMHx1TD0tdgYl+kuPnJ8E6ql7A==", + "dev": true, + "requires": { + "unique-slug": "^3.0.0" + } + }, + "unique-slug": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/unique-slug/-/unique-slug-3.0.0.tgz", + "integrity": "sha512-8EyMynh679x/0gqE9fT9oilG+qEt+ibFyqjuVTsZn1+CMxH+XLlpvr2UZx4nVcCwTpx81nICr2JQFkM+HPLq4w==", + "dev": true, + "requires": { + "imurmurhash": "^0.1.4" + } + }, + "unique-string": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/unique-string/-/unique-string-3.0.0.tgz", + "integrity": "sha512-VGXBUVwxKMBUznyffQweQABPRRW1vHZAbadFZud4pLFAqRGvv/96vafgjWFqzourzr8YonlQiPgH0YCJfawoGQ==", + "dev": true, + "requires": { + "crypto-random-string": "^4.0.0" + } + }, + "universal-user-agent": { + "version": "6.0.0", + "resolved": "https://registry.npmjs.org/universal-user-agent/-/universal-user-agent-6.0.0.tgz", + "integrity": "sha512-isyNax3wXoKaulPDZWHQqbmIx1k2tb9fb3GGDBRxCscfYV2Ch7WxPArBsFEG8s/safwXTT7H4QGhaIkTp9447w==", + "dev": true + }, + "universalify": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/universalify/-/universalify-2.0.0.tgz", + "integrity": "sha512-hAZsKq7Yy11Zu1DE0OzWjw7nnLZmJZYTDZZyEFHZdUhV8FkH5MCfoU1XMaxXovpyW5nq5scPqq0ZDP9Zyl04oQ==", + "dev": true + }, + "untildify": { + "version": "4.0.0", + "resolved": "https://registry.npmjs.org/untildify/-/untildify-4.0.0.tgz", + "integrity": "sha512-KK8xQ1mkzZeg9inewmFVDNkg3l5LUhoq9kN6iWYB/CC9YMG8HA+c1Q8HwDe6dEX7kErrEVNVBO3fWsVq5iDgtw==", + "dev": true + }, + "upath": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/upath/-/upath-2.0.1.tgz", + "integrity": "sha512-1uEe95xksV1O0CYKXo8vQvN1JEbtJp7lb7C5U9HMsIp6IVwntkH/oNUzyVNQSd4S1sYk2FpSSW44FqMc8qee5w==", + "dev": true + }, + "update-notifier": { + "version": "6.0.2", + "resolved": "https://registry.npmjs.org/update-notifier/-/update-notifier-6.0.2.tgz", + "integrity": "sha512-EDxhTEVPZZRLWYcJ4ZXjGFN0oP7qYvbXWzEgRm/Yql4dHX5wDbvh89YHP6PK1lzZJYrMtXUuZZz8XGK+U6U1og==", + "dev": true, + "requires": { + "boxen": "^7.0.0", + "chalk": "^5.0.1", + "configstore": "^6.0.0", + "has-yarn": "^3.0.0", + "import-lazy": "^4.0.0", + "is-ci": "^3.0.1", + "is-installed-globally": "^0.4.0", + "is-npm": "^6.0.0", + "is-yarn-global": "^0.4.0", + "latest-version": "^7.0.0", + "pupa": "^3.1.0", + "semver": "^7.3.7", + "semver-diff": "^4.0.0", + "xdg-basedir": "^5.1.0" + }, + "dependencies": { + "chalk": { + "version": "5.1.0", + "resolved": "https://registry.npmjs.org/chalk/-/chalk-5.1.0.tgz", + "integrity": "sha512-56zD4khRTBoIyzUYAFgDDaPhUMN/fC/rySe6aZGqbj/VWiU2eI3l6ZLOtYGFZAV5v02mwPjtpzlrOveJiz5eZQ==", + "dev": true + }, + "ci-info": { + "version": "3.5.0", + "resolved": "https://registry.npmjs.org/ci-info/-/ci-info-3.5.0.tgz", + "integrity": "sha512-yH4RezKOGlOhxkmhbeNuC4eYZKAUsEaGtBuBzDDP1eFUKiccDWzBABxBfOx31IDwDIXMTxWuwAxUGModvkbuVw==", + "dev": true + }, + "is-ci": { + "version": "3.0.1", + "resolved": "https://registry.npmjs.org/is-ci/-/is-ci-3.0.1.tgz", + "integrity": "sha512-ZYvCgrefwqoQ6yTyYUbQu64HsITZ3NfKX1lzaEYdkTDcfKzzCI/wthRRYKkdjHKFVgNiXKAKm65Zo1pk2as/QQ==", + "dev": true, + "requires": { + "ci-info": "^3.2.0" + } + } + } + }, + "uri-js": { + "version": "4.4.1", + "resolved": "https://registry.npmjs.org/uri-js/-/uri-js-4.4.1.tgz", + "integrity": "sha512-7rKUyy33Q1yc98pQ1DAmLtwX109F7TIfWlW1Ydo8Wl1ii1SeHieeh0HHfPeL2fMXK6z0s8ecKs9frCuLJvndBg==", + "dev": true, + "requires": { + "punycode": "^2.1.0" + } + }, + "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 + }, + "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 + }, + "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, + "requires": { + "@jridgewell/trace-mapping": "^0.3.12", + "@types/istanbul-lib-coverage": "^2.0.1", + "convert-source-map": "^1.6.0" + } + }, + "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, + "requires": { + "spdx-correct": "^3.0.0", + "spdx-expression-parse": "^3.0.0" + } + }, + "validate-npm-package-name": { + "version": "4.0.0", + "resolved": "https://registry.npmjs.org/validate-npm-package-name/-/validate-npm-package-name-4.0.0.tgz", + "integrity": "sha512-mzR0L8ZDktZjpX4OB46KT+56MAhl4EIazWP/+G/HPGuvfdaqg4YsCdtOm6U9+LOFyYDoh4dpnpxZRB9MQQns5Q==", + "dev": true, + "requires": { + "builtins": "^5.0.0" + } + }, + "walk-up-path": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/walk-up-path/-/walk-up-path-1.0.0.tgz", + "integrity": "sha512-hwj/qMDUEjCU5h0xr90KGCf0tg0/LgJbmOWgrWKYlcJZM7XvquvUJZ0G/HMGr7F7OQMOUuPHWP9JpriinkAlkg==", + "dev": true + }, + "wcwidth": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/wcwidth/-/wcwidth-1.0.1.tgz", + "integrity": "sha512-XHPEwS0q6TaxcvG85+8EYkbiCux2XtWG2mkc47Ng2A77BQu9+DqIOJldST4HgPkuea7dvKSj5VgX3P1d4rW8Tg==", + "dev": true, + "requires": { + "defaults": "^1.0.3" + } + }, + "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==", + "dev": true + }, + "whatwg-url": { + "version": "5.0.0", + "resolved": "https://registry.npmjs.org/whatwg-url/-/whatwg-url-5.0.0.tgz", + "integrity": "sha512-saE57nupxk6v3HY35+jzBwYa0rKSy0XR8JSxZPwgLr7ys0IBzhGviA1/TUGJLmSVqs8pb9AnvICXEuOHLprYTw==", + "dev": true, + "requires": { + "tr46": "~0.0.3", + "webidl-conversions": "^3.0.0" + } + }, + "which": { + "version": "2.0.2", + "resolved": "https://registry.npmjs.org/which/-/which-2.0.2.tgz", + "integrity": "sha512-BLI3Tl1TW3Pvl70l3yq3Y64i+awpwXqsGBYWkkqMtnbXgrMD+yj7rhW0kuEDxzJaYXGjEW5ogapKNMEKNMjibA==", + "dev": true, + "requires": { + "isexe": "^2.0.0" + } + }, + "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==", + "dev": true, + "requires": { + "string-width": "^1.0.2 || 2 || 3 || 4" + } + }, + "widest-line": { + "version": "4.0.1", + "resolved": "https://registry.npmjs.org/widest-line/-/widest-line-4.0.1.tgz", + "integrity": "sha512-o0cyEG0e8GPzT4iGHphIOh0cJOV8fivsXxddQasHPHfoZf1ZexrfeA21w2NaEN1RHE+fXlfISmOE8R9N3u3Qig==", + "dev": true, + "requires": { + "string-width": "^5.0.1" + }, + "dependencies": { + "ansi-regex": { + "version": "6.0.1", + "resolved": "https://registry.npmjs.org/ansi-regex/-/ansi-regex-6.0.1.tgz", + "integrity": "sha512-n5M855fKb2SsfMIiFFoVrABHJC8QtHwVx+mHWP3QcEqBHYienj5dHSgjbxtC0WEZXYt4wcD6zrQElDPhFuZgfA==", + "dev": true + }, + "emoji-regex": { + "version": "9.2.2", + "resolved": "https://registry.npmjs.org/emoji-regex/-/emoji-regex-9.2.2.tgz", + "integrity": "sha512-L18DaJsXSUk2+42pv8mLs5jJT2hqFkFE4j21wOmgbUqsZ2hL72NsUU785g9RXgo3s0ZNgVl42TiHp3ZtOv/Vyg==", + "dev": true + }, + "string-width": { + "version": "5.1.2", + "resolved": "https://registry.npmjs.org/string-width/-/string-width-5.1.2.tgz", + "integrity": "sha512-HnLOCR3vjcY8beoNLtcjZ5/nxn2afmME6lhrDrebokqMap+XbeW8n9TXpPDOqdGK5qcI3oT0GKTW6wC7EMiVqA==", + "dev": true, + "requires": { + "eastasianwidth": "^0.2.0", + "emoji-regex": "^9.2.2", + "strip-ansi": "^7.0.1" + } + }, + "strip-ansi": { + "version": "7.0.1", + "resolved": "https://registry.npmjs.org/strip-ansi/-/strip-ansi-7.0.1.tgz", + "integrity": "sha512-cXNxvT8dFNRVfhVME3JAe98mkXDYN2O1l7jmcwMnOslDeESg1rF/OZMtK0nRAhiari1unG5cD4jG3rapUAkLbw==", + "dev": true, + "requires": { + "ansi-regex": "^6.0.1" + } + } + } + }, + "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 + }, + "wordwrap": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/wordwrap/-/wordwrap-1.0.0.tgz", + "integrity": "sha512-gvVzJFlPycKc5dZN4yPkP8w7Dc37BtP1yczEneOb4uq34pXZcvrtRTmWV8W+Ume+XCxKgbjM+nevkyFPMybd4Q==", + "dev": true + }, + "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, + "requires": { + "ansi-styles": "^4.0.0", + "string-width": "^4.1.0", + "strip-ansi": "^6.0.0" + } + }, + "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 + }, + "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, + "requires": { + "imurmurhash": "^0.1.4", + "signal-exit": "^3.0.7" + } + }, + "write-json-file": { + "version": "4.3.0", + "resolved": "https://registry.npmjs.org/write-json-file/-/write-json-file-4.3.0.tgz", + "integrity": "sha512-PxiShnxf0IlnQuMYOPPhPkhExoCQuTUNPOa/2JWCYTmBquU9njyyDuwRKN26IZBlp4yn1nt+Agh2HOOBl+55HQ==", + "dev": true, + "requires": { + "detect-indent": "^6.0.0", + "graceful-fs": "^4.1.15", + "is-plain-obj": "^2.0.0", + "make-dir": "^3.0.0", + "sort-keys": "^4.0.0", + "write-file-atomic": "^3.0.0" + }, + "dependencies": { + "is-plain-obj": { + "version": "2.1.0", + "resolved": "https://registry.npmjs.org/is-plain-obj/-/is-plain-obj-2.1.0.tgz", + "integrity": "sha512-YWnfyRwxL/+SsrWYfOpUtz5b3YD+nyfkHvjbcanzk8zgyO4ASD67uVMRt8k5bM4lLMDnXfriRhOpemw+NfT1eA==", + "dev": true + }, + "write-file-atomic": { + "version": "3.0.3", + "resolved": "https://registry.npmjs.org/write-file-atomic/-/write-file-atomic-3.0.3.tgz", + "integrity": "sha512-AvHcyZ5JnSfq3ioSyjrBkH9yW4m7Ayk8/9My/DD9onKeu/94fwrMocemO2QAJFAlnnDN+ZDS+ZjAR5ua1/PV/Q==", + "dev": true, + "requires": { + "imurmurhash": "^0.1.4", + "is-typedarray": "^1.0.0", + "signal-exit": "^3.0.2", + "typedarray-to-buffer": "^3.1.5" + } + } + } + }, + "write-pkg": { + "version": "4.0.0", + "resolved": "https://registry.npmjs.org/write-pkg/-/write-pkg-4.0.0.tgz", + "integrity": "sha512-v2UQ+50TNf2rNHJ8NyWttfm/EJUBWMJcx6ZTYZr6Qp52uuegWw/lBkCtCbnYZEmPRNL61m+u67dAmGxo+HTULA==", + "dev": true, + "requires": { + "sort-keys": "^2.0.0", + "type-fest": "^0.4.1", + "write-json-file": "^3.2.0" + }, + "dependencies": { + "detect-indent": { + "version": "5.0.0", + "resolved": "https://registry.npmjs.org/detect-indent/-/detect-indent-5.0.0.tgz", + "integrity": "sha512-rlpvsxUtM0PQvy9iZe640/IWwWYyBsTApREbA1pHOpmOUIl9MkP/U4z7vTtg4Oaojvqhxt7sdufnT0EzGaR31g==", + "dev": true + }, + "make-dir": { + "version": "2.1.0", + "resolved": "https://registry.npmjs.org/make-dir/-/make-dir-2.1.0.tgz", + "integrity": "sha512-LS9X+dc8KLxXCb8dni79fLIIUA5VyZoyjSMCwTluaXA0o27cCK0bhXkpgw+sTXVpPy/lSO57ilRixqk0vDmtRA==", + "dev": true, + "requires": { + "pify": "^4.0.1", + "semver": "^5.6.0" + } + }, + "pify": { + "version": "4.0.1", + "resolved": "https://registry.npmjs.org/pify/-/pify-4.0.1.tgz", + "integrity": "sha512-uB80kBFb/tfd68bVleG9T5GGsGPjJrLAUpR5PZIrhBnIaRTQRjqdJSsIKkOP6OAIFbj7GOrcudc5pNjZ+geV2g==", + "dev": true + }, + "semver": { + "version": "5.7.1", + "resolved": "https://registry.npmjs.org/semver/-/semver-5.7.1.tgz", + "integrity": "sha512-sauaDf/PZdVgrLTNYHRtpXa1iRiKcaebiKQ1BJdpQlWH2lCvexQdX55snPFyK7QzpudqbCI0qXFfOasHdyNDGQ==", + "dev": true + }, + "sort-keys": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/sort-keys/-/sort-keys-2.0.0.tgz", + "integrity": "sha512-/dPCrG1s3ePpWm6yBbxZq5Be1dXGLyLn9Z791chDC3NFrpkVbWGzkBwPN1knaciexFXgRJ7hzdnwZ4stHSDmjg==", + "dev": true, + "requires": { + "is-plain-obj": "^1.0.0" + } + }, + "type-fest": { + "version": "0.4.1", + "resolved": "https://registry.npmjs.org/type-fest/-/type-fest-0.4.1.tgz", + "integrity": "sha512-IwzA/LSfD2vC1/YDYMv/zHP4rDF1usCwllsDpbolT3D4fUepIO7f9K70jjmUewU/LmGUKJcwcVtDCpnKk4BPMw==", + "dev": true + }, + "write-file-atomic": { + "version": "2.4.3", + "resolved": "https://registry.npmjs.org/write-file-atomic/-/write-file-atomic-2.4.3.tgz", + "integrity": "sha512-GaETH5wwsX+GcnzhPgKcKjJ6M2Cq3/iZp1WyY/X1CSqrW+jVNM9Y7D8EC2sM4ZG/V8wZlSniJnCKWPmBYAucRQ==", + "dev": true, + "requires": { + "graceful-fs": "^4.1.11", + "imurmurhash": "^0.1.4", + "signal-exit": "^3.0.2" + } + }, + "write-json-file": { + "version": "3.2.0", + "resolved": "https://registry.npmjs.org/write-json-file/-/write-json-file-3.2.0.tgz", + "integrity": "sha512-3xZqT7Byc2uORAatYiP3DHUUAVEkNOswEWNs9H5KXiicRTvzYzYqKjYc4G7p+8pltvAw641lVByKVtMpf+4sYQ==", + "dev": true, + "requires": { + "detect-indent": "^5.0.0", + "graceful-fs": "^4.1.15", + "make-dir": "^2.1.0", + "pify": "^4.0.1", + "sort-keys": "^2.0.0", + "write-file-atomic": "^2.4.2" + } + } + } + }, + "xdg-basedir": { + "version": "5.1.0", + "resolved": "https://registry.npmjs.org/xdg-basedir/-/xdg-basedir-5.1.0.tgz", + "integrity": "sha512-GCPAHLvrIH13+c0SuacwvRYj2SxJXQ4kaVTT5xgL3kPrz56XxkF21IGhjSE1+W0aw7gpBWRGXLCPnPby6lSpmQ==", + "dev": true + }, + "xtend": { + "version": "4.0.2", + "resolved": "https://registry.npmjs.org/xtend/-/xtend-4.0.2.tgz", + "integrity": "sha512-LKYU1iAXJXUgAXn9URjiu+MWhyUXHsvfp7mcuYm9dSUKK0/CjtrUwFAxD82/mCWbtLsGjFIad0wIsod4zrTAEQ==", + "dev": true + }, + "y18n": { + "version": "5.0.8", + "resolved": "https://registry.npmjs.org/y18n/-/y18n-5.0.8.tgz", + "integrity": "sha512-0pfFzegeDWJHJIAmTLRP2DwHjdF5s7jo9tuztdQxAhINCdvS+3nGINqPd00AphqJR/0LhANUS6/+7SCb98YOfA==", + "dev": true + }, + "yallist": { + "version": "4.0.0", + "resolved": "https://registry.npmjs.org/yallist/-/yallist-4.0.0.tgz", + "integrity": "sha512-3wdGidZyq5PB084XLES5TpOSRA3wjXAlIWMhum2kRcv/41Sn2emQ0dycQW4uZXLejwKvg6EsvbdlVL+FYEct7A==", + "dev": true + }, + "yaml": { + "version": "1.10.2", + "resolved": "https://registry.npmjs.org/yaml/-/yaml-1.10.2.tgz", + "integrity": "sha512-r3vXyErRCYJ7wg28yvBY5VSoAF8ZvlcW9/BwUzEtUsjvX/DKs24dIkuwjtuprwJJHsbyUbLApepYTR1BN4uHrg==", + "dev": true + }, + "yargs": { + "version": "16.2.0", + "resolved": "https://registry.npmjs.org/yargs/-/yargs-16.2.0.tgz", + "integrity": "sha512-D1mvvtDG0L5ft/jGWkLpG1+m0eQxOfaBvTNELraWj22wSVUMWxZUvYgJYcKh6jGGIkJFhH4IZPQhR4TKpc8mBw==", + "dev": true, + "requires": { + "cliui": "^7.0.2", + "escalade": "^3.1.1", + "get-caller-file": "^2.0.5", + "require-directory": "^2.1.1", + "string-width": "^4.2.0", + "y18n": "^5.0.5", + "yargs-parser": "^20.2.2" + } + }, + "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 + }, + "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 + } + } } diff --git a/package.json b/package.json index c000297190..262f60bf65 100644 --- a/package.json +++ b/package.json @@ -20,28 +20,32 @@ "url": "https://github.com/feathersjs/feathers/issues" }, "engines": { - "node": ">= 12" + "node": ">= 14" }, "scripts": { "install": "lerna bootstrap", "publish": "lerna publish && git commit -am \"chore: Update changelog\" && git push origin", "publish:premajor": "lerna publish premajor --preid pre --pre-dist-tag pre && git commit -am \"chore: Update version and changelog\" && git push origin", - "publish:prerelease": "lerna publish prerelease --preid pre --pre-dist-tag pre --dist-tag pre && git commit -am \"chore: Update version and changelog\" && git push origin", - "lint": "eslint packages/**/src/**/*.ts packages/**/test/**/*.ts --fix", - "update-dependencies": "ncu -u && lerna exec -- ncu -u -x node-fetch", + "publish:prerelease": "lerna publish prerelease --preid pre --pre-dist-tag pre --dist-tag pre --force-publish && git commit -am \"chore: Update version and changelog\" && git push origin", + "prettier": "npx prettier \"packages/{,!(node_modules)/**/(src|test)/**/}*.ts\" --write", + "eslint": "eslint \"packages/**/*.ts\" --fix", + "lint": "npm run prettier && npm run eslint", + "compile": "lerna run compile", + "update-dependencies": "ncu -u && lerna exec -- ncu -u -x node-fetch -x chalk -x axios", "clean": "find . -name node_modules -exec rm -rf '{}' + && find . -name package-lock.json -exec rm -rf '{}' +", "test:deno": "deno test --config deno/tsconfig.json deno/test.ts", - "test": "npm run lint && nyc lerna run test" + "test": "npm run lint && npm run compile && c8 lerna run test --ignore @feathersjs/tests" }, "devDependencies": { - "@typescript-eslint/eslint-plugin": "^5.8.1", - "@typescript-eslint/parser": "^5.8.1", - "eslint": "^8.6.0", - "eslint-plugin-import": "^2.25.3", - "eslint-plugin-prefer-arrow": "^1.2.3", - "lerna": "^4.0.0", - "npm-check-updates": "^12.0.5", - "nyc": "^15.1.0", - "typescript": "^4.5.4" + "@typescript-eslint/eslint-plugin": "^5.39.0", + "@typescript-eslint/parser": "^5.39.0", + "c8": "^7.12.0", + "eslint": "^8.24.0", + "eslint-config-prettier": "^8.5.0", + "eslint-plugin-prettier": "^4.2.1", + "lerna": "^5.6.1", + "npm-check-updates": "^16.3.8", + "prettier": "^2.7.1", + "typescript": "^4.8.4" } } diff --git a/packages/adapter-commons/CHANGELOG.md b/packages/adapter-commons/CHANGELOG.md index 34d10356fc..6ccbc7047a 100644 --- a/packages/adapter-commons/CHANGELOG.md +++ b/packages/adapter-commons/CHANGELOG.md @@ -3,632 +3,445 @@ All notable changes to this project will be documented in this file. See [Conventional Commits](https://conventionalcommits.org) for commit guidelines. -# [5.0.0-pre.16](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.15...v5.0.0-pre.16) (2022-01-12) +# [5.0.0-pre.31](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.30...v5.0.0-pre.31) (2022-10-12) **Note:** Version bump only for package @feathersjs/adapter-commons +# [5.0.0-pre.30](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.29...v5.0.0-pre.30) (2022-10-07) +### Features +- **core:** Allow to unregister services at runtime ([#2756](https://github.com/feathersjs/feathers/issues/2756)) ([d16601f](https://github.com/feathersjs/feathers/commit/d16601f2277dca5357866ffdefba2a611f6dc7fa)) +# [5.0.0-pre.29](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.28...v5.0.0-pre.29) (2022-09-16) -# [5.0.0-pre.15](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.14...v5.0.0-pre.15) (2021-11-27) +**Note:** Version bump only for package @feathersjs/adapter-commons +# [5.0.0-pre.28](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.27...v5.0.0-pre.28) (2022-08-03) ### Bug Fixes -* **adapter-commons:** clean up in sort.ts and select function ([#2492](https://github.com/feathersjs/feathers/issues/2492)) ([c3ec8a4](https://github.com/feathersjs/feathers/commit/c3ec8a418bdc85506e3c5100015720a45454d8d3)) -* **adapter-commons:** Fix sorting for embedded objects ([#2488](https://github.com/feathersjs/feathers/issues/2488)) ([9c22f70](https://github.com/feathersjs/feathers/commit/9c22f70a838cb6341775d91705a7527c8fc5590e)) -* **typescript:** Overall typing improvements ([#2478](https://github.com/feathersjs/feathers/issues/2478)) ([b8eb804](https://github.com/feathersjs/feathers/commit/b8eb804158556d9651a8607e3c3fda15e0bfd110)) +- **cli:** Improve generated application and client ([#2701](https://github.com/feathersjs/feathers/issues/2701)) ([bd55ffb](https://github.com/feathersjs/feathers/commit/bd55ffb812e89bf215f4515e7f137656ea888c3f)) +# [5.0.0-pre.27](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.26...v5.0.0-pre.27) (2022-07-13) +**Note:** Version bump only for package @feathersjs/adapter-commons +# [5.0.0-pre.26](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.25...v5.0.0-pre.26) (2022-06-22) +**Note:** Version bump only for package @feathersjs/adapter-commons -# [5.0.0-pre.14](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.13...v5.0.0-pre.14) (2021-10-13) +# [5.0.0-pre.25](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.24...v5.0.0-pre.25) (2022-06-22) **Note:** Version bump only for package @feathersjs/adapter-commons +# [5.0.0-pre.24](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.23...v5.0.0-pre.24) (2022-06-21) +### Features +- **knex:** Add KnexJS SQL database adapter to core ([#2671](https://github.com/feathersjs/feathers/issues/2671)) ([9380fff](https://github.com/feathersjs/feathers/commit/9380fff58596e8bb90b8bb098d2795b7eadfec20)) - -# [5.0.0-pre.13](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.12...v5.0.0-pre.13) (2021-10-13) +# [5.0.0-pre.23](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.22...v5.0.0-pre.23) (2022-06-06) **Note:** Version bump only for package @feathersjs/adapter-commons +# [5.0.0-pre.22](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.21...v5.0.0-pre.22) (2022-05-24) +**Note:** Version bump only for package @feathersjs/adapter-commons - - -# [5.0.0-pre.12](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.11...v5.0.0-pre.12) (2021-10-12) +# [5.0.0-pre.21](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.20...v5.0.0-pre.21) (2022-05-23) **Note:** Version bump only for package @feathersjs/adapter-commons +# [5.0.0-pre.20](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.19...v5.0.0-pre.20) (2022-05-04) +### Bug Fixes +- **dependencies:** Lock monorepo package version numbers ([#2623](https://github.com/feathersjs/feathers/issues/2623)) ([5640c10](https://github.com/feathersjs/feathers/commit/5640c1020cc139994e695d658c08bad3494db507)) +# [5.0.0-pre.19](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.18...v5.0.0-pre.19) (2022-05-01) -# [5.0.0-pre.11](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.10...v5.0.0-pre.11) (2021-10-06) - -**Note:** Version bump only for package @feathersjs/adapter-commons +### Bug Fixes +- **adapter-commons:** Clarify adapter query filtering ([#2607](https://github.com/feathersjs/feathers/issues/2607)) ([2dac771](https://github.com/feathersjs/feathers/commit/2dac771b0a3298d6dd25994d05186701b0617718)) +### Features +- **mongodb:** Add feathers-mongodb adapter as @feathersjs/mongodb ([#2610](https://github.com/feathersjs/feathers/issues/2610)) ([6d43734](https://github.com/feathersjs/feathers/commit/6d43734a53db02c435cafc52a22dca414e5d0940)) +- **typescript:** Improve adapter typings ([#2605](https://github.com/feathersjs/feathers/issues/2605)) ([3b2ca0a](https://github.com/feathersjs/feathers/commit/3b2ca0a6a8e03e8390272c4d7e930b4bffdaacf5)) +- **typescript:** Improve params and query typeability ([#2600](https://github.com/feathersjs/feathers/issues/2600)) ([df28b76](https://github.com/feathersjs/feathers/commit/df28b7619161f1df5e700326f52cca1a92dc5d28)) +### BREAKING CHANGES -# [5.0.0-pre.10](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.9...v5.0.0-pre.10) (2021-09-19) +- **adapter-commons:** Changes the common adapter base class to use `sanitizeQuery` and `sanitizeData` -**Note:** Version bump only for package @feathersjs/adapter-commons +# [5.0.0-pre.18](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.17...v5.0.0-pre.18) (2022-04-11) +### Features +- **core:** Add app.teardown functionality ([#2570](https://github.com/feathersjs/feathers/issues/2570)) ([fcdf524](https://github.com/feathersjs/feathers/commit/fcdf524ae1995bb59265d39f12e98b7794bed023)) +- **core:** Finalize app.teardown() functionality ([#2584](https://github.com/feathersjs/feathers/issues/2584)) ([1a166f3](https://github.com/feathersjs/feathers/commit/1a166f3ded811ecacf0ae8cb67880bc9fa2eeafa)) +# [5.0.0-pre.17](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.16...v5.0.0-pre.17) (2022-02-15) +**Note:** Version bump only for package @feathersjs/adapter-commons -# [5.0.0-pre.9](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.8...v5.0.0-pre.9) (2021-08-09) +# [5.0.0-pre.16](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.15...v5.0.0-pre.16) (2022-01-12) **Note:** Version bump only for package @feathersjs/adapter-commons +# [5.0.0-pre.15](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.14...v5.0.0-pre.15) (2021-11-27) +### Bug Fixes +- **adapter-commons:** clean up in sort.ts and select function ([#2492](https://github.com/feathersjs/feathers/issues/2492)) ([c3ec8a4](https://github.com/feathersjs/feathers/commit/c3ec8a418bdc85506e3c5100015720a45454d8d3)) +- **adapter-commons:** Fix sorting for embedded objects ([#2488](https://github.com/feathersjs/feathers/issues/2488)) ([9c22f70](https://github.com/feathersjs/feathers/commit/9c22f70a838cb6341775d91705a7527c8fc5590e)) +- **typescript:** Overall typing improvements ([#2478](https://github.com/feathersjs/feathers/issues/2478)) ([b8eb804](https://github.com/feathersjs/feathers/commit/b8eb804158556d9651a8607e3c3fda15e0bfd110)) - -# [5.0.0-pre.8](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.7...v5.0.0-pre.8) (2021-08-09) +# [5.0.0-pre.14](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.13...v5.0.0-pre.14) (2021-10-13) **Note:** Version bump only for package @feathersjs/adapter-commons +# [5.0.0-pre.13](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.12...v5.0.0-pre.13) (2021-10-13) +**Note:** Version bump only for package @feathersjs/adapter-commons +# [5.0.0-pre.12](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.11...v5.0.0-pre.12) (2021-10-12) +**Note:** Version bump only for package @feathersjs/adapter-commons -# [5.0.0-pre.7](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.6...v5.0.0-pre.7) (2021-08-09) +# [5.0.0-pre.11](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.10...v5.0.0-pre.11) (2021-10-06) **Note:** Version bump only for package @feathersjs/adapter-commons +# [5.0.0-pre.10](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.9...v5.0.0-pre.10) (2021-09-19) +**Note:** Version bump only for package @feathersjs/adapter-commons +# [5.0.0-pre.9](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.8...v5.0.0-pre.9) (2021-08-09) +**Note:** Version bump only for package @feathersjs/adapter-commons -# [5.0.0-pre.6](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.5...v5.0.0-pre.6) (2021-08-08) +# [5.0.0-pre.8](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.7...v5.0.0-pre.8) (2021-08-09) **Note:** Version bump only for package @feathersjs/adapter-commons +# [5.0.0-pre.7](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.6...v5.0.0-pre.7) (2021-08-09) +**Note:** Version bump only for package @feathersjs/adapter-commons +# [5.0.0-pre.6](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.5...v5.0.0-pre.6) (2021-08-08) +**Note:** Version bump only for package @feathersjs/adapter-commons # [5.0.0-pre.5](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.4...v5.0.0-pre.5) (2021-06-23) - ### Bug Fixes -* Update database adapter common repository urls ([#2380](https://github.com/feathersjs/feathers/issues/2380)) ([3f4db68](https://github.com/feathersjs/feathers/commit/3f4db68d6700c7d9023ecd17d0d39893f75a19fd)) - +- Update database adapter common repository urls ([#2380](https://github.com/feathersjs/feathers/issues/2380)) ([3f4db68](https://github.com/feathersjs/feathers/commit/3f4db68d6700c7d9023ecd17d0d39893f75a19fd)) ### Features -* **adapter-commons:** Add support for params.adapter option and move memory adapter to @feathersjs/memory ([#2367](https://github.com/feathersjs/feathers/issues/2367)) ([a43e7da](https://github.com/feathersjs/feathers/commit/a43e7da22b6b981a96d1321736ea9a0cb924fb4f)) -* **typescript:** Allow to pass generic service options to adapter services ([#2392](https://github.com/feathersjs/feathers/issues/2392)) ([f9431f2](https://github.com/feathersjs/feathers/commit/f9431f242354f804cafb835519f98dd405ac4f0b)) - - - - +- **adapter-commons:** Add support for params.adapter option and move memory adapter to @feathersjs/memory ([#2367](https://github.com/feathersjs/feathers/issues/2367)) ([a43e7da](https://github.com/feathersjs/feathers/commit/a43e7da22b6b981a96d1321736ea9a0cb924fb4f)) +- **typescript:** Allow to pass generic service options to adapter services ([#2392](https://github.com/feathersjs/feathers/issues/2392)) ([f9431f2](https://github.com/feathersjs/feathers/commit/f9431f242354f804cafb835519f98dd405ac4f0b)) # [5.0.0-pre.4](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.3...v5.0.0-pre.4) (2021-05-13) - ### Bug Fixes -* **typescript:** Move Paginated type back for better compatibility ([#2350](https://github.com/feathersjs/feathers/issues/2350)) ([2917d05](https://github.com/feathersjs/feathers/commit/2917d05fffb4716d3c4cdaa5ac6a1aee0972e8a6)) - - - - +- **typescript:** Move Paginated type back for better compatibility ([#2350](https://github.com/feathersjs/feathers/issues/2350)) ([2917d05](https://github.com/feathersjs/feathers/commit/2917d05fffb4716d3c4cdaa5ac6a1aee0972e8a6)) # [5.0.0-pre.3](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.2...v5.0.0-pre.3) (2021-04-21) - ### Bug Fixes -* **typescript:** Improve TypeScript backwards compatibility ([#2310](https://github.com/feathersjs/feathers/issues/2310)) ([f33be73](https://github.com/feathersjs/feathers/commit/f33be73fc46a533efb15df9aab0658e3240d3897)) - - - - +- **typescript:** Improve TypeScript backwards compatibility ([#2310](https://github.com/feathersjs/feathers/issues/2310)) ([f33be73](https://github.com/feathersjs/feathers/commit/f33be73fc46a533efb15df9aab0658e3240d3897)) # [5.0.0-pre.2](https://github.com/feathersjs/feathers/compare/v5.0.0-beta.1...v5.0.0-pre.2) (2021-04-06) **Note:** Version bump only for package @feathersjs/adapter-commons - - - - # [5.0.0-beta.1](https://github.com/feathersjs/feathers/compare/v5.0.0-beta.0...v5.0.0-beta.1) (2021-04-03) - ### Bug Fixes -* **dependencies:** Fix transport-commons dependency and update other dependencies ([#2284](https://github.com/feathersjs/feathers/issues/2284)) ([05b03b2](https://github.com/feathersjs/feathers/commit/05b03b27b40604d956047e3021d8053c3a137616)) - +- **dependencies:** Fix transport-commons dependency and update other dependencies ([#2284](https://github.com/feathersjs/feathers/issues/2284)) ([05b03b2](https://github.com/feathersjs/feathers/commit/05b03b27b40604d956047e3021d8053c3a137616)) ### Features -* **adapter-commons:** Added mongoDB like search in embedded objects ([687e3c7](https://github.com/feathersjs/feathers/commit/687e3c7c36904221b2707d0220c0893e3cb1faa9)) - - - - +- **adapter-commons:** Added mongoDB like search in embedded objects ([687e3c7](https://github.com/feathersjs/feathers/commit/687e3c7c36904221b2707d0220c0893e3cb1faa9)) # [5.0.0-beta.0](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.1...v5.0.0-beta.0) (2021-03-28) - ### Bug Fixes -* **adapter-commons:** Always respect paginate.max ([#2267](https://github.com/feathersjs/feathers/issues/2267)) ([f588257](https://github.com/feathersjs/feathers/commit/f5882575536624ed3a32bb6e3ff1919fa17e366d)) -* Update Grant usage and other dependencies ([#2264](https://github.com/feathersjs/feathers/issues/2264)) ([7b0f8fa](https://github.com/feathersjs/feathers/commit/7b0f8fad252419ed0ad0bf259cdf3104d322ab60)) -* **adapter-commons:** Return missing overloads ([#2203](https://github.com/feathersjs/feathers/issues/2203)) ([bbe7e2a](https://github.com/feathersjs/feathers/commit/bbe7e2a131633e9a6e7aac7f7fa02a312bca63c7)) - +- **adapter-commons:** Always respect paginate.max ([#2267](https://github.com/feathersjs/feathers/issues/2267)) ([f588257](https://github.com/feathersjs/feathers/commit/f5882575536624ed3a32bb6e3ff1919fa17e366d)) +- Update Grant usage and other dependencies ([#2264](https://github.com/feathersjs/feathers/issues/2264)) ([7b0f8fa](https://github.com/feathersjs/feathers/commit/7b0f8fad252419ed0ad0bf259cdf3104d322ab60)) +- **adapter-commons:** Return missing overloads ([#2203](https://github.com/feathersjs/feathers/issues/2203)) ([bbe7e2a](https://github.com/feathersjs/feathers/commit/bbe7e2a131633e9a6e7aac7f7fa02a312bca63c7)) ### Features -* Feathers v5 core refactoring and features ([#2255](https://github.com/feathersjs/feathers/issues/2255)) ([2dafb7c](https://github.com/feathersjs/feathers/commit/2dafb7ce14ba57406aeec13d10ca45b1e709bee9)) - - - - +- Feathers v5 core refactoring and features ([#2255](https://github.com/feathersjs/feathers/issues/2255)) ([2dafb7c](https://github.com/feathersjs/feathers/commit/2dafb7ce14ba57406aeec13d10ca45b1e709bee9)) # [5.0.0-pre.1](https://github.com/feathersjs/feathers/compare/v4.5.11...v5.0.0-pre.1) (2020-12-17) - ### Features -* **memory:** Move feathers-memory into @feathersjs/memory ([#2153](https://github.com/feathersjs/feathers/issues/2153)) ([dd61fe3](https://github.com/feathersjs/feathers/commit/dd61fe371fb0502f78b8ccbe1f45a030e31ecff6)) - - - - +- **memory:** Move feathers-memory into @feathersjs/memory ([#2153](https://github.com/feathersjs/feathers/issues/2153)) ([dd61fe3](https://github.com/feathersjs/feathers/commit/dd61fe371fb0502f78b8ccbe1f45a030e31ecff6)) ## [4.5.11](https://github.com/feathersjs/feathers/compare/v4.5.10...v4.5.11) (2020-12-05) **Note:** Version bump only for package @feathersjs/adapter-commons - - - - ## [4.5.7](https://github.com/feathersjs/feathers/compare/v4.5.6...v4.5.7) (2020-10-21) - ### Bug Fixes -* **typescript:** Remove remaining overloads ([a29fabc](https://github.com/feathersjs/databases/commit/a29fabc9cf6050793a5e93948507ce3e19a235dd)) - - - - +- **typescript:** Remove remaining overloads ([a29fabc](https://github.com/feathersjs/databases/commit/a29fabc9cf6050793a5e93948507ce3e19a235dd)) ## [4.5.6](https://github.com/feathersjs/feathers/compare/v4.5.5...v4.5.6) (2020-10-21) - ### Bug Fixes -* Revert "fix(adapter-commons): Add missing overloads ([#4](https://github.com/feathersjs/databases/issues/4))" ([dfaa850](https://github.com/feathersjs/databases/commit/dfaa8500644021f78d6234a79358f1b26ce2c8d3)) - - - - +- Revert "fix(adapter-commons): Add missing overloads ([#4](https://github.com/feathersjs/databases/issues/4))" ([dfaa850](https://github.com/feathersjs/databases/commit/dfaa8500644021f78d6234a79358f1b26ce2c8d3)) ## [4.5.5](https://github.com/feathersjs/feathers/compare/v4.5.4...v4.5.5) (2020-10-21) - ### Bug Fixes -* **typescript:** Revert "fix: add overloads for `find` ([#9](https://github.com/feathersjs/databases/issues/9))" ([85c20b2](https://github.com/feathersjs/databases/commit/85c20b267e67192169ded97dd5056f116a5ad7b5)) - - - - +- **typescript:** Revert "fix: add overloads for `find` ([#9](https://github.com/feathersjs/databases/issues/9))" ([85c20b2](https://github.com/feathersjs/databases/commit/85c20b267e67192169ded97dd5056f116a5ad7b5)) ## [4.5.4](https://github.com/feathersjs/feathers/compare/v4.5.3...v4.5.4) (2020-09-27) **Note:** Version bump only for package @feathersjs/adapter-commons - - - - ## 4.5.3 (2020-09-24) - ### Bug Fixes -* add overloads for `find` ([#9](https://github.com/feathersjs/databases/issues/9)) ([87c7c29](https://github.com/feathersjs/databases/commit/87c7c29ef017b3cae135e7b7597a7e63fb7d0961)) -* **adapter-commons:** Add missing overloads ([#4](https://github.com/feathersjs/databases/issues/4)) ([b6c80ff](https://github.com/feathersjs/databases/commit/b6c80ff39a32c1b023178f06cffbcaa6d08c554d)) -* Improve Service typings for DB Common API ([#1](https://github.com/feathersjs/databases/issues/1)) ([fd3b949](https://github.com/feathersjs/databases/commit/fd3b9496b0a46f8fd9779c2603faeeb92bd1afc1)) - - - - +- add overloads for `find` ([#9](https://github.com/feathersjs/databases/issues/9)) ([87c7c29](https://github.com/feathersjs/databases/commit/87c7c29ef017b3cae135e7b7597a7e63fb7d0961)) +- **adapter-commons:** Add missing overloads ([#4](https://github.com/feathersjs/databases/issues/4)) ([b6c80ff](https://github.com/feathersjs/databases/commit/b6c80ff39a32c1b023178f06cffbcaa6d08c554d)) +- Improve Service typings for DB Common API ([#1](https://github.com/feathersjs/databases/issues/1)) ([fd3b949](https://github.com/feathersjs/databases/commit/fd3b9496b0a46f8fd9779c2603faeeb92bd1afc1)) ## [4.5.2](https://github.com/feathersjs/feathers/compare/v4.5.1...v4.5.2) (2020-03-04) **Note:** Version bump only for package @feathersjs/adapter-commons - - - - ## [4.5.1](https://github.com/feathersjs/feathers/compare/v4.5.0...v4.5.1) (2020-01-24) **Note:** Version bump only for package @feathersjs/adapter-commons - - - - # [4.5.0](https://github.com/feathersjs/feathers/compare/v4.4.3...v4.5.0) (2020-01-18) **Note:** Version bump only for package @feathersjs/adapter-commons - - - - ## [4.4.3](https://github.com/feathersjs/feathers/compare/v4.4.1...v4.4.3) (2019-12-06) - ### Bug Fixes -* **adapter-commons:** Filter arrays in queries ([#1724](https://github.com/feathersjs/feathers/issues/1724)) ([872b669](https://github.com/feathersjs/feathers/commit/872b66906a806ab92ca41b5f6f504ff0af1ce79e)) - - - - +- **adapter-commons:** Filter arrays in queries ([#1724](https://github.com/feathersjs/feathers/issues/1724)) ([872b669](https://github.com/feathersjs/feathers/commit/872b66906a806ab92ca41b5f6f504ff0af1ce79e)) ## [4.4.1](https://github.com/feathersjs/feathers/compare/v4.4.0...v4.4.1) (2019-11-27) **Note:** Version bump only for package @feathersjs/adapter-commons - - - - # [4.4.0](https://github.com/feathersjs/feathers/compare/v4.3.11...v4.4.0) (2019-11-27) **Note:** Version bump only for package @feathersjs/adapter-commons - - - - ## [4.3.11](https://github.com/feathersjs/feathers/compare/v4.3.10...v4.3.11) (2019-11-11) **Note:** Version bump only for package @feathersjs/adapter-commons - - - - ## [4.3.10](https://github.com/feathersjs/feathers/compare/v4.3.9...v4.3.10) (2019-10-26) **Note:** Version bump only for package @feathersjs/adapter-commons - - - - ## [4.3.9](https://github.com/feathersjs/feathers/compare/v4.3.8...v4.3.9) (2019-10-26) **Note:** Version bump only for package @feathersjs/adapter-commons - - - - ## [4.3.8](https://github.com/feathersjs/feathers/compare/v4.3.7...v4.3.8) (2019-10-14) - ### Bug Fixes -* Remove adapter commons type alternatives ([#1620](https://github.com/feathersjs/feathers/issues/1620)) ([c9f3086](https://github.com/feathersjs/feathers/commit/c9f3086344420b57dbce7c4169cf550c97509f0d)) - - - - +- Remove adapter commons type alternatives ([#1620](https://github.com/feathersjs/feathers/issues/1620)) ([c9f3086](https://github.com/feathersjs/feathers/commit/c9f3086344420b57dbce7c4169cf550c97509f0d)) ## [4.3.7](https://github.com/feathersjs/feathers/compare/v4.3.6...v4.3.7) (2019-10-14) - ### Bug Fixes -* improve Service and AdapterService types ([#1567](https://github.com/feathersjs/feathers/issues/1567)) ([baad6a2](https://github.com/feathersjs/feathers/commit/baad6a26f0f543b712ccb40359b3933ad3a21392)) - - - - +- improve Service and AdapterService types ([#1567](https://github.com/feathersjs/feathers/issues/1567)) ([baad6a2](https://github.com/feathersjs/feathers/commit/baad6a26f0f543b712ccb40359b3933ad3a21392)) ## [4.3.6](https://github.com/feathersjs/feathers/compare/v4.3.5...v4.3.6) (2019-10-07) - ### Bug Fixes -* Check query for NaN ([#1607](https://github.com/feathersjs/feathers/issues/1607)) ([f1a781f](https://github.com/feathersjs/feathers/commit/f1a781f)) - - - - +- Check query for NaN ([#1607](https://github.com/feathersjs/feathers/issues/1607)) ([f1a781f](https://github.com/feathersjs/feathers/commit/f1a781f)) ## [4.3.4](https://github.com/feathersjs/feathers/compare/v4.3.3...v4.3.4) (2019-10-03) **Note:** Version bump only for package @feathersjs/adapter-commons - - - - ## [4.3.3](https://github.com/feathersjs/feathers/compare/v4.3.2...v4.3.3) (2019-09-21) **Note:** Version bump only for package @feathersjs/adapter-commons - - - - ## [4.3.2](https://github.com/feathersjs/feathers/compare/v4.3.1...v4.3.2) (2019-09-16) **Note:** Version bump only for package @feathersjs/adapter-commons - - - - ## [4.3.1](https://github.com/feathersjs/feathers/compare/v4.3.0...v4.3.1) (2019-09-09) **Note:** Version bump only for package @feathersjs/adapter-commons - - - - # [4.3.0](https://github.com/feathersjs/feathers/compare/v4.3.0-pre.4...v4.3.0) (2019-08-27) **Note:** Version bump only for package @feathersjs/adapter-commons - - - - # [4.3.0-pre.4](https://github.com/feathersjs/feathers/compare/v4.3.0-pre.3...v4.3.0-pre.4) (2019-08-22) **Note:** Version bump only for package @feathersjs/adapter-commons - - - - # [4.3.0-pre.3](https://github.com/feathersjs/feathers/compare/v4.3.0-pre.2...v4.3.0-pre.3) (2019-08-19) - ### Bug Fixes -* Update all dependencies ([7d53a00](https://github.com/feathersjs/feathers/commit/7d53a00)) - - - - +- Update all dependencies ([7d53a00](https://github.com/feathersjs/feathers/commit/7d53a00)) # [4.3.0-pre.2](https://github.com/feathersjs/feathers/compare/v4.3.0-pre.1...v4.3.0-pre.2) (2019-08-02) - ### Bug Fixes -* @feathersjs/adapter-commons: `update` id is non-nullable ([#1468](https://github.com/feathersjs/feathers/issues/1468)) ([43ec802](https://github.com/feathersjs/feathers/commit/43ec802)) - - - - +- @feathersjs/adapter-commons: `update` id is non-nullable ([#1468](https://github.com/feathersjs/feathers/issues/1468)) ([43ec802](https://github.com/feathersjs/feathers/commit/43ec802)) # [4.3.0-pre.1](https://github.com/feathersjs/feathers/compare/v4.0.0-pre.5...v4.3.0-pre.1) (2019-07-11) **Note:** Version bump only for package @feathersjs/adapter-commons - - - - # [4.0.0-pre.5](https://github.com/feathersjs/feathers/compare/v4.0.0-pre.4...v4.0.0-pre.5) (2019-07-10) **Note:** Version bump only for package @feathersjs/adapter-commons - - - - # [4.0.0-pre.4](https://github.com/feathersjs/feathers/compare/v4.0.0-pre.3...v4.0.0-pre.4) (2019-07-05) - ### Bug Fixes -* @feathersjs/adapter-commons: remove data from `remove` arguments ([#1426](https://github.com/feathersjs/feathers/issues/1426)) ([fd54ae9](https://github.com/feathersjs/feathers/commit/fd54ae9)) - +- @feathersjs/adapter-commons: remove data from `remove` arguments ([#1426](https://github.com/feathersjs/feathers/issues/1426)) ([fd54ae9](https://github.com/feathersjs/feathers/commit/fd54ae9)) ### Features -* adapter-commons: add `allowsMulti(method)` to AdapterService ([#1431](https://github.com/feathersjs/feathers/issues/1431)) ([e688851](https://github.com/feathersjs/feathers/commit/e688851)) -* Add hook-less methods and service option types to adapter-commons ([#1433](https://github.com/feathersjs/feathers/issues/1433)) ([857f54a](https://github.com/feathersjs/feathers/commit/857f54a)) - - - - +- adapter-commons: add `allowsMulti(method)` to AdapterService ([#1431](https://github.com/feathersjs/feathers/issues/1431)) ([e688851](https://github.com/feathersjs/feathers/commit/e688851)) +- Add hook-less methods and service option types to adapter-commons ([#1433](https://github.com/feathersjs/feathers/issues/1433)) ([857f54a](https://github.com/feathersjs/feathers/commit/857f54a)) # [4.0.0-pre.3](https://github.com/feathersjs/feathers/compare/v4.0.0-pre.2...v4.0.0-pre.3) (2019-06-01) - ### Bug Fixes -* Update dependencies and fix tests ([#1373](https://github.com/feathersjs/feathers/issues/1373)) ([d743a7f](https://github.com/feathersjs/feathers/commit/d743a7f)) - - - - +- Update dependencies and fix tests ([#1373](https://github.com/feathersjs/feathers/issues/1373)) ([d743a7f](https://github.com/feathersjs/feathers/commit/d743a7f)) # [4.0.0-pre.2](https://github.com/feathersjs/feathers/compare/v4.0.0-pre.1...v4.0.0-pre.2) (2019-05-15) **Note:** Version bump only for package @feathersjs/adapter-commons - - - - # [4.0.0-pre.1](https://github.com/feathersjs/feathers/compare/v4.0.0-pre.0...v4.0.0-pre.1) (2019-05-08) **Note:** Version bump only for package @feathersjs/adapter-commons - - - - # [4.0.0-pre.0](https://github.com/feathersjs/feathers/compare/v3.2.0-pre.1...v4.0.0-pre.0) (2019-04-21) - ### Bug Fixes -* Update all dependencies to latest ([#1206](https://github.com/feathersjs/feathers/issues/1206)) ([e51e0f6](https://github.com/feathersjs/feathers/commit/e51e0f6)) -* **adapter-commons:** Keep Symbols when filtering a query ([#1141](https://github.com/feathersjs/feathers/issues/1141)) ([c9f55d8](https://github.com/feathersjs/feathers/commit/c9f55d8)) -* **chore:** Add .npmignore to adapter-commons ([8e129d8](https://github.com/feathersjs/feathers/commit/8e129d8)) -* Add whitelist and filter support to common adapter service ([#1132](https://github.com/feathersjs/feathers/issues/1132)) ([df1daaa](https://github.com/feathersjs/feathers/commit/df1daaa)) -* Fix AdapterService multi option when set to true ([#1134](https://github.com/feathersjs/feathers/issues/1134)) ([40402fc](https://github.com/feathersjs/feathers/commit/40402fc)) -* Throw error in `filterQuery` when query parameter is unknown ([#1131](https://github.com/feathersjs/feathers/issues/1131)) ([cd1a183](https://github.com/feathersjs/feathers/commit/cd1a183)) -* Update adapter common tests ([#1135](https://github.com/feathersjs/feathers/issues/1135)) ([8166dda](https://github.com/feathersjs/feathers/commit/8166dda)) -* Update adapter common tests to check for falsy ([#1140](https://github.com/feathersjs/feathers/issues/1140)) ([2856722](https://github.com/feathersjs/feathers/commit/2856722)) - +- Update all dependencies to latest ([#1206](https://github.com/feathersjs/feathers/issues/1206)) ([e51e0f6](https://github.com/feathersjs/feathers/commit/e51e0f6)) +- **adapter-commons:** Keep Symbols when filtering a query ([#1141](https://github.com/feathersjs/feathers/issues/1141)) ([c9f55d8](https://github.com/feathersjs/feathers/commit/c9f55d8)) +- **chore:** Add .npmignore to adapter-commons ([8e129d8](https://github.com/feathersjs/feathers/commit/8e129d8)) +- Add whitelist and filter support to common adapter service ([#1132](https://github.com/feathersjs/feathers/issues/1132)) ([df1daaa](https://github.com/feathersjs/feathers/commit/df1daaa)) +- Fix AdapterService multi option when set to true ([#1134](https://github.com/feathersjs/feathers/issues/1134)) ([40402fc](https://github.com/feathersjs/feathers/commit/40402fc)) +- Throw error in `filterQuery` when query parameter is unknown ([#1131](https://github.com/feathersjs/feathers/issues/1131)) ([cd1a183](https://github.com/feathersjs/feathers/commit/cd1a183)) +- Update adapter common tests ([#1135](https://github.com/feathersjs/feathers/issues/1135)) ([8166dda](https://github.com/feathersjs/feathers/commit/8166dda)) +- Update adapter common tests to check for falsy ([#1140](https://github.com/feathersjs/feathers/issues/1140)) ([2856722](https://github.com/feathersjs/feathers/commit/2856722)) ### chore -* **package:** Move adapter tests into their own module ([#1164](https://github.com/feathersjs/feathers/issues/1164)) ([dcc1e6b](https://github.com/feathersjs/feathers/commit/dcc1e6b)) - +- **package:** Move adapter tests into their own module ([#1164](https://github.com/feathersjs/feathers/issues/1164)) ([dcc1e6b](https://github.com/feathersjs/feathers/commit/dcc1e6b)) ### Features -* Add TypeScript definitions ([#1275](https://github.com/feathersjs/feathers/issues/1275)) ([9dd6713](https://github.com/feathersjs/feathers/commit/9dd6713)) -* Authentication v3 core server implementation ([#1205](https://github.com/feathersjs/feathers/issues/1205)) ([1bd7591](https://github.com/feathersjs/feathers/commit/1bd7591)) -* Common database adapter utilities and test suite ([#1130](https://github.com/feathersjs/feathers/issues/1130)) ([17b3dc8](https://github.com/feathersjs/feathers/commit/17b3dc8)) - +- Add TypeScript definitions ([#1275](https://github.com/feathersjs/feathers/issues/1275)) ([9dd6713](https://github.com/feathersjs/feathers/commit/9dd6713)) +- Authentication v3 core server implementation ([#1205](https://github.com/feathersjs/feathers/issues/1205)) ([1bd7591](https://github.com/feathersjs/feathers/commit/1bd7591)) +- Common database adapter utilities and test suite ([#1130](https://github.com/feathersjs/feathers/issues/1130)) ([17b3dc8](https://github.com/feathersjs/feathers/commit/17b3dc8)) ### BREAKING CHANGES -* **package:** Removes adapter tests from @feathersjs/adapter-commons -* Move database adapter utilities from @feathersjs/commons into its own module - - - - +- **package:** Removes adapter tests from @feathersjs/adapter-commons +- Move database adapter utilities from @feathersjs/commons into its own module # [2.0.0](https://github.com/feathersjs/feathers/compare/@feathersjs/adapter-commons@1.0.7...@feathersjs/adapter-commons@2.0.0) (2019-01-10) - ### chore -* **package:** Move adapter tests into their own module ([#1164](https://github.com/feathersjs/feathers/issues/1164)) ([dcc1e6b](https://github.com/feathersjs/feathers/commit/dcc1e6b)) - +- **package:** Move adapter tests into their own module ([#1164](https://github.com/feathersjs/feathers/issues/1164)) ([dcc1e6b](https://github.com/feathersjs/feathers/commit/dcc1e6b)) ### BREAKING CHANGES -* **package:** Removes adapter tests from @feathersjs/adapter-commons - - - - +- **package:** Removes adapter tests from @feathersjs/adapter-commons ## [1.0.7](https://github.com/feathersjs/feathers/compare/@feathersjs/adapter-commons@1.0.6...@feathersjs/adapter-commons@1.0.7) (2019-01-02) - ### Bug Fixes -* **chore:** Add .npmignore to adapter-commons ([8e129d8](https://github.com/feathersjs/feathers/commit/8e129d8)) - - - - +- **chore:** Add .npmignore to adapter-commons ([8e129d8](https://github.com/feathersjs/feathers/commit/8e129d8)) ## [1.0.6](https://github.com/feathersjs/feathers/compare/@feathersjs/adapter-commons@1.0.5...@feathersjs/adapter-commons@1.0.6) (2018-12-21) - ### Bug Fixes -* **adapter-commons:** Keep Symbols when filtering a query ([#1141](https://github.com/feathersjs/feathers/issues/1141)) ([c9f55d8](https://github.com/feathersjs/feathers/commit/c9f55d8)) - - - - +- **adapter-commons:** Keep Symbols when filtering a query ([#1141](https://github.com/feathersjs/feathers/issues/1141)) ([c9f55d8](https://github.com/feathersjs/feathers/commit/c9f55d8)) ## [1.0.5](https://github.com/feathersjs/feathers/compare/@feathersjs/adapter-commons@1.0.4...@feathersjs/adapter-commons@1.0.5) (2018-12-20) - ### Bug Fixes -* Update adapter common tests to check for falsy ([#1140](https://github.com/feathersjs/feathers/issues/1140)) ([2856722](https://github.com/feathersjs/feathers/commit/2856722)) - - - - +- Update adapter common tests to check for falsy ([#1140](https://github.com/feathersjs/feathers/issues/1140)) ([2856722](https://github.com/feathersjs/feathers/commit/2856722)) ## [1.0.4](https://github.com/feathersjs/feathers/compare/@feathersjs/adapter-commons@1.0.3...@feathersjs/adapter-commons@1.0.4) (2018-12-17) - ### Bug Fixes -* Update adapter common tests ([#1135](https://github.com/feathersjs/feathers/issues/1135)) ([8166dda](https://github.com/feathersjs/feathers/commit/8166dda)) - - - - +- Update adapter common tests ([#1135](https://github.com/feathersjs/feathers/issues/1135)) ([8166dda](https://github.com/feathersjs/feathers/commit/8166dda)) -## [1.0.3](https://github.com/feathersjs/feathers/compare/@feathersjs/adapter-commons@1.0.2...@feathersjs/adapter-commons@1.0.3) (2018-12-17) +## [1.0.3](https://github.com/feathersjs/feathers/compare/@feathersjs/adapter-commons@1.0.2...@feathersjs/adapter-commons@1.0.3) (2018-12-17) ### Bug Fixes -* Fix AdapterService multi option when set to true ([#1134](https://github.com/feathersjs/feathers/issues/1134)) ([40402fc](https://github.com/feathersjs/feathers/commit/40402fc)) - - - - +- Fix AdapterService multi option when set to true ([#1134](https://github.com/feathersjs/feathers/issues/1134)) ([40402fc](https://github.com/feathersjs/feathers/commit/40402fc)) -## [1.0.2](https://github.com/feathersjs/feathers/compare/@feathersjs/adapter-commons@1.0.1...@feathersjs/adapter-commons@1.0.2) (2018-12-17) +## [1.0.2](https://github.com/feathersjs/feathers/compare/@feathersjs/adapter-commons@1.0.1...@feathersjs/adapter-commons@1.0.2) (2018-12-17) ### Bug Fixes -* Add whitelist and filter support to common adapter service ([#1132](https://github.com/feathersjs/feathers/issues/1132)) ([df1daaa](https://github.com/feathersjs/feathers/commit/df1daaa)) - - - - +- Add whitelist and filter support to common adapter service ([#1132](https://github.com/feathersjs/feathers/issues/1132)) ([df1daaa](https://github.com/feathersjs/feathers/commit/df1daaa)) -## [1.0.1](https://github.com/feathersjs/feathers/compare/@feathersjs/adapter-commons@1.0.0...@feathersjs/adapter-commons@1.0.1) (2018-12-17) +## [1.0.1](https://github.com/feathersjs/feathers/compare/@feathersjs/adapter-commons@1.0.0...@feathersjs/adapter-commons@1.0.1) (2018-12-17) ### Bug Fixes -* Throw error in `filterQuery` when query parameter is unknown ([#1131](https://github.com/feathersjs/feathers/issues/1131)) ([cd1a183](https://github.com/feathersjs/feathers/commit/cd1a183)) - - - - +- Throw error in `filterQuery` when query parameter is unknown ([#1131](https://github.com/feathersjs/feathers/issues/1131)) ([cd1a183](https://github.com/feathersjs/feathers/commit/cd1a183)) -# 1.0.0 (2018-12-16) +# 1.0.0 (2018-12-16) ### Features -* Common database adapter utilities and test suite ([#1130](https://github.com/feathersjs/feathers/issues/1130)) ([17b3dc8](https://github.com/feathersjs/feathers/commit/17b3dc8)) - +- Common database adapter utilities and test suite ([#1130](https://github.com/feathersjs/feathers/issues/1130)) ([17b3dc8](https://github.com/feathersjs/feathers/commit/17b3dc8)) ### BREAKING CHANGES -* Move database adapter utilities from @feathersjs/commons into its own module +- Move database adapter utilities from @feathersjs/commons into its own module diff --git a/packages/adapter-commons/LICENSE b/packages/adapter-commons/LICENSE index 3f395cc665..59604f46f3 100644 --- a/packages/adapter-commons/LICENSE +++ b/packages/adapter-commons/LICENSE @@ -1,6 +1,6 @@ The MIT License (MIT) -Copyright (c) 2021 Feathers +Copyright (c) 2022 Feathers Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated documentation files (the "Software"), to deal diff --git a/packages/adapter-commons/README.md b/packages/adapter-commons/README.md index d4f31e7f63..23e75566a1 100644 --- a/packages/adapter-commons/README.md +++ b/packages/adapter-commons/README.md @@ -1,8 +1,8 @@ # Feathers Adapter Commons [![CI](https://github.com/feathersjs/feathers/workflows/Node.js%20CI/badge.svg)](https://github.com/feathersjs/feathers/actions?query=workflow%3A%22Node.js+CI%22) -[![Dependency Status](https://img.shields.io/david/feathersjs/feathers.svg?style=flat-square&path=packages/adapter-commons)](https://david-dm.org/feathersjs/feathers?path=packages/adapter-commons) [![Download Status](https://img.shields.io/npm/dm/@feathersjs/adapter-commons.svg?style=flat-square)](https://www.npmjs.com/package/@feathersjs/adapter-commons) +[![Discord](https://badgen.net/badge/icon/discord?icon=discord&label)](https://discord.gg/qa8kez8QBx) > Shared utility functions for Feathers adatabase adapters @@ -17,6 +17,6 @@ This is a repository for handling Feathers common database syntax. See the [API ## License -Copyright (c) 2021 [Feathers contributors](https://github.com/feathersjs/feathers/graphs/contributors) +Copyright (c) 2022 [Feathers contributors](https://github.com/feathersjs/feathers/graphs/contributors) Licensed under the [MIT license](LICENSE). diff --git a/packages/adapter-commons/package.json b/packages/adapter-commons/package.json index a00898b099..c9afa36f3b 100644 --- a/packages/adapter-commons/package.json +++ b/packages/adapter-commons/package.json @@ -1,6 +1,6 @@ { "name": "@feathersjs/adapter-commons", - "version": "5.0.0-pre.16", + "version": "5.0.0-pre.31", "description": "Shared database adapter utility functions", "homepage": "https://feathersjs.com", "keywords": [ @@ -13,7 +13,8 @@ }, "repository": { "type": "git", - "url": "git://github.com/feathersjs/feathers.git" + "url": "git://github.com/feathersjs/feathers.git", + "directory": "packages/adapter-commons" }, "author": { "name": "Feathers contributor", @@ -31,7 +32,8 @@ "types": "lib/", "scripts": { "prepublish": "npm run compile", - "compile": "shx rm -rf lib/ && tsc", + "pack": "npm pack --pack-destination ../cli/test/build", + "compile": "shx rm -rf lib/ && tsc && npm run pack", "test": "mocha --config ../../.mocharc.json --recursive test/**.test.ts test/**/*.test.ts" }, "directories": { @@ -48,19 +50,19 @@ "access": "public" }, "dependencies": { - "@feathersjs/commons": "^5.0.0-pre.16", - "@feathersjs/errors": "^5.0.0-pre.16", - "@feathersjs/feathers": "^5.0.0-pre.16" + "@feathersjs/commons": "^5.0.0-pre.31", + "@feathersjs/errors": "^5.0.0-pre.31", + "@feathersjs/feathers": "^5.0.0-pre.31" }, "devDependencies": { - "@types/mocha": "^9.0.0", + "@types/mocha": "^10.0.0", "@types/mongodb": "^4.0.6", - "@types/node": "^17.0.5", - "mocha": "^9.1.3", - "mongodb": "^4.2.2", - "shx": "^0.3.3", - "ts-node": "^10.4.0", - "typescript": "^4.5.4" + "@types/node": "^18.8.2", + "mocha": "^10.0.0", + "mongodb": "^4.10.0", + "shx": "^0.3.4", + "ts-node": "^10.9.1", + "typescript": "^4.8.4" }, - "gitHead": "f0cd227a82d159b528193bd33747c97684a48773" + "gitHead": "4500dbeb8cea566678cf88b3313a88efd93a2ed9" } diff --git a/packages/adapter-commons/src/declarations.ts b/packages/adapter-commons/src/declarations.ts new file mode 100644 index 0000000000..351fbe2226 --- /dev/null +++ b/packages/adapter-commons/src/declarations.ts @@ -0,0 +1,156 @@ +import { Query, Params, Paginated, Id, NullableId } from '@feathersjs/feathers' + +export type FilterQueryOptions = { + filters?: FilterSettings + operators?: string[] + paginate?: PaginationParams +} + +export type QueryFilter = (value: any, options: FilterQueryOptions) => any + +export type FilterSettings = { + [key: string]: QueryFilter | true +} + +export interface PaginationOptions { + default?: number + max?: number +} + +export type PaginationParams = false | PaginationOptions + +export interface AdapterServiceOptions { + /** + * Whether to allow multiple updates for everything (`true`) or specific methods (e.g. `['create', 'remove']`) + */ + multi?: boolean | string[] + /** + * The name of the id property + */ + id?: string + /** + * Pagination settings for this service + */ + paginate?: PaginationParams + /** + * A list of additional property query operators to allow in a query + */ + operators?: string[] + /** + * An object of additional top level query filters, e.g. `{ $populate: true }` + * Can also be a converter function like `{ $ignoreCase: (value) => value === 'true' ? true : false }` + */ + filters?: FilterSettings + /** + * @deprecated Use service `events` option when registering the service with `app.use`. + */ + events?: string[] + /** + * @deprecated renamed to `operators`. + */ + whitelist?: string[] +} + +export interface AdapterQuery extends Query { + $limit?: number + $skip?: number + $select?: string[] + $sort?: { [key: string]: 1 | -1 } +} +/** + * Additional `params` that can be passed to an adapter service method call. + */ +export interface AdapterParams< + Q = AdapterQuery, + A extends Partial = Partial +> extends Params { + adapter?: A + paginate?: PaginationParams +} + +/** + * Hook-less (internal) service methods. Directly call database adapter service methods + * without running any service-level hooks or sanitization. This can be useful if you need the raw data + * from the service and don't want to trigger any of its hooks. + * + * Important: These methods are only available internally on the server, not on the client + * side and only for the Feathers database adapters. + * + * These methods do not trigger events. + * + * @see {@link https://docs.feathersjs.com/guides/migrating.html#hook-less-service-methods} + */ +export interface InternalServiceMethods, P extends AdapterParams = AdapterParams> { + /** + * Retrieve all resources from this service. + * Does not sanitize the query and should only be used on the server. + * + * @param _params - Service call parameters {@link Params} + */ + $find(_params?: P & { paginate?: PaginationOptions }): Promise> + $find(_params?: P & { paginate: false }): Promise + $find(params?: P): Promise> + + /** + * Retrieve a single resource matching the given ID, skipping any service-level hooks. + * Does not sanitize the query and should only be used on the server. + * + * @param id - ID of the resource to locate + * @param params - Service call parameters {@link Params} + * @see {@link HookLessServiceMethods} + * @see {@link https://docs.feathersjs.com/api/services.html#get-id-params|Feathers API Documentation: .get(id, params)} + */ + $get(id: Id, params?: P): Promise + + /** + * Create a new resource for this service, skipping any service-level hooks. + * Does not sanitize data or checks if multiple updates are allowed and should only be used on the server. + * + * @param data - Data to insert into this service. + * @param params - Service call parameters {@link Params} + * @see {@link HookLessServiceMethods} + * @see {@link https://docs.feathersjs.com/api/services.html#create-data-params|Feathers API Documentation: .create(data, params)} + */ + $create(data: Partial, params?: P): Promise + $create(data: Partial[], params?: P): Promise + $create(data: Partial | Partial[], params?: P): Promise + + /** + * Completely replace the resource identified by id, skipping any service-level hooks. + * Does not sanitize data or query and should only be used on the server. + * + * @param id - ID of the resource to be updated + * @param data - Data to be put in place of the current resource. + * @param params - Service call parameters {@link Params} + * @see {@link HookLessServiceMethods} + * @see {@link https://docs.feathersjs.com/api/services.html#update-id-data-params|Feathers API Documentation: .update(id, data, params)} + */ + $update(id: Id, data: D, params?: P): Promise + + /** + * Merge any resources matching the given ID with the given data, skipping any service-level hooks. + * Does not sanitize the data or query and should only be used on the server. + * + * @param id - ID of the resource to be patched + * @param data - Data to merge with the current resource. + * @param params - Service call parameters {@link Params} + * @see {@link HookLessServiceMethods} + * @see {@link https://docs.feathersjs.com/api/services.html#patch-id-data-params|Feathers API Documentation: .patch(id, data, params)} + */ + $patch(id: null, data: Partial, params?: P): Promise + $patch(id: Id, data: Partial, params?: P): Promise + $patch(id: NullableId, data: Partial, params?: P): Promise + + /** + * Remove resources matching the given ID from the this service, skipping any service-level hooks. + * Does not sanitize query and should only be used on the server. + * + * @param id - ID of the resource to be removed + * @param params - Service call parameters {@link Params} + * @see {@link HookLessServiceMethods} + * @see {@link https://docs.feathersjs.com/api/services.html#remove-id-params|Feathers API Documentation: .remove(id, params)} + */ + $remove(id: null, params?: P): Promise + $remove(id: Id, params?: P): Promise + $remove(id: NullableId, params?: P): Promise +} diff --git a/packages/adapter-commons/src/filter-query.ts b/packages/adapter-commons/src/filter-query.ts deleted file mode 100644 index 415ac54cbc..0000000000 --- a/packages/adapter-commons/src/filter-query.ts +++ /dev/null @@ -1,116 +0,0 @@ -import { _ } from '@feathersjs/commons'; -import { BadRequest } from '@feathersjs/errors'; - -function parse (number: any) { - if (typeof number !== 'undefined') { - return Math.abs(parseInt(number, 10)); - } - - return undefined; -} - -// Returns the pagination limit and will take into account the -// default and max pagination settings -function getLimit (limit: any, paginate: any) { - if (paginate && (paginate.default || paginate.max)) { - const base = paginate.default || 0; - const lower = typeof limit === 'number' && !isNaN(limit) ? limit : base; - const upper = typeof paginate.max === 'number' ? paginate.max : Number.MAX_VALUE; - - return Math.min(lower, upper); - } - - return limit; -} - -// Makes sure that $sort order is always converted to an actual number -function convertSort (sort: any) { - if (typeof sort !== 'object' || Array.isArray(sort)) { - return sort; - } - - return Object.keys(sort).reduce((result, key) => { - result[key] = typeof sort[key] === 'object' - ? sort[key] : parseInt(sort[key], 10); - - return result; - }, {} as { [key: string]: number }); -} - -function cleanQuery (query: any, operators: any, filters: any): any { - if (Array.isArray(query)) { - return query.map(value => cleanQuery(value, operators, filters)); - } else if (_.isObject(query) && query.constructor === {}.constructor) { - const result: { [key: string]: any } = {}; - - _.each(query, (value, key) => { - if (key[0] === '$') { - if (filters[key] !== undefined) { - return; - } - - if (!operators.includes(key)) { - throw new BadRequest(`Invalid query parameter ${key}`, query); - } - } - - result[key] = cleanQuery(value, operators, filters); - }); - - Object.getOwnPropertySymbols(query).forEach(symbol => { - // @ts-ignore - result[symbol] = query[symbol]; - }); - - return result; - } - - return query; -} - -function assignFilters (object: any, query: any, filters: any, options: any) { - if (Array.isArray(filters)) { - _.each(filters, (key) => { - if (query[key] !== undefined) { - object[key] = query[key]; - } - }); - } else { - _.each(filters, (converter, key) => { - const converted = converter(query[key], options); - - if (converted !== undefined) { - object[key] = converted; - } - }); - } - - return object; -} - -export const FILTERS = { - $sort: (value: any) => convertSort(value), - $limit: (value: any, options: any) => getLimit(parse(value), options.paginate), - $skip: (value: any) => parse(value), - $select: (value: any) => value -}; - -export const OPERATORS = ['$in', '$nin', '$lt', '$lte', '$gt', '$gte', '$ne', '$or']; - -// Converts Feathers special query parameters and pagination settings -// and returns them separately a `filters` and the rest of the query -// as `query` -export function filterQuery (query: any, options: any = {}) { - const { - filters: additionalFilters = {}, - operators: additionalOperators = [] - } = options; - const result: { [key: string]: any } = {}; - - result.filters = assignFilters({}, query, FILTERS, options); - result.filters = assignFilters(result.filters, query, additionalFilters, options); - - result.query = cleanQuery(query, OPERATORS.concat(additionalOperators), result.filters); - - return result; -} diff --git a/packages/adapter-commons/src/index.ts b/packages/adapter-commons/src/index.ts index aa83aca48f..c7d585a296 100644 --- a/packages/adapter-commons/src/index.ts +++ b/packages/adapter-commons/src/index.ts @@ -1,27 +1,29 @@ -import { _ } from '@feathersjs/commons'; +import { _ } from '@feathersjs/commons' +import { Params } from '@feathersjs/feathers' -export { AdapterService, InternalServiceMethods, ServiceOptions, AdapterParams } from './service'; -export { filterQuery, FILTERS, OPERATORS } from './filter-query'; -export * from './sort'; +export * from './declarations' +export * from './service' +export { filterQuery, FILTERS, OPERATORS } from './query' +export * from './sort' // Return a function that filters a result object or array // and picks only the fields passed as `params.query.$select` // and additional `otherFields` -export function select (params: any, ...otherFields: string[]) { - const queryFields: string[] | undefined = params?.query?.$select; +export function select(params: Params, ...otherFields: string[]) { + const queryFields: string[] | undefined = params?.query?.$select if (!queryFields) { - return (result: any) => result; + return (result: any) => result } - const resultFields = queryFields.concat(otherFields); - const convert = (result: any) => _.pick(result, ...resultFields); + const resultFields = queryFields.concat(otherFields) + const convert = (result: any) => _.pick(result, ...resultFields) return (result: any) => { if (Array.isArray(result)) { - return result.map(convert); + return result.map(convert) } - return convert(result); - }; + return convert(result) + } } diff --git a/packages/adapter-commons/src/query.ts b/packages/adapter-commons/src/query.ts new file mode 100644 index 0000000000..f2001e15bb --- /dev/null +++ b/packages/adapter-commons/src/query.ts @@ -0,0 +1,137 @@ +import { _ } from '@feathersjs/commons' +import { BadRequest } from '@feathersjs/errors' +import { Query } from '@feathersjs/feathers' +import { FilterQueryOptions, FilterSettings } from './declarations' + +const parse = (value: any) => (typeof value !== 'undefined' ? parseInt(value, 10) : value) + +const isPlainObject = (value: any) => _.isObject(value) && value.constructor === {}.constructor + +const validateQueryProperty = (query: any, operators: string[] = []): Query => { + if (!isPlainObject(query)) { + return query + } + + for (const key of Object.keys(query)) { + if (key.startsWith('$') && !operators.includes(key)) { + throw new BadRequest(`Invalid query parameter ${key}`, query) + } + + const value = query[key] + + if (isPlainObject(value)) { + query[key] = validateQueryProperty(value, operators) + } + } + + return { + ...query + } +} + +const getFilters = (query: Query, settings: FilterQueryOptions) => { + const filterNames = Object.keys(settings.filters) + + return filterNames.reduce((current, key) => { + const queryValue = query[key] + const filter = settings.filters[key] + + if (filter) { + const value = typeof filter === 'function' ? filter(queryValue, settings) : queryValue + + if (value !== undefined) { + current[key] = value + } + } + + return current + }, {} as { [key: string]: any }) +} + +const getQuery = (query: Query, settings: FilterQueryOptions) => { + const keys = Object.keys(query).concat(Object.getOwnPropertySymbols(query) as any as string[]) + + return keys.reduce((result, key) => { + if (typeof key === 'string' && key.startsWith('$')) { + if (settings.filters[key] === undefined) { + throw new BadRequest(`Invalid filter value ${key}`) + } + } else { + result[key] = validateQueryProperty(query[key], settings.operators) + } + + return result + }, {} as Query) +} + +export const OPERATORS = ['$in', '$nin', '$lt', '$lte', '$gt', '$gte', '$ne', '$or'] + +export const FILTERS: FilterSettings = { + $skip: (value: any) => parse(value), + $sort: (sort: any): { [key: string]: number } => { + if (typeof sort !== 'object' || Array.isArray(sort)) { + return sort + } + + return Object.keys(sort).reduce((result, key) => { + result[key] = typeof sort[key] === 'object' ? sort[key] : parse(sort[key]) + + return result + }, {} as { [key: string]: number }) + }, + $limit: (_limit: any, { paginate }: FilterQueryOptions) => { + const limit = parse(_limit) + + if (paginate && (paginate.default || paginate.max)) { + const base = paginate.default || 0 + const lower = typeof limit === 'number' && !isNaN(limit) && limit >= 0 ? limit : base + const upper = typeof paginate.max === 'number' ? paginate.max : Number.MAX_VALUE + + return Math.min(lower, upper) + } + + return limit + }, + $select: (select: any) => { + if (Array.isArray(select)) { + return select.map((current) => `${current}`) + } + + return select + }, + $or: (or: any, { operators }: FilterQueryOptions) => { + if (Array.isArray(or)) { + return or.map((current) => validateQueryProperty(current, operators)) + } + + return or + } +} + +/** + * Converts Feathers special query parameters and pagination settings + * and returns them separately as `filters` and the rest of the query + * as `query`. `options` also gets passed the pagination settings and + * a list of additional `operators` to allow when querying properties. + * + * @param query The initial query + * @param options Options for filtering the query + * @returns An object with `query` which contains the query without `filters` + * and `filters` which contains the converted values for each filter. + */ +export function filterQuery(_query: Query, options: FilterQueryOptions = {}) { + const query = _query || {} + const settings = { + ...options, + filters: { + ...FILTERS, + ...options.filters + }, + operators: OPERATORS.concat(options.operators || []) + } + + return { + filters: getFilters(query, settings), + query: getQuery(query, settings) + } +} diff --git a/packages/adapter-commons/src/service.ts b/packages/adapter-commons/src/service.ts index 0d407f4357..fb5070fbaa 100644 --- a/packages/adapter-commons/src/service.ts +++ b/packages/adapter-commons/src/service.ts @@ -1,87 +1,194 @@ -import { NotImplemented, BadRequest, MethodNotAllowed } from '@feathersjs/errors'; -import { ServiceMethods, Params, Id, NullableId, Paginated } from '@feathersjs/feathers'; -import { filterQuery } from './filter-query'; - -const callMethod = (self: any, name: any, ...args: any[]) => { - if (typeof self[name] !== 'function') { - return Promise.reject(new NotImplemented(`Method ${name} not available`)); - } - - return self[name](...args); -}; +import { BadRequest, MethodNotAllowed } from '@feathersjs/errors' +import { Id, NullableId, Paginated, Query } from '@feathersjs/feathers' +import { + AdapterParams, + AdapterServiceOptions, + InternalServiceMethods, + PaginationOptions +} from './declarations' +import { filterQuery } from './query' const alwaysMulti: { [key: string]: boolean } = { find: true, get: false, update: false -}; - -export interface ServiceOptions { - events?: string[]; - multi?: boolean|string[]; - id?: string; - paginate?: { - default?: number; - max?: number; +} + +/** + * An abstract base class that a database adapter can extend from to implement the + * `__find`, `__get`, `__update`, `__patch` and `__remove` methods. + */ +export abstract class AdapterBase< + T = any, + D = Partial, + P extends AdapterParams = AdapterParams, + O extends AdapterServiceOptions = AdapterServiceOptions +> implements InternalServiceMethods +{ + options: O + + constructor(options: O) { + this.options = { + id: 'id', + events: [], + paginate: false, + multi: false, + filters: {}, + operators: [], + ...options + } + } + + get id() { + return this.options.id + } + + get events() { + return this.options.events } + /** - * @deprecated renamed to `allow`. + * Check if this adapter allows multiple updates for a method. + * @param method The method name to check. + * @param params The service call params. + * @returns Wether or not multiple updates are allowed. */ - whitelist?: string[]; - allow?: string[]; - filters?: string[]; -} + allowsMulti(method: string, params: P = {} as P) { + const always = alwaysMulti[method] -export interface AdapterOptions extends Pick { - Model?: M; -} + if (typeof always !== 'undefined') { + return always + } -export interface AdapterParams extends Params { - adapter?: Partial>; -} + const { multi } = this.getOptions(params) -/** - * Hook-less (internal) service methods. Directly call database adapter service methods - * without running any service-level hooks. This can be useful if you need the raw data - * from the service and don't want to trigger any of its hooks. - * - * Important: These methods are only available internally on the server, not on the client - * side and only for the Feathers database adapters. - * - * These methods do not trigger events. - * - * @see {@link https://docs.feathersjs.com/guides/migrating.html#hook-less-service-methods} - */ -export interface InternalServiceMethods> { + if (multi === true || multi === false) { + return multi + } + + return multi.includes(method) + } + + /** + * Returns the combined options for a service call. Options will be merged + * with `this.options` and `params.adapter` for dynamic overrides. + * + * @param params The parameters for the service method call + * @returns The actual options for this call + */ + getOptions(params: P): O { + const paginate = params.paginate !== undefined ? params.paginate : this.options.paginate + + return { + ...this.options, + paginate, + ...params.adapter + } + } + + /** + * Sanitize the incoming data, e.g. removing invalid keywords etc. + * + * @param data The data to sanitize + * @param _params Service call parameters + * @returns The sanitized data + */ + async sanitizeData>(data: X, _params: P) { + return data + } + + /** + * Returns a sanitized version of `params.query`, converting filter values + * (like $limit and $skip) into the expected type. Will throw an error if + * a `$` prefixed filter or operator value that is not allowed in `filters` + * or `operators` is encountered. + * + * @param params The service call parameter. + * @returns A new object containing the sanitized query. + */ + async sanitizeQuery(params: P = {} as P): Promise { + const options = this.getOptions(params) + const { query, filters } = filterQuery(params.query, options) + + return { + ...filters, + ...query + } + } + + abstract $find(_params?: P & { paginate?: PaginationOptions }): Promise> + abstract $find(_params?: P & { paginate: false }): Promise + abstract $find(params?: P): Promise> /** - * Retrieve all resources from this service, skipping any service-level hooks. + * Retrieve all resources from this service, skipping any service-level hooks but sanitize the query + * with allowed filters and properties by calling `sanitizeQuery`. * * @param params - Service call parameters {@link Params} * @see {@link HookLessServiceMethods} * @see {@link https://docs.feathersjs.com/api/services.html#find-params|Feathers API Documentation: .find(params)} */ - _find (params?: AdapterParams): Promise>; + async _find(_params?: P & { paginate?: PaginationOptions }): Promise> + async _find(_params?: P & { paginate: false }): Promise + async _find(params?: P): Promise> + async _find(params?: P): Promise> { + const query = await this.sanitizeQuery(params) + + return this.$find({ + ...params, + query + }) + } + + abstract $get(id: Id, params?: P): Promise /** - * Retrieve a single resource matching the given ID, skipping any service-level hooks. + * Retrieve a single resource matching the given ID, skipping any service-level hooks but sanitize the query + * with allowed filters and properties by calling `sanitizeQuery`. * * @param id - ID of the resource to locate * @param params - Service call parameters {@link Params} * @see {@link HookLessServiceMethods} * @see {@link https://docs.feathersjs.com/api/services.html#get-id-params|Feathers API Documentation: .get(id, params)} */ - _get (id: Id, params?: AdapterParams): Promise; + async _get(id: Id, params?: P): Promise { + const query = await this.sanitizeQuery(params) + + return this.$get(id, { + ...params, + query + }) + } + + abstract $create(data: Partial, params?: P): Promise + abstract $create(data: Partial[], params?: P): Promise + abstract $create(data: Partial | Partial[], params?: P): Promise /** - * Create a new resource for this service, skipping any service-level hooks. + * Create a new resource for this service, skipping any service-level hooks, sanitize the data + * and check if multiple updates are allowed. * * @param data - Data to insert into this service. * @param params - Service call parameters {@link Params} * @see {@link HookLessServiceMethods} * @see {@link https://docs.feathersjs.com/api/services.html#create-data-params|Feathers API Documentation: .create(data, params)} */ - _create (data: D | D[], params?: AdapterParams): Promise; + async _create(data: Partial, params?: P): Promise + async _create(data: Partial[], params?: P): Promise + async _create(data: Partial | Partial[], params?: P): Promise + async _create(data: Partial | Partial[], params?: P): Promise { + if (Array.isArray(data) && !this.allowsMulti('create', params)) { + throw new MethodNotAllowed('Can not create multiple entries') + } + + const payload = Array.isArray(data) + ? await Promise.all(data.map((current) => this.sanitizeData(current, params))) + : await this.sanitizeData(data, params) + + return this.$create(payload, params) + } + + abstract $update(id: Id, data: D, params?: P): Promise /** * Replace any resources matching the given ID with the given data, skipping any service-level hooks. @@ -92,10 +199,27 @@ export interface InternalServiceMethods> { * @see {@link HookLessServiceMethods} * @see {@link https://docs.feathersjs.com/api/services.html#update-id-data-params|Feathers API Documentation: .update(id, data, params)} */ - _update (id: Id, data: D, params?: AdapterParams): Promise; + async _update(id: Id, data: D, params?: P): Promise { + if (id === null || Array.isArray(data)) { + throw new BadRequest("You can not replace multiple instances. Did you mean 'patch'?") + } + + const payload = await this.sanitizeData(data, params) + const query = await this.sanitizeQuery(params) + + return this.$update(id, payload, { + ...params, + query + }) + } + + abstract $patch(id: null, data: Partial, params?: P): Promise + abstract $patch(id: Id, data: Partial, params?: P): Promise + abstract $patch(id: NullableId, data: Partial, params?: P): Promise /** * Merge any resources matching the given ID with the given data, skipping any service-level hooks. + * Sanitizes the query and data and checks it multiple updates are allowed. * * @param id - ID of the resource to be patched * @param data - Data to merge with the current resource. @@ -103,132 +227,49 @@ export interface InternalServiceMethods> { * @see {@link HookLessServiceMethods} * @see {@link https://docs.feathersjs.com/api/services.html#patch-id-data-params|Feathers API Documentation: .patch(id, data, params)} */ - _patch (id: NullableId, data: D, params?: AdapterParams): Promise; + async _patch(id: null, data: Partial, params?: P): Promise + async _patch(id: Id, data: Partial, params?: P): Promise + async _patch(id: NullableId, data: Partial, params?: P): Promise + async _patch(id: NullableId, data: Partial, params?: P): Promise { + if (id === null && !this.allowsMulti('patch', params)) { + throw new MethodNotAllowed('Can not patch multiple entries') + } + + const { $limit, ...query } = await this.sanitizeQuery(params) + const payload = await this.sanitizeData(data, params) + + return this.$patch(id, payload, { + ...params, + query + }) + } + + abstract $remove(id: null, params?: P): Promise + abstract $remove(id: Id, params?: P): Promise + abstract $remove(id: NullableId, params?: P): Promise /** * Remove resources matching the given ID from the this service, skipping any service-level hooks. + * Sanitized the query and verifies that multiple updates are allowed. * * @param id - ID of the resource to be removed * @param params - Service call parameters {@link Params} * @see {@link HookLessServiceMethods} * @see {@link https://docs.feathersjs.com/api/services.html#remove-id-params|Feathers API Documentation: .remove(id, params)} */ - _remove (id: NullableId, params?: AdapterParams): Promise; -} - -export class AdapterService< - T = any, - D = Partial, - O extends Partial = Partial -> implements ServiceMethods, D> { - options: ServiceOptions & O; - - constructor (options: O) { - this.options = Object.assign({ - id: 'id', - events: [], - paginate: {}, - multi: false, - filters: [], - allow: [] - }, options); - } - - get id () { - return this.options.id; - } - - get events () { - return this.options.events; - } - - filterQuery (params: AdapterParams = {}, opts: any = {}) { - const paginate = typeof params.paginate !== 'undefined' - ? params.paginate - : this.getOptions(params).paginate; - const { query = {} } = params; - const options = Object.assign({ - operators: this.options.whitelist || this.options.allow || [], - filters: this.options.filters, - paginate - }, opts); - const result = filterQuery(query, options); - - return Object.assign(result, { paginate }); - } - - allowsMulti (method: string, params: AdapterParams = {}) { - const always = alwaysMulti[method]; - - if (typeof always !== 'undefined') { - return always; - } - - const { multi: option } = this.getOptions(params); - - if (option === true || option === false) { - return option; - } - - return option.includes(method); - } - - getOptions (params: AdapterParams): ServiceOptions & { model?: any } { - return { - ...this.options, - ...params.adapter - } - } - - find (params?: AdapterParams): Promise> { - return callMethod(this, '_find', params); - } - - get (id: Id, params?: AdapterParams): Promise { - return callMethod(this, '_get', id, params); - } - - create (data: Partial, params?: AdapterParams): Promise; - create (data: Partial[], params?: AdapterParams): Promise; - create (data: Partial | Partial[], params?: AdapterParams): Promise { - if (Array.isArray(data) && !this.allowsMulti('create', params)) { - return Promise.reject(new MethodNotAllowed('Can not create multiple entries')); - } - - return callMethod(this, '_create', data, params); - } - - update (id: Id, data: D, params?: AdapterParams): Promise { - if (id === null || Array.isArray(data)) { - return Promise.reject(new BadRequest( - 'You can not replace multiple instances. Did you mean \'patch\'?' - )); - } - - return callMethod(this, '_update', id, data, params); - } - - patch (id: Id, data: Partial, params?: AdapterParams): Promise; - patch (id: null, data: Partial, params?: AdapterParams): Promise; - patch (id: NullableId, data: Partial, params?: AdapterParams): Promise; - patch (id: NullableId, data: Partial, params?: AdapterParams): Promise { - if (id === null && !this.allowsMulti('patch', params)) { - return Promise.reject(new MethodNotAllowed('Can not patch multiple entries')); - } - - return callMethod(this, '_patch', id, data, params); - } - - remove (id: Id, params?: AdapterParams): Promise; - remove (id: null, params?: AdapterParams): Promise; - remove (id: NullableId, params?: AdapterParams): Promise; - remove (id: NullableId, params?: AdapterParams): Promise { + async _remove(id: null, params?: P): Promise + async _remove(id: Id, params?: P): Promise + async _remove(id: NullableId, params?: P): Promise + async _remove(id: NullableId, params?: P): Promise { if (id === null && !this.allowsMulti('remove', params)) { - return Promise.reject(new MethodNotAllowed('Can not remove multiple entries')); + throw new MethodNotAllowed('Can not remove multiple entries') } - return callMethod(this, '_remove', id, params); - } + const { $limit, ...query } = await this.sanitizeQuery(params) - async setup () {} + return this.$remove(id, { + ...params, + query + }) + } } diff --git a/packages/adapter-commons/src/sort.ts b/packages/adapter-commons/src/sort.ts index fc2e436bda..6e24fb5853 100644 --- a/packages/adapter-commons/src/sort.ts +++ b/packages/adapter-commons/src/sort.ts @@ -1,90 +1,130 @@ // Sorting algorithm taken from NeDB (https://github.com/louischatriot/nedb) // See https://github.com/louischatriot/nedb/blob/e3f0078499aa1005a59d0c2372e425ab789145c1/lib/model.js#L189 -export function compareNSB (a: any, b: any) { - if (a < b) { return -1; } - if (a > b) { return 1; } - return 0; +export function compareNSB(a: any, b: any) { + if (a < b) { + return -1 + } + if (a > b) { + return 1 + } + return 0 } -export function compareArrays (a: any[], b: any[]) { +export function compareArrays(a: any[], b: any[]) { for (let i = 0, l = Math.min(a.length, b.length); i < l; i++) { - const comparison = compare(a[i], b[i]); + const comparison = compare(a[i], b[i]) - if (comparison !== 0) { return comparison; } + if (comparison !== 0) { + return comparison + } } // Common section was identical, longest one wins - return compareNSB(a.length, b.length); + return compareNSB(a.length, b.length) } -export function compare (a: any, b: any, compareStrings: any = compareNSB): 0 | 1 | -1 { - if (a === b) { return 0; } +export function compare(a: any, b: any, compareStrings: any = compareNSB): 0 | 1 | -1 { + if (a === b) { + return 0 + } // undefined - if (a === undefined) { return -1; } - if (b === undefined) { return 1; } + if (a === undefined) { + return -1 + } + if (b === undefined) { + return 1 + } // null - if (a === null) { return -1; } - if (b === null) { return 1; } + if (a === null) { + return -1 + } + if (b === null) { + return 1 + } // Numbers - if (typeof a === 'number') { return typeof b === 'number' ? compareNSB(a, b) : -1; } - if (typeof b === 'number') { return 1; } + if (typeof a === 'number') { + return typeof b === 'number' ? compareNSB(a, b) : -1 + } + if (typeof b === 'number') { + return 1 + } // Strings - if (typeof a === 'string') { return typeof b === 'string' ? compareStrings(a, b) : -1; } - if (typeof b === 'string') { return 1; } + if (typeof a === 'string') { + return typeof b === 'string' ? compareStrings(a, b) : -1 + } + if (typeof b === 'string') { + return 1 + } // Booleans - if (typeof a === 'boolean') { return typeof b === 'boolean' ? compareNSB(a, b) : -1; } - if (typeof b === 'boolean') { return 1; } + if (typeof a === 'boolean') { + return typeof b === 'boolean' ? compareNSB(a, b) : -1 + } + if (typeof b === 'boolean') { + return 1 + } // Dates - if (a instanceof Date) { return b instanceof Date ? compareNSB(a.getTime(), b.getTime()) : -1; } - if (b instanceof Date) { return 1; } + if (a instanceof Date) { + return b instanceof Date ? compareNSB(a.getTime(), b.getTime()) : -1 + } + if (b instanceof Date) { + return 1 + } // Arrays (first element is most significant and so on) - if (Array.isArray(a)) { return Array.isArray(b) ? compareArrays(a, b) : -1; } - if (Array.isArray(b)) { return 1; } + if (Array.isArray(a)) { + return Array.isArray(b) ? compareArrays(a, b) : -1 + } + if (Array.isArray(b)) { + return 1 + } // Objects - const aKeys = Object.keys(a).sort(); - const bKeys = Object.keys(b).sort(); + const aKeys = Object.keys(a).sort() + const bKeys = Object.keys(b).sort() for (let i = 0, l = Math.min(aKeys.length, bKeys.length); i < l; i++) { - const comparison = compare(a[aKeys[i]], b[bKeys[i]]); + const comparison = compare(a[aKeys[i]], b[bKeys[i]]) - if (comparison !== 0) { return comparison; } + if (comparison !== 0) { + return comparison + } } - return compareNSB(aKeys.length, bKeys.length); + return compareNSB(aKeys.length, bKeys.length) } // An in-memory sorting function according to the // $sort special query parameter -export function sorter ($sort: { [key: string]: -1 | 1 }) { - const get = (value: any, path: string[]) => path.reduce((value, key) => value[key], value); +export function sorter($sort: { [key: string]: -1 | 1 }) { + const get = (value: any, path: string[]) => path.reduce((value, key) => value[key], value) - const compares = Object.keys($sort).map(key => { - const direction = $sort[key]; - const path = key.split('.'); + const compares = Object.keys($sort).map((key) => { + const direction = $sort[key] + const path = key.split('.') if (path.length === 1) { - return (a: any, b: any) => direction * compare(a[key], b[key]); + return (a: any, b: any) => direction * compare(a[key], b[key]) } else { - return (a: any, b: any) => direction * compare(get(a, path), get(b, path)); + return (a: any, b: any) => direction * compare(get(a, path), get(b, path)) } - }); + }) return function (a: any, b: any) { for (const compare of compares) { - const comparasion = compare(a, b); + const comparasion = compare(a, b) - if (comparasion !== 0) { return comparasion; } + if (comparasion !== 0) { + return comparasion + } } - return 0; - }; + return 0 + } } diff --git a/packages/adapter-commons/test/commons.test.ts b/packages/adapter-commons/test/commons.test.ts index 8a74671e07..b0f5eb8d23 100644 --- a/packages/adapter-commons/test/commons.test.ts +++ b/packages/adapter-commons/test/commons.test.ts @@ -1,72 +1,91 @@ -import assert from 'assert'; -import { select } from '../src'; +import assert from 'assert' +import { select } from '../src' describe('@feathersjs/adapter-commons', () => { describe('select', () => { it('select', () => { const selector = select({ query: { $select: ['name', 'age'] } - }); + }) return Promise.resolve({ name: 'David', age: 3, test: 'me' - }).then(selector).then(result => assert.deepStrictEqual(result, { - name: 'David', - age: 3 - })); - }); + }) + .then(selector) + .then((result) => + assert.deepStrictEqual(result, { + name: 'David', + age: 3 + }) + ) + }) it('select with arrays', () => { const selector = select({ query: { $select: ['name', 'age'] } - }); + }) - return Promise.resolve([{ - name: 'David', - age: 3, - test: 'me' - }, { - name: 'D', - age: 4, - test: 'you' - }]).then(selector).then(result => assert.deepStrictEqual(result, [{ - name: 'David', - age: 3 - }, { - name: 'D', - age: 4 - }])); - }); + return Promise.resolve([ + { + name: 'David', + age: 3, + test: 'me' + }, + { + name: 'D', + age: 4, + test: 'you' + } + ]) + .then(selector) + .then((result) => + assert.deepStrictEqual(result, [ + { + name: 'David', + age: 3 + }, + { + name: 'D', + age: 4 + } + ]) + ) + }) it('select with no query', () => { - const selector = select({}); + const selector = select({}) const data = { name: 'David' - }; + } - return Promise.resolve(data).then(selector).then(result => - assert.deepStrictEqual(result, data) - ); - }); + return Promise.resolve(data) + .then(selector) + .then((result) => assert.deepStrictEqual(result, data)) + }) it('select with other fields', () => { - const selector = select({ - query: { $select: [ 'name' ] } - }, 'id'); + const selector = select( + { + query: { $select: ['name'] } + }, + 'id' + ) const data = { id: 'me', name: 'David', age: 10 - }; + } return Promise.resolve(data) .then(selector) - .then(result => assert.deepStrictEqual(result, { - id: 'me', - name: 'David' - })); - }); - }); -}); + .then((result) => + assert.deepStrictEqual(result, { + id: 'me', + name: 'David' + }) + ) + }) + }) +}) diff --git a/packages/adapter-commons/test/filter-query.test.ts b/packages/adapter-commons/test/filter-query.test.ts deleted file mode 100644 index 9db9b94790..0000000000 --- a/packages/adapter-commons/test/filter-query.test.ts +++ /dev/null @@ -1,270 +0,0 @@ -import assert from 'assert'; -import { ObjectId } from 'mongodb'; -import { filterQuery } from '../src'; - -describe('@feathersjs/adapter-commons/filterQuery', () => { - describe('$sort', () => { - it('returns $sort when present in query', () => { - const originalQuery = { $sort: { name: 1 } }; - const { filters, query } = filterQuery(originalQuery); - - assert.strictEqual(filters.$sort.name, 1); - assert.deepStrictEqual(query, {}); - assert.deepStrictEqual(originalQuery, { - $sort: { name: 1 } - }, 'does not modify original query'); - }); - - it('returns $sort when present in query as an object', () => { - const { filters, query } = filterQuery({ $sort: { name: { something: 10 } } }); - - assert.strictEqual(filters.$sort.name.something, 10); - assert.deepStrictEqual(query, {}); - }); - - it('converts strings in $sort', () => { - const { filters, query } = filterQuery({ $sort: { test: '-1' } }); - - assert.strictEqual(filters.$sort.test, -1); - assert.deepStrictEqual(query, {}); - }); - - it('does not convert $sort arrays', () => { - const $sort = [ [ 'test', '-1' ], [ 'a', '1' ] ]; - const { filters, query } = filterQuery({ $sort }); - - assert.strictEqual(filters.$sort, $sort); - assert.deepStrictEqual(query, {}); - }); - - it('throws an error when special parameter is not known', () => { - try { - const query = { $foo: 1 }; - filterQuery(query); - assert.ok(false, 'Should never get here'); - } catch (error: any) { - assert.strictEqual(error.name, 'BadRequest'); - assert.strictEqual(error.message, 'Invalid query parameter $foo'); - } - }); - - it('returns undefined when not present in query', () => { - const query = { foo: 1 }; - const { filters } = filterQuery(query); - - assert.strictEqual(filters.$sort, undefined); - }); - }); - - describe('$limit', () => { - let testQuery: any; - - beforeEach(() => { - testQuery = { $limit: 1 }; - }); - - it('returns $limit when present in query', () => { - const { filters, query } = filterQuery(testQuery); - - assert.strictEqual(filters.$limit, 1); - assert.deepStrictEqual(query, {}); - }); - - it('returns undefined when not present in query', () => { - const query = { foo: 1 }; - const { filters } = filterQuery(query); - - assert.strictEqual(filters.$limit, undefined); - }); - - it('removes $limit from query when present', () => { - assert.deepStrictEqual(filterQuery(testQuery).query, {}); - }); - - it('parses $limit strings into integers (#4)', () => { - const { filters } = filterQuery({ $limit: '2' }); - - assert.strictEqual(filters.$limit, 2); - }); - - it('allows $limit 0', () => { - const { filters } = filterQuery({ $limit: 0 }, { default: 10 }); - - assert.strictEqual(filters.$limit, 0); - }); - - describe('pagination', () => { - it('limits with default pagination', () => { - const { filters } = filterQuery({}, { paginate: { default: 10 } }); - - assert.strictEqual(filters.$limit, 10); - }); - - it('limits with max pagination', () => { - const { filters } = filterQuery({ $limit: 20 }, { paginate: { default: 5, max: 10 } }); - const { filters: filtersNeg } = filterQuery({ $limit: -20 }, { paginate: { default: 5, max: 10 } }); - - assert.strictEqual(filters.$limit, 10); - assert.strictEqual(filtersNeg.$limit, 10); - }); - - it('limits with default pagination when not a number', () => { - const { filters } = filterQuery({ $limit: 'something' }, { paginate: { default: 5, max: 10 } }); - - assert.strictEqual(filters.$limit, 5); - }); - - it('limits to 0 when no paginate.default and not a number', () => { - const { filters } = filterQuery({ $limit: 'something' }, { paginate: { max: 10 } }); - - assert.strictEqual(filters.$limit, 0); - }); - - it('still uses paginate.max when there is no paginate.default (#2104)', () => { - const { filters } = filterQuery({ $limit: 100 }, { paginate: { max: 10 } }); - - assert.strictEqual(filters.$limit, 10); - }); - }); - }); - - describe('$skip', () => { - let testQuery: any; - - beforeEach(() => { - testQuery = { $skip: 1 }; - }); - - it('returns $skip when present in query', () => { - const { filters } = filterQuery(testQuery); - - assert.strictEqual(filters.$skip, 1); - }); - - it('removes $skip from query when present', () => { - assert.deepStrictEqual(filterQuery(testQuery).query, {}); - }); - - it('returns undefined when not present in query', () => { - const query = { foo: 1 }; - const { filters } = filterQuery(query); - - assert.strictEqual(filters.$skip, undefined); - }); - - it('parses $skip strings into integers (#4)', () => { - const { filters } = filterQuery({ $skip: '33' }); - - assert.strictEqual(filters.$skip, 33); - }); - }); - - describe('$select', () => { - let testQuery: any; - - beforeEach(() => { - testQuery = { $select: 1 }; - }); - - it('returns $select when present in query', () => { - const { filters } = filterQuery(testQuery); - - assert.strictEqual(filters.$select, 1); - }); - - it('removes $select from query when present', () => { - assert.deepStrictEqual(filterQuery(testQuery).query, {}); - }); - - it('returns undefined when not present in query', () => { - const query = { foo: 1 }; - const { filters } = filterQuery(query); - - assert.strictEqual(filters.$select, undefined); - }); - - it('includes Symbols', () => { - const TEST = Symbol('testing'); - const original = { - [TEST]: 'message', - other: true, - sub: { [TEST]: 'othermessage' } - }; - - const { query } = filterQuery(original); - - assert.deepStrictEqual(query, { - [TEST]: 'message', - other: true, - sub: { [TEST]: 'othermessage' } - }); - }); - - it('only converts plain objects', () => { - const userId = new ObjectId(); - const original = { - userId - }; - - const { query } = filterQuery(original); - - assert.deepStrictEqual(query, original); - }); - }); - - describe('arrays', () => { - it('validates queries in arrays', () => { - assert.throws(() => { - filterQuery({ - $or: [{ $exists: false }] - }); - }, { - name: 'BadRequest', - message: 'Invalid query parameter $exists' - }); - }); - }); - - describe('additional filters', () => { - it('throw error when not set as additionals', () => { - try { - filterQuery({ $select: 1, $known: 1 }); - assert.ok(false, 'Should never get here'); - } catch (error: any) { - assert.strictEqual(error.message, 'Invalid query parameter $known'); - } - }); - - it('returns default and known additional filters (array)', () => { - const query = { $select: ['a', 'b'], $known: 1, $unknown: 1 }; - const { filters } = filterQuery(query, { filters: [ '$known', '$unknown' ] }); - - assert.strictEqual(filters.$unknown, 1); - assert.strictEqual(filters.$known, 1); - assert.deepStrictEqual(filters.$select, [ 'a', 'b' ]); - }); - - it('returns default and known additional filters (object)', () => { - const { filters } = filterQuery({ - $known: 1, - $select: 1 - }, { filters: { $known: (value: any) => value.toString() } }); - - assert.strictEqual(filters.$unknown, undefined); - assert.strictEqual(filters.$known, '1'); - assert.strictEqual(filters.$select, 1); - }); - }); - - describe('additional operators', () => { - it('returns query with default and known additional operators', () => { - const { query } = filterQuery({ - $ne: 1, $known: 1 - }, { operators: [ '$known' ] }); - - assert.strictEqual(query.$ne, 1); - assert.strictEqual(query.$known, 1); - assert.strictEqual(query.$unknown, undefined); - }); - }); -}); diff --git a/packages/adapter-commons/test/fixture.ts b/packages/adapter-commons/test/fixture.ts new file mode 100644 index 0000000000..675b831ee2 --- /dev/null +++ b/packages/adapter-commons/test/fixture.ts @@ -0,0 +1,98 @@ +import { AdapterBase, AdapterParams, InternalServiceMethods, PaginationOptions } from '../src' +import { Id, NullableId, Paginated } from '@feathersjs/feathers' + +export type Data = { + id: Id +} + +export class MethodBase + extends AdapterBase, AdapterParams> + implements InternalServiceMethods +{ + async $find(_params?: AdapterParams & { paginate?: PaginationOptions }): Promise> + async $find(_params?: AdapterParams & { paginate: false }): Promise + async $find(params?: AdapterParams): Promise> + async $find(params?: AdapterParams): Promise> { + if (params && params.paginate === false) { + return { + total: 0, + limit: 10, + skip: 0, + data: [] + } + } + + return [] + } + + async $get(id: Id, _params?: AdapterParams): Promise { + return { id } + } + + async $create(data: Partial[], _params?: AdapterParams): Promise + async $create(data: Partial, _params?: AdapterParams): Promise + async $create(data: Partial | Partial[], _params?: AdapterParams): Promise { + if (Array.isArray(data)) { + return [ + { + id: 'something' + } + ] + } + + return { + id: 'something', + ...data + } + } + + async create(data: Partial | Partial[], params?: AdapterParams): Promise { + return this._create(data, params) + } + + async $update(id: NullableId, _data: Data, _params?: AdapterParams) { + return Promise.resolve({ id }) + } + + async $patch(id: null, _data: Partial, _params?: AdapterParams): Promise + async $patch(id: Id, _data: Partial, _params?: AdapterParams): Promise + async $patch(id: NullableId, _data: Partial, _params?: AdapterParams): Promise { + if (id === null) { + return [] + } + + return { id } + } + + async $remove(id: null, _params?: AdapterParams): Promise + async $remove(id: Id, _params?: AdapterParams): Promise + async $remove(id: NullableId, _params?: AdapterParams) { + if (id === null) { + return [] as Data[] + } + + return { id } + } +} + +export class MethodService extends MethodBase { + find(params?: AdapterParams): Promise> { + return this._find(params) + } + + get(id: Id, params?: AdapterParams): Promise { + return this._get(id, params) + } + + async update(id: Id, data: Data, params?: AdapterParams) { + return this._update(id, data, params) + } + + async patch(id: NullableId, data: Partial, params?: AdapterParams) { + return this._patch(id, data, params) + } + + async remove(id: NullableId, params?: AdapterParams) { + return this._remove(id, params) + } +} diff --git a/packages/adapter-commons/test/query.test.ts b/packages/adapter-commons/test/query.test.ts new file mode 100644 index 0000000000..805704c97e --- /dev/null +++ b/packages/adapter-commons/test/query.test.ts @@ -0,0 +1,313 @@ +import assert from 'assert' +import { ObjectId } from 'mongodb' +import { filterQuery } from '../src' + +describe('@feathersjs/adapter-commons/filterQuery', () => { + describe('$sort', () => { + it('returns $sort when present in query', () => { + const originalQuery = { $sort: { name: 1 } } + const { filters, query } = filterQuery(originalQuery) + + assert.strictEqual(filters.$sort.name, 1) + assert.deepStrictEqual(query, {}) + assert.deepStrictEqual( + originalQuery, + { + $sort: { name: 1 } + }, + 'does not modify original query' + ) + }) + + it('returns $sort when present in query as an object', () => { + const { filters, query } = filterQuery({ + $sort: { name: { something: 10 } } + }) + + assert.strictEqual(filters.$sort.name.something, 10) + assert.deepStrictEqual(query, {}) + }) + + it('converts strings in $sort', () => { + const { filters, query } = filterQuery({ $sort: { test: '-1' } }) + + assert.strictEqual(filters.$sort.test, -1) + assert.deepStrictEqual(query, {}) + }) + + it('does not convert $sort arrays', () => { + const $sort = [ + ['test', '-1'], + ['a', '1'] + ] + const { filters, query } = filterQuery({ $sort }) + + assert.strictEqual(filters.$sort, $sort) + assert.deepStrictEqual(query, {}) + }) + + it('throws an error when special parameter is not known', () => { + try { + const query = { $foo: 1 } + filterQuery(query) + assert.ok(false, 'Should never get here') + } catch (error: any) { + assert.strictEqual(error.name, 'BadRequest') + assert.strictEqual(error.message, 'Invalid filter value $foo') + } + }) + + it('returns undefined when not present in query', () => { + const query = { foo: 1 } + const { filters } = filterQuery(query) + + assert.strictEqual(filters.$sort, undefined) + }) + }) + + describe('$limit', () => { + let testQuery: any + + beforeEach(() => { + testQuery = { $limit: 1 } + }) + + it('returns $limit when present in query', () => { + const { filters, query } = filterQuery(testQuery) + + assert.strictEqual(filters.$limit, 1) + assert.deepStrictEqual(query, {}) + }) + + it('returns undefined when not present in query', () => { + const query = { foo: 1 } + const { filters } = filterQuery(query) + + assert.strictEqual(filters.$limit, undefined) + }) + + it('removes $limit from query when present', () => { + assert.deepStrictEqual(filterQuery(testQuery).query, {}) + }) + + it('parses $limit strings into integers (#4)', () => { + const { filters } = filterQuery({ $limit: '2' }) + + assert.strictEqual(filters.$limit, 2) + }) + + it('allows $limit 0', () => { + const { filters } = filterQuery({ $limit: 0 }, { paginate: { default: 10 } }) + + assert.strictEqual(filters.$limit, 0) + }) + + describe('pagination', () => { + it('limits with default pagination', () => { + const { filters } = filterQuery({}, { paginate: { default: 10 } }) + const { filters: filtersNeg } = filterQuery({ $limit: -20 }, { paginate: { default: 5, max: 10 } }) + + assert.strictEqual(filters.$limit, 10) + assert.strictEqual(filtersNeg.$limit, 5) + }) + + it('limits with max pagination', () => { + const { filters } = filterQuery({ $limit: 20 }, { paginate: { default: 5, max: 10 } }) + + assert.strictEqual(filters.$limit, 10) + }) + + it('limits with default pagination when not a number', () => { + const { filters } = filterQuery({ $limit: 'something' }, { paginate: { default: 5, max: 10 } }) + + assert.strictEqual(filters.$limit, 5) + }) + + it('limits to 0 when no paginate.default and not a number', () => { + const { filters } = filterQuery({ $limit: 'something' }, { paginate: { max: 10 } }) + + assert.strictEqual(filters.$limit, 0) + }) + + it('still uses paginate.max when there is no paginate.default (#2104)', () => { + const { filters } = filterQuery({ $limit: 100 }, { paginate: { max: 10 } }) + + assert.strictEqual(filters.$limit, 10) + }) + }) + }) + + describe('$skip', () => { + let testQuery: any + + beforeEach(() => { + testQuery = { $skip: 1 } + }) + + it('returns $skip when present in query', () => { + const { filters } = filterQuery(testQuery) + + assert.strictEqual(filters.$skip, 1) + }) + + it('removes $skip from query when present', () => { + assert.deepStrictEqual(filterQuery(testQuery).query, {}) + }) + + it('returns undefined when not present in query', () => { + const query = { foo: 1 } + const { filters } = filterQuery(query) + + assert.strictEqual(filters.$skip, undefined) + }) + + it('parses $skip strings into integers (#4)', () => { + const { filters } = filterQuery({ $skip: '33' }) + + assert.strictEqual(filters.$skip, 33) + }) + }) + + describe('$select', () => { + let testQuery: any + + beforeEach(() => { + testQuery = { $select: 1 } + }) + + it('returns $select when present in query', () => { + const { filters } = filterQuery(testQuery) + + assert.strictEqual(filters.$select, 1) + }) + + it('removes $select from query when present', () => { + assert.deepStrictEqual(filterQuery(testQuery).query, {}) + }) + + it('returns undefined when not present in query', () => { + const query = { foo: 1 } + const { filters } = filterQuery(query) + + assert.strictEqual(filters.$select, undefined) + }) + + it('includes Symbols', () => { + const TEST = Symbol('testing') + const original = { + [TEST]: 'message', + other: true, + sub: { [TEST]: 'othermessage' } + } + + const { query } = filterQuery(original) + + assert.deepStrictEqual(query, { + [TEST]: 'message', + other: true, + sub: { [TEST]: 'othermessage' } + }) + }) + + it('only converts plain objects', () => { + const userId = new ObjectId() + const original = { + userId + } + + const { query } = filterQuery(original) + + assert.deepStrictEqual(query, original) + }) + }) + + describe('arrays', () => { + it('validates queries in arrays', () => { + assert.throws( + () => { + filterQuery({ + $or: [{ $exists: false }] + }) + }, + { + name: 'BadRequest', + message: 'Invalid query parameter $exists' + } + ) + }) + + it('allows default operators in $or', () => { + const { filters } = filterQuery({ + $or: [{ value: { $gte: 10 } }] + }) + + assert.deepStrictEqual(filters, { + $or: [{ value: { $gte: 10 } }] + }) + }) + }) + + describe('additional filters', () => { + it('throw error when not set as additionals', () => { + try { + filterQuery({ $select: 1, $known: 1 }) + assert.ok(false, 'Should never get here') + } catch (error: any) { + assert.strictEqual(error.message, 'Invalid filter value $known') + } + }) + + it('returns default and known additional filters (array)', () => { + const query = { $select: ['a', 'b'], $known: 1, $unknown: 1 } + const { filters } = filterQuery(query, { + filters: { + $known: true, + $unknown: true + } + }) + + assert.strictEqual(filters.$unknown, 1) + assert.strictEqual(filters.$known, 1) + assert.deepStrictEqual(filters.$select, ['a', 'b']) + }) + + it('returns default and known additional filters (object)', () => { + const { filters } = filterQuery( + { + $known: 1, + $select: 1 + }, + { filters: { $known: (value: any) => value.toString() } } + ) + + assert.strictEqual(filters.$unknown, undefined) + assert.strictEqual(filters.$known, '1') + assert.strictEqual(filters.$select, 1) + }) + }) + + describe('additional operators', () => { + it('returns query with default and known additional operators', () => { + const { query } = filterQuery( + { + prop: { $ne: 1, $known: 1 } + }, + { operators: ['$known'] } + ) + + assert.deepStrictEqual(query, { prop: { $ne: 1, $known: 1 } }) + }) + + it('throws an error with unknown query operator', () => { + assert.throws( + () => + filterQuery({ + prop: { $unknown: 'something' } + }), + { + message: 'Invalid query parameter $unknown' + } + ) + }) + }) +}) diff --git a/packages/adapter-commons/test/service.test.ts b/packages/adapter-commons/test/service.test.ts index 5329df86ef..5eee9c62b2 100644 --- a/packages/adapter-commons/test/service.test.ts +++ b/packages/adapter-commons/test/service.test.ts @@ -1,223 +1,214 @@ -/* eslint-disable @typescript-eslint/no-unused-vars */ -import assert from 'assert'; -import { NotImplemented } from '@feathersjs/errors'; -import { AdapterService, InternalServiceMethods } from '../src'; -import { Params, Id, NullableId } from '@feathersjs/feathers'; - -const METHODS: [ 'find', 'get', 'create', 'update', 'patch', 'remove' ] = [ 'find', 'get', 'create', 'update', 'patch', 'remove' ]; +/* eslint-disable @typescript-eslint/no-unused-vars, @typescript-eslint/ban-ts-comment */ +import assert from 'assert' +import { MethodService } from './fixture' + +const METHODS: ['find', 'get', 'create', 'update', 'patch', 'remove'] = [ + 'find', + 'get', + 'create', + 'update', + 'patch', + 'remove' +] describe('@feathersjs/adapter-commons/service', () => { - class CustomService extends AdapterService { - } - - describe('errors when method does not exit', () => { - METHODS.forEach(method => { - it(`${method}`, () => { - const service = new CustomService({}); - - // @ts-ignore - return service[method]().then(() => { - throw new Error('Should never get here'); - }).catch((error: Error) => { - assert.ok(error instanceof NotImplemented); - assert.strictEqual(error.message, `Method _${method} not available`); - }); - }); - }); - }); - describe('works when methods exist', () => { - class MethodService extends AdapterService implements InternalServiceMethods { - _find (_params?: Params) { - return Promise.resolve([]); - } - - _get (id: Id, _params?: Params) { - return Promise.resolve({ id }); - } - - _create (data: Partial | Partial[], _params?: Params) { - return Promise.resolve(data); - } - - _update (id: NullableId, _data: any, _params?: Params) { - return Promise.resolve({ id }); - } - - _patch (id: NullableId, _data: any, _params?: Params) { - return Promise.resolve({ id }); - } - - _remove (id: NullableId, _params?: Params) { - return Promise.resolve({ id }); - } - } - - METHODS.forEach(method => { + METHODS.forEach((method) => { it(`${method}`, () => { - const service = new MethodService({}); - const args = []; + const service = new MethodService({}) + const args = [] if (method !== 'find') { - args.push('test'); + args.push('test') } if (method === 'update' || method === 'patch') { - args.push({}); + args.push({}) } // @ts-ignore - return service[method](...args); - }); - }); - - it('does not allow multi patch', () => { - const service = new MethodService({}); - - return service.patch(null, {}) - .then(() => assert.ok(false)) - .catch(error => { - assert.strictEqual(error.name, 'MethodNotAllowed'); - assert.strictEqual(error.message, 'Can not patch multiple entries'); - }); - }); - - it('does not allow multi remove', () => { - const service = new MethodService({}); - - return service.remove(null, {}) - .then(() => assert.ok(false)) - .catch(error => { - assert.strictEqual(error.name, 'MethodNotAllowed'); - assert.strictEqual(error.message, 'Can not remove multiple entries'); - }); - }); - - it('does not allow multi create', () => { - const service = new MethodService({}); - - return service.create([]) - .then(() => assert.ok(false)) - .catch(error => { - assert.strictEqual(error.name, 'MethodNotAllowed'); - assert.strictEqual(error.message, 'Can not create multiple entries'); - }); - }); - - it('multi can be set to true', () => { - const service = new MethodService({}); - - service.options.multi = true; - - return service.create([]) - .then(() => assert.ok(true)); - }); - }); - - it('filterQuery', () => { - const service = new CustomService({ - whitelist: [ '$something' ] - }); - const filtered = service.filterQuery({ - query: { $limit: 10, test: 'me' } - }); - - assert.deepStrictEqual(filtered, { - paginate: {}, - filters: { $limit: 10 }, - query: { test: 'me' } - }); - - const withWhitelisted = service.filterQuery({ - query: { $limit: 10, $something: 'else' } - }); - - assert.deepStrictEqual(withWhitelisted, { - paginate: {}, - filters: { $limit: 10 }, - query: { $something: 'else' } - }); - }); + return service[method](...args) + }) + }) + + it('does not allow multi patch', async () => { + const service = new MethodService({}) + + await assert.rejects(() => service.patch(null, {}), { + name: 'MethodNotAllowed', + message: 'Can not patch multiple entries' + }) + }) + + it('does not allow multi remove', async () => { + const service = new MethodService({}) + + await assert.rejects(() => service.remove(null, {}), { + name: 'MethodNotAllowed', + message: 'Can not remove multiple entries' + }) + }) + + it('does not allow multi create', async () => { + const service = new MethodService({}) + + await assert.rejects(() => service.create([], {}), { + name: 'MethodNotAllowed', + message: 'Can not create multiple entries' + }) + }) + + it('multi can be set to true', async () => { + const service = new MethodService({}) + + service.options.multi = true + + await service.create([]) + }) + }) + + it('sanitizeQuery', async () => { + const service = new MethodService({ + filters: { + $something: true + }, + operators: ['$test'] + }) + + assert.deepStrictEqual( + await service.sanitizeQuery({ + query: { $limit: '10', test: 'me' } as any + }), + { $limit: 10, test: 'me' } + ) + + assert.deepStrictEqual( + await service.sanitizeQuery({ + adapter: { + paginate: { max: 2 } + }, + query: { $limit: '10', test: 'me' } as any + }), + { $limit: 2, test: 'me' } + ) + + await assert.rejects( + () => + service.sanitizeQuery({ + query: { name: { $bla: 'me' } } + }), + { + message: 'Invalid query parameter $bla' + } + ) + + assert.deepStrictEqual( + await service.sanitizeQuery({ + adapter: { + operators: ['$bla'] + }, + query: { name: { $bla: 'Dave' } } + }), + { name: { $bla: 'Dave' } } + ) + }) it('getOptions', () => { - const service = new AdapterService({ - multi: true - }); + const service = new MethodService({ + multi: true, + paginate: { + default: 1, + max: 10 + } + }) const opts = service.getOptions({ adapter: { - multi: [ 'create' ], + multi: ['create'], paginate: { default: 10, max: 100 } } - }); + }) assert.deepStrictEqual(opts, { id: 'id', events: [], paginate: { default: 10, max: 100 }, - multi: [ 'create' ], - filters: [], - allow: [] - }); - }); + multi: ['create'], + filters: {}, + operators: [] + }) + + const notPaginated = service.getOptions({ + paginate: false + }) + + assert.deepStrictEqual(notPaginated, { + id: 'id', + events: [], + paginate: false, + multi: true, + filters: {}, + operators: [] + }) + }) it('allowsMulti', () => { context('with true', () => { - const service = new AdapterService({multi: true}); + const service = new MethodService({ multi: true }) - it('does return true for multible methodes', () => { - assert.equal(service.allowsMulti('patch'), true); - }); + it('does return true for multiple methodes', () => { + assert.equal(service.allowsMulti('patch'), true) + }) - it('does return false for always non-multible methodes', () => { - assert.equal(service.allowsMulti('update'), false); - }); + it('does return false for always non-multiple methodes', () => { + assert.equal(service.allowsMulti('update'), false) + }) it('does return true for unknown methods', () => { - assert.equal(service.allowsMulti('other'), true); - }); - }); + assert.equal(service.allowsMulti('other'), true) + }) + }) context('with false', () => { - const service = new AdapterService({multi: false}); + const service = new MethodService({ multi: false }) - it('does return false for multible methodes', () => { - assert.equal(service.allowsMulti('remove'), false); - }); + it('does return false for multiple methodes', () => { + assert.equal(service.allowsMulti('remove'), false) + }) - it('does return true for always multible methodes', () => { - assert.equal(service.allowsMulti('find'), true); - }); + it('does return true for always multiple methodes', () => { + assert.equal(service.allowsMulti('find'), true) + }) it('does return false for unknown methods', () => { - assert.equal(service.allowsMulti('other'), false); - }); - }); + assert.equal(service.allowsMulti('other'), false) + }) + }) context('with array', () => { - const service = new AdapterService({multi: ['create', 'get', 'other']}); + const service = new MethodService({ multi: ['create', 'get', 'other'] }) - it('does return true for specified multible methodes', () => { - assert.equal(service.allowsMulti('create'), true); - }); + it('does return true for specified multiple methodes', () => { + assert.equal(service.allowsMulti('create'), true) + }) - it('does return false for non-specified multible methodes', () => { - assert.equal(service.allowsMulti('patch'), false); - }); + it('does return false for non-specified multiple methodes', () => { + assert.equal(service.allowsMulti('patch'), false) + }) - it('does return false for specified always multible methodes', () => { - assert.equal(service.allowsMulti('get'), false); - }); + it('does return false for specified always multiple methodes', () => { + assert.equal(service.allowsMulti('get'), false) + }) it('does return true for specified unknown methodes', () => { - assert.equal(service.allowsMulti('other'), true); - }); + assert.equal(service.allowsMulti('other'), true) + }) it('does return false for non-specified unknown methodes', () => { - assert.equal(service.allowsMulti('another'), false); - }); - }); - }); -}); + assert.equal(service.allowsMulti('another'), false) + }) + }) + }) +}) diff --git a/packages/adapter-commons/test/sort.test.ts b/packages/adapter-commons/test/sort.test.ts index 67964b57a5..d361c681af 100644 --- a/packages/adapter-commons/test/sort.test.ts +++ b/packages/adapter-commons/test/sort.test.ts @@ -1,127 +1,157 @@ -import assert from 'assert'; -import { sorter } from '../src'; +import assert from 'assert' +import { sorter } from '../src' describe('@feathersjs/adapter-commons', () => { describe('sorter', () => { it('simple sorter', () => { - const array = [{ - name: 'David' - }, { - name: 'Eric' - }]; + const array = [ + { + name: 'David' + }, + { + name: 'Eric' + } + ] const sort = sorter({ name: -1 - }); + }) - assert.deepStrictEqual(array.sort(sort), [{ - name: 'Eric' - }, { - name: 'David' - }]); - }); + assert.deepStrictEqual(array.sort(sort), [ + { + name: 'Eric' + }, + { + name: 'David' + } + ]) + }) it('simple sorter with arrays', () => { - const array = [{ - names: [ 'a', 'b' ] - }, { - names: [ 'c', 'd' ] - }]; + const array = [ + { + names: ['a', 'b'] + }, + { + names: ['c', 'd'] + } + ] const sort = sorter({ names: -1 - }); + }) - assert.deepStrictEqual(array.sort(sort), [{ - names: [ 'c', 'd' ] - }, { - names: [ 'a', 'b' ] - }]); - }); + assert.deepStrictEqual(array.sort(sort), [ + { + names: ['c', 'd'] + }, + { + names: ['a', 'b'] + } + ]) + }) it('simple sorter with objects', () => { - const array = [{ - names: { - first: 'Dave', - last: 'L' + const array = [ + { + names: { + first: 'Dave', + last: 'L' + } + }, + { + names: { + first: 'A', + last: 'B' + } } - }, { - names: { - first: 'A', - last: 'B' - } - }]; + ] const sort = sorter({ names: 1 - }); + }) - assert.deepStrictEqual(array.sort(sort), [{ - names: { - first: 'A', - last: 'B' - } - }, { - names: { - first: 'Dave', - last: 'L' + assert.deepStrictEqual(array.sort(sort), [ + { + names: { + first: 'A', + last: 'B' + } + }, + { + names: { + first: 'Dave', + last: 'L' + } } - }]); - }); + ]) + }) it('two property sorter', () => { - const array = [{ - name: 'David', - counter: 0 - }, { - name: 'Eric', - counter: 1 - }, { - name: 'David', - counter: 1 - }, { - name: 'Eric', - counter: 0 - }]; + const array = [ + { + name: 'David', + counter: 0 + }, + { + name: 'Eric', + counter: 1 + }, + { + name: 'David', + counter: 1 + }, + { + name: 'Eric', + counter: 0 + } + ] const sort = sorter({ name: -1, counter: 1 - }); + }) assert.deepStrictEqual(array.sort(sort), [ { name: 'Eric', counter: 0 }, { name: 'Eric', counter: 1 }, { name: 'David', counter: 0 }, { name: 'David', counter: 1 } - ]); - }); + ]) + }) it('two property sorter with names', () => { - const array = [{ - name: 'David', - counter: 0 - }, { - name: 'Eric', - counter: 1 - }, { - name: 'Andrew', - counter: 1 - }, { - name: 'David', - counter: 1 - }, { - name: 'Andrew', - counter: 0 - }, { - name: 'Eric', - counter: 0 - }]; + const array = [ + { + name: 'David', + counter: 0 + }, + { + name: 'Eric', + counter: 1 + }, + { + name: 'Andrew', + counter: 1 + }, + { + name: 'David', + counter: 1 + }, + { + name: 'Andrew', + counter: 0 + }, + { + name: 'Eric', + counter: 0 + } + ] const sort = sorter({ name: -1, counter: 1 - }); + }) assert.deepStrictEqual(array.sort(sort), [ { name: 'Eric', counter: 0 }, @@ -130,41 +160,48 @@ describe('@feathersjs/adapter-commons', () => { { name: 'David', counter: 1 }, { name: 'Andrew', counter: 0 }, { name: 'Andrew', counter: 1 } - ]); - }); + ]) + }) it('three property sorter with names', () => { - const array = [{ - name: 'David', - counter: 0, - age: 2 - }, { - name: 'Eric', - counter: 1, - age: 2 - }, { - name: 'David', - counter: 1, - age: 1 - }, { - name: 'Eric', - counter: 0, - age: 1 - }, { - name: 'Andrew', - counter: 0, - age: 2 - }, { - name: 'Andrew', - counter: 0, - age: 1 - }]; + const array = [ + { + name: 'David', + counter: 0, + age: 2 + }, + { + name: 'Eric', + counter: 1, + age: 2 + }, + { + name: 'David', + counter: 1, + age: 1 + }, + { + name: 'Eric', + counter: 0, + age: 1 + }, + { + name: 'Andrew', + counter: 0, + age: 2 + }, + { + name: 'Andrew', + counter: 0, + age: 1 + } + ] const sort = sorter({ name: -1, counter: 1, age: -1 - }); + }) assert.deepStrictEqual(array.sort(sort), [ { name: 'Eric', counter: 0, age: 1 }, @@ -173,121 +210,175 @@ describe('@feathersjs/adapter-commons', () => { { name: 'David', counter: 1, age: 1 }, { name: 'Andrew', counter: 0, age: 2 }, { name: 'Andrew', counter: 0, age: 1 } - ]); - }); - }); + ]) + }) + }) describe('sorter mongoDB-like sorting on embedded objects', () => { - let data: any[] = []; + let data: any[] = [] beforeEach(() => { data = [ - { _id: 1, item: { category: "cake", type: "chiffon" }, amount: 10 }, - { _id: 2, item: { category: "cookies", type: "chocolate chip" }, amount: 50 }, - { _id: 3, item: { category: "cookies", type: "chocolate chip" }, amount: 15 }, - { _id: 4, item: { category: "cake", type: "lemon" }, amount: 30 }, - { _id: 5, item: { category: "cake", type: "carrot" }, amount: 20 }, - { _id: 6, item: { category: "brownies", type: "blondie" }, amount: 10 } - ]; - - }); + { _id: 1, item: { category: 'cake', type: 'chiffon' }, amount: 10 }, + { + _id: 2, + item: { category: 'cookies', type: 'chocolate chip' }, + amount: 50 + }, + { + _id: 3, + item: { category: 'cookies', type: 'chocolate chip' }, + amount: 15 + }, + { _id: 4, item: { category: 'cake', type: 'lemon' }, amount: 30 }, + { _id: 5, item: { category: 'cake', type: 'carrot' }, amount: 20 }, + { _id: 6, item: { category: 'brownies', type: 'blondie' }, amount: 10 } + ] + }) it('straight test', () => { const sort = sorter({ amount: -1 - }); + }) assert.deepStrictEqual(data.sort(sort), [ - { _id: 2, item: { category: "cookies", type: "chocolate chip" }, amount: 50 }, - { _id: 4, item: { category: "cake", type: "lemon" }, amount: 30 }, - { _id: 5, item: { category: "cake", type: "carrot" }, amount: 20 }, - { _id: 3, item: { category: "cookies", type: "chocolate chip" }, amount: 15 }, - { _id: 1, item: { category: "cake", type: "chiffon" }, amount: 10 }, - { _id: 6, item: { category: "brownies", type: "blondie" }, amount: 10 } - ]); - }); + { + _id: 2, + item: { category: 'cookies', type: 'chocolate chip' }, + amount: 50 + }, + { _id: 4, item: { category: 'cake', type: 'lemon' }, amount: 30 }, + { _id: 5, item: { category: 'cake', type: 'carrot' }, amount: 20 }, + { + _id: 3, + item: { category: 'cookies', type: 'chocolate chip' }, + amount: 15 + }, + { _id: 1, item: { category: 'cake', type: 'chiffon' }, amount: 10 }, + { _id: 6, item: { category: 'brownies', type: 'blondie' }, amount: 10 } + ]) + }) it('embedded sort 1', () => { const sort = sorter({ - "item.category": 1, - "item.type": 1, - }); + 'item.category': 1, + 'item.type': 1 + }) assert.deepStrictEqual(data.sort(sort), [ - { _id: 6, item: { category: "brownies", type: "blondie" }, amount: 10 }, - { _id: 5, item: { category: "cake", type: "carrot" }, amount: 20 }, - { _id: 1, item: { category: "cake", type: "chiffon" }, amount: 10 }, - { _id: 4, item: { category: "cake", type: "lemon" }, amount: 30 }, - { _id: 2, item: { category: "cookies", type: "chocolate chip" }, amount: 50 }, - { _id: 3, item: { category: "cookies", type: "chocolate chip" }, amount: 15 } - ]); - }); + { _id: 6, item: { category: 'brownies', type: 'blondie' }, amount: 10 }, + { _id: 5, item: { category: 'cake', type: 'carrot' }, amount: 20 }, + { _id: 1, item: { category: 'cake', type: 'chiffon' }, amount: 10 }, + { _id: 4, item: { category: 'cake', type: 'lemon' }, amount: 30 }, + { + _id: 2, + item: { category: 'cookies', type: 'chocolate chip' }, + amount: 50 + }, + { + _id: 3, + item: { category: 'cookies', type: 'chocolate chip' }, + amount: 15 + } + ]) + }) it('embedded sort 2', () => { const sort = sorter({ - "item.category": 1, - "item.type": 1, + 'item.category': 1, + 'item.type': 1, amount: 1 - }); + }) assert.deepStrictEqual(data.sort(sort), [ - { _id: 6, item: { category: "brownies", type: "blondie" }, amount: 10 }, - { _id: 5, item: { category: "cake", type: "carrot" }, amount: 20 }, - { _id: 1, item: { category: "cake", type: "chiffon" }, amount: 10 }, - { _id: 4, item: { category: "cake", type: "lemon" }, amount: 30 }, - { _id: 3, item: { category: "cookies", type: "chocolate chip" }, amount: 15 }, - { _id: 2, item: { category: "cookies", type: "chocolate chip" }, amount: 50 } - ]); - }); + { _id: 6, item: { category: 'brownies', type: 'blondie' }, amount: 10 }, + { _id: 5, item: { category: 'cake', type: 'carrot' }, amount: 20 }, + { _id: 1, item: { category: 'cake', type: 'chiffon' }, amount: 10 }, + { _id: 4, item: { category: 'cake', type: 'lemon' }, amount: 30 }, + { + _id: 3, + item: { category: 'cookies', type: 'chocolate chip' }, + amount: 15 + }, + { + _id: 2, + item: { category: 'cookies', type: 'chocolate chip' }, + amount: 50 + } + ]) + }) it('embedded sort 3', () => { const sort = sorter({ - "item.category": 1, - "item.type": 1, + 'item.category': 1, + 'item.type': 1, amount: -1 - }); + }) assert.deepStrictEqual(data.sort(sort), [ - { _id: 6, item: { category: "brownies", type: "blondie" }, amount: 10 }, - { _id: 5, item: { category: "cake", type: "carrot" }, amount: 20 }, - { _id: 1, item: { category: "cake", type: "chiffon" }, amount: 10 }, - { _id: 4, item: { category: "cake", type: "lemon" }, amount: 30 }, - { _id: 2, item: { category: "cookies", type: "chocolate chip" }, amount: 50 }, - { _id: 3, item: { category: "cookies", type: "chocolate chip" }, amount: 15 } - ]); - }); + { _id: 6, item: { category: 'brownies', type: 'blondie' }, amount: 10 }, + { _id: 5, item: { category: 'cake', type: 'carrot' }, amount: 20 }, + { _id: 1, item: { category: 'cake', type: 'chiffon' }, amount: 10 }, + { _id: 4, item: { category: 'cake', type: 'lemon' }, amount: 30 }, + { + _id: 2, + item: { category: 'cookies', type: 'chocolate chip' }, + amount: 50 + }, + { + _id: 3, + item: { category: 'cookies', type: 'chocolate chip' }, + amount: 15 + } + ]) + }) it('embedded sort 4', () => { const sort = sorter({ amount: -1, - "item.category": 1 - }); + 'item.category': 1 + }) assert.deepStrictEqual(data.sort(sort), [ - { _id: 2, item: { category: "cookies", type: "chocolate chip" }, amount: 50 }, - { _id: 4, item: { category: "cake", type: "lemon" }, amount: 30 }, - { _id: 5, item: { category: "cake", type: "carrot" }, amount: 20 }, - { _id: 3, item: { category: "cookies", type: "chocolate chip" }, amount: 15 }, - { _id: 6, item: { category: "brownies", type: "blondie" }, amount: 10 }, - { _id: 1, item: { category: "cake", type: "chiffon" }, amount: 10 } - ]); - }); + { + _id: 2, + item: { category: 'cookies', type: 'chocolate chip' }, + amount: 50 + }, + { _id: 4, item: { category: 'cake', type: 'lemon' }, amount: 30 }, + { _id: 5, item: { category: 'cake', type: 'carrot' }, amount: 20 }, + { + _id: 3, + item: { category: 'cookies', type: 'chocolate chip' }, + amount: 15 + }, + { _id: 6, item: { category: 'brownies', type: 'blondie' }, amount: 10 }, + { _id: 1, item: { category: 'cake', type: 'chiffon' }, amount: 10 } + ]) + }) it('embedded sort 5', () => { const sort = sorter({ - "item.category": 1, + 'item.category': 1, amount: 1 - }); + }) assert.deepStrictEqual(data.sort(sort), [ - { _id: 6, item: { category: "brownies", type: "blondie" }, amount: 10 }, - { _id: 1, item: { category: "cake", type: "chiffon" }, amount: 10 }, - { _id: 5, item: { category: "cake", type: "carrot" }, amount: 20 }, - { _id: 4, item: { category: "cake", type: "lemon" }, amount: 30 }, - { _id: 3, item: { category: "cookies", type: "chocolate chip" }, amount: 15 }, - { _id: 2, item: { category: "cookies", type: "chocolate chip" }, amount: 50 } - ]); - }); - }); - -}); + { _id: 6, item: { category: 'brownies', type: 'blondie' }, amount: 10 }, + { _id: 1, item: { category: 'cake', type: 'chiffon' }, amount: 10 }, + { _id: 5, item: { category: 'cake', type: 'carrot' }, amount: 20 }, + { _id: 4, item: { category: 'cake', type: 'lemon' }, amount: 30 }, + { + _id: 3, + item: { category: 'cookies', type: 'chocolate chip' }, + amount: 15 + }, + { + _id: 2, + item: { category: 'cookies', type: 'chocolate chip' }, + amount: 50 + } + ]) + }) + }) +}) diff --git a/packages/adapter-tests/CHANGELOG.md b/packages/adapter-tests/CHANGELOG.md index 3ae8789023..1ce95e8341 100644 --- a/packages/adapter-tests/CHANGELOG.md +++ b/packages/adapter-tests/CHANGELOG.md @@ -3,452 +3,315 @@ All notable changes to this project will be documented in this file. See [Conventional Commits](https://conventionalcommits.org) for commit guidelines. -# [5.0.0-pre.16](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.15...v5.0.0-pre.16) (2022-01-12) +# [5.0.0-pre.31](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.30...v5.0.0-pre.31) (2022-10-12) **Note:** Version bump only for package @feathersjs/adapter-tests +# [5.0.0-pre.30](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.29...v5.0.0-pre.30) (2022-10-07) +### Features +- **core:** Allow to unregister services at runtime ([#2756](https://github.com/feathersjs/feathers/issues/2756)) ([d16601f](https://github.com/feathersjs/feathers/commit/d16601f2277dca5357866ffdefba2a611f6dc7fa)) +# [5.0.0-pre.29](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.28...v5.0.0-pre.29) (2022-09-16) -# [5.0.0-pre.15](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.14...v5.0.0-pre.15) (2021-11-27) +**Note:** Version bump only for package @feathersjs/adapter-tests +# [5.0.0-pre.28](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.27...v5.0.0-pre.28) (2022-08-03) ### Bug Fixes -* **typescript:** Overall typing improvements ([#2478](https://github.com/feathersjs/feathers/issues/2478)) ([b8eb804](https://github.com/feathersjs/feathers/commit/b8eb804158556d9651a8607e3c3fda15e0bfd110)) +- **cli:** Improve generated application and client ([#2701](https://github.com/feathersjs/feathers/issues/2701)) ([bd55ffb](https://github.com/feathersjs/feathers/commit/bd55ffb812e89bf215f4515e7f137656ea888c3f)) +# [5.0.0-pre.27](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.26...v5.0.0-pre.27) (2022-07-13) +**Note:** Version bump only for package @feathersjs/adapter-tests +# [5.0.0-pre.26](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.25...v5.0.0-pre.26) (2022-06-22) +**Note:** Version bump only for package @feathersjs/adapter-tests -# [5.0.0-pre.14](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.13...v5.0.0-pre.14) (2021-10-13) +# [5.0.0-pre.25](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.24...v5.0.0-pre.25) (2022-06-22) **Note:** Version bump only for package @feathersjs/adapter-tests +# [5.0.0-pre.24](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.23...v5.0.0-pre.24) (2022-06-21) +**Note:** Version bump only for package @feathersjs/adapter-tests +# [5.0.0-pre.23](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.22...v5.0.0-pre.23) (2022-06-06) +**Note:** Version bump only for package @feathersjs/adapter-tests -# [5.0.0-pre.13](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.12...v5.0.0-pre.13) (2021-10-13) +# [5.0.0-pre.22](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.21...v5.0.0-pre.22) (2022-05-24) **Note:** Version bump only for package @feathersjs/adapter-tests +# [5.0.0-pre.20](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.19...v5.0.0-pre.20) (2022-05-04) +**Note:** Version bump only for package @feathersjs/adapter-tests +# [5.0.0-pre.19](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.18...v5.0.0-pre.19) (2022-05-01) +### Bug Fixes -# [5.0.0-pre.12](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.11...v5.0.0-pre.12) (2021-10-12) +- **adapter-commons:** Clarify adapter query filtering ([#2607](https://github.com/feathersjs/feathers/issues/2607)) ([2dac771](https://github.com/feathersjs/feathers/commit/2dac771b0a3298d6dd25994d05186701b0617718)) +- **adapter-tests:** Ensure multi tests can run standalone ([#2608](https://github.com/feathersjs/feathers/issues/2608)) ([d7243f2](https://github.com/feathersjs/feathers/commit/d7243f20e84d9dde428ad8dfc7f48388ca569e6e)) -**Note:** Version bump only for package @feathersjs/adapter-tests +### BREAKING CHANGES +- **adapter-commons:** Changes the common adapter base class to use `sanitizeQuery` and `sanitizeData` +# [5.0.0-pre.18](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.17...v5.0.0-pre.18) (2022-04-11) +### Bug Fixes +- **adapter-tests:** Add tests for pagination in multi updates ([#2472](https://github.com/feathersjs/feathers/issues/2472)) ([98a811a](https://github.com/feathersjs/feathers/commit/98a811ac605575ff812a08d0504729a5efe7a69c)) -# [5.0.0-pre.11](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.10...v5.0.0-pre.11) (2021-10-06) +# [5.0.0-pre.17](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.16...v5.0.0-pre.17) (2022-02-15) **Note:** Version bump only for package @feathersjs/adapter-tests +# [5.0.0-pre.16](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.15...v5.0.0-pre.16) (2022-01-12) +**Note:** Version bump only for package @feathersjs/adapter-tests +# [5.0.0-pre.15](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.14...v5.0.0-pre.15) (2021-11-27) +### Bug Fixes -# [5.0.0-pre.10](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.9...v5.0.0-pre.10) (2021-09-19) +- **typescript:** Overall typing improvements ([#2478](https://github.com/feathersjs/feathers/issues/2478)) ([b8eb804](https://github.com/feathersjs/feathers/commit/b8eb804158556d9651a8607e3c3fda15e0bfd110)) + +# [5.0.0-pre.14](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.13...v5.0.0-pre.14) (2021-10-13) **Note:** Version bump only for package @feathersjs/adapter-tests +# [5.0.0-pre.13](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.12...v5.0.0-pre.13) (2021-10-13) +**Note:** Version bump only for package @feathersjs/adapter-tests +# [5.0.0-pre.12](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.11...v5.0.0-pre.12) (2021-10-12) +**Note:** Version bump only for package @feathersjs/adapter-tests -# [5.0.0-pre.9](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.8...v5.0.0-pre.9) (2021-08-09) +# [5.0.0-pre.11](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.10...v5.0.0-pre.11) (2021-10-06) **Note:** Version bump only for package @feathersjs/adapter-tests +# [5.0.0-pre.10](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.9...v5.0.0-pre.10) (2021-09-19) +**Note:** Version bump only for package @feathersjs/adapter-tests +# [5.0.0-pre.9](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.8...v5.0.0-pre.9) (2021-08-09) +**Note:** Version bump only for package @feathersjs/adapter-tests # [5.0.0-pre.8](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.7...v5.0.0-pre.8) (2021-08-09) **Note:** Version bump only for package @feathersjs/adapter-tests - - - - # [5.0.0-pre.7](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.6...v5.0.0-pre.7) (2021-08-09) **Note:** Version bump only for package @feathersjs/adapter-tests - - - - # [5.0.0-pre.6](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.5...v5.0.0-pre.6) (2021-08-08) **Note:** Version bump only for package @feathersjs/adapter-tests - - - - # [5.0.0-pre.5](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.4...v5.0.0-pre.5) (2021-06-23) - ### Bug Fixes -* Update database adapter common repository urls ([#2380](https://github.com/feathersjs/feathers/issues/2380)) ([3f4db68](https://github.com/feathersjs/feathers/commit/3f4db68d6700c7d9023ecd17d0d39893f75a19fd)) - +- Update database adapter common repository urls ([#2380](https://github.com/feathersjs/feathers/issues/2380)) ([3f4db68](https://github.com/feathersjs/feathers/commit/3f4db68d6700c7d9023ecd17d0d39893f75a19fd)) ### Features -* **adapter-commons:** Add support for params.adapter option and move memory adapter to @feathersjs/memory ([#2367](https://github.com/feathersjs/feathers/issues/2367)) ([a43e7da](https://github.com/feathersjs/feathers/commit/a43e7da22b6b981a96d1321736ea9a0cb924fb4f)) - - - - +- **adapter-commons:** Add support for params.adapter option and move memory adapter to @feathersjs/memory ([#2367](https://github.com/feathersjs/feathers/issues/2367)) ([a43e7da](https://github.com/feathersjs/feathers/commit/a43e7da22b6b981a96d1321736ea9a0cb924fb4f)) # [5.0.0-pre.4](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.3...v5.0.0-pre.4) (2021-05-13) **Note:** Version bump only for package @feathersjs/adapter-tests - - - - # [5.0.0-pre.3](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.2...v5.0.0-pre.3) (2021-04-21) - ### Bug Fixes -* **typescript:** Improve TypeScript backwards compatibility ([#2310](https://github.com/feathersjs/feathers/issues/2310)) ([f33be73](https://github.com/feathersjs/feathers/commit/f33be73fc46a533efb15df9aab0658e3240d3897)) - - - - +- **typescript:** Improve TypeScript backwards compatibility ([#2310](https://github.com/feathersjs/feathers/issues/2310)) ([f33be73](https://github.com/feathersjs/feathers/commit/f33be73fc46a533efb15df9aab0658e3240d3897)) # [5.0.0-pre.2](https://github.com/feathersjs/feathers/compare/v5.0.0-beta.1...v5.0.0-pre.2) (2021-04-06) **Note:** Version bump only for package @feathersjs/adapter-tests - - - - # [5.0.0-beta.1](https://github.com/feathersjs/feathers/compare/v5.0.0-beta.0...v5.0.0-beta.1) (2021-04-03) - ### Bug Fixes -* **adapter-tests:** Add test that verified paginated total ([#2273](https://github.com/feathersjs/feathers/issues/2273)) ([879bd6b](https://github.com/feathersjs/feathers/commit/879bd6b24f42e04eeeeba110ddddda3e1e1dea34)) - - - - +- **adapter-tests:** Add test that verified paginated total ([#2273](https://github.com/feathersjs/feathers/issues/2273)) ([879bd6b](https://github.com/feathersjs/feathers/commit/879bd6b24f42e04eeeeba110ddddda3e1e1dea34)) # [5.0.0-beta.0](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.1...v5.0.0-beta.0) (2021-03-28) - ### Features -* **core:** Remove Uberproto ([#2178](https://github.com/feathersjs/feathers/issues/2178)) ([ddf8821](https://github.com/feathersjs/feathers/commit/ddf8821f53317e6a378657f7d66acb03a037ee47)) - +- **core:** Remove Uberproto ([#2178](https://github.com/feathersjs/feathers/issues/2178)) ([ddf8821](https://github.com/feathersjs/feathers/commit/ddf8821f53317e6a378657f7d66acb03a037ee47)) ### BREAKING CHANGES -* **core:** Services no longer extend Uberproto objects and -`service.mixin()` is no longer available. - - - - +- **core:** Services no longer extend Uberproto objects and + `service.mixin()` is no longer available. # [5.0.0-pre.1](https://github.com/feathersjs/feathers/compare/v4.5.11...v5.0.0-pre.1) (2020-12-17) - ### Features -* **memory:** Move feathers-memory into @feathersjs/memory ([#2153](https://github.com/feathersjs/feathers/issues/2153)) ([dd61fe3](https://github.com/feathersjs/feathers/commit/dd61fe371fb0502f78b8ccbe1f45a030e31ecff6)) - - - - +- **memory:** Move feathers-memory into @feathersjs/memory ([#2153](https://github.com/feathersjs/feathers/issues/2153)) ([dd61fe3](https://github.com/feathersjs/feathers/commit/dd61fe371fb0502f78b8ccbe1f45a030e31ecff6)) ## [4.5.11](https://github.com/feathersjs/feathers/compare/v4.5.10...v4.5.11) (2020-12-05) **Note:** Version bump only for package @feathersjs/adapter-tests - - - - ## [4.5.4](https://github.com/feathersjs/feathers/compare/v4.5.3...v4.5.4) (2020-09-27) **Note:** Version bump only for package @feathersjs/adapter-tests - - - - ## 4.5.3 (2020-09-24) - ### Bug Fixes -* **adapter-tests:** Update multi patch + query tests ([#5](https://github.com/feathersjs/databases/issues/5)) ([84f1fe4](https://github.com/feathersjs/databases/commit/84f1fe4f13dc3a26891e43b965f75d08243f6c6f)) - - - - +- **adapter-tests:** Update multi patch + query tests ([#5](https://github.com/feathersjs/databases/issues/5)) ([84f1fe4](https://github.com/feathersjs/databases/commit/84f1fe4f13dc3a26891e43b965f75d08243f6c6f)) ## [4.5.2](https://github.com/feathersjs/feathers/compare/v4.5.1...v4.5.2) (2020-03-04) **Note:** Version bump only for package @feathersjs/adapter-tests - - - - ## [4.5.1](https://github.com/feathersjs/feathers/compare/v4.5.0...v4.5.1) (2020-01-24) **Note:** Version bump only for package @feathersjs/adapter-tests - - - - # [4.5.0](https://github.com/feathersjs/feathers/compare/v4.4.3...v4.5.0) (2020-01-18) **Note:** Version bump only for package @feathersjs/adapter-tests - - - - ## [4.4.3](https://github.com/feathersjs/feathers/compare/v4.4.1...v4.4.3) (2019-12-06) **Note:** Version bump only for package @feathersjs/adapter-tests - - - - ## [4.4.1](https://github.com/feathersjs/feathers/compare/v4.4.0...v4.4.1) (2019-11-27) **Note:** Version bump only for package @feathersjs/adapter-tests - - - - # [4.4.0](https://github.com/feathersjs/feathers/compare/v4.3.11...v4.4.0) (2019-11-27) **Note:** Version bump only for package @feathersjs/adapter-tests - - - - ## [4.3.11](https://github.com/feathersjs/feathers/compare/v4.3.10...v4.3.11) (2019-11-11) **Note:** Version bump only for package @feathersjs/adapter-tests - - - - ## [4.3.10](https://github.com/feathersjs/feathers/compare/v4.3.9...v4.3.10) (2019-10-26) **Note:** Version bump only for package @feathersjs/adapter-tests - - - - ## [4.3.9](https://github.com/feathersjs/feathers/compare/v4.3.8...v4.3.9) (2019-10-26) **Note:** Version bump only for package @feathersjs/adapter-tests - - - - ## [4.3.7](https://github.com/feathersjs/feathers/compare/v4.3.6...v4.3.7) (2019-10-14) **Note:** Version bump only for package @feathersjs/adapter-tests - - - - ## [4.3.4](https://github.com/feathersjs/feathers/compare/v4.3.3...v4.3.4) (2019-10-03) **Note:** Version bump only for package @feathersjs/adapter-tests - - - - ## [4.3.3](https://github.com/feathersjs/feathers/compare/v4.3.2...v4.3.3) (2019-09-21) **Note:** Version bump only for package @feathersjs/adapter-tests - - - - ## [4.3.2](https://github.com/feathersjs/feathers/compare/v4.3.1...v4.3.2) (2019-09-16) **Note:** Version bump only for package @feathersjs/adapter-tests - - - - ## [4.3.1](https://github.com/feathersjs/feathers/compare/v4.3.0...v4.3.1) (2019-09-09) **Note:** Version bump only for package @feathersjs/adapter-tests - - - - # [4.3.0](https://github.com/feathersjs/feathers/compare/v4.3.0-pre.4...v4.3.0) (2019-08-27) **Note:** Version bump only for package @feathersjs/adapter-tests - - - - # [4.3.0-pre.4](https://github.com/feathersjs/feathers/compare/v4.3.0-pre.3...v4.3.0-pre.4) (2019-08-22) **Note:** Version bump only for package @feathersjs/adapter-tests - - - - # [4.3.0-pre.3](https://github.com/feathersjs/feathers/compare/v4.3.0-pre.2...v4.3.0-pre.3) (2019-08-19) **Note:** Version bump only for package @feathersjs/adapter-tests - - - - # [4.3.0-pre.2](https://github.com/feathersjs/feathers/compare/v4.3.0-pre.1...v4.3.0-pre.2) (2019-08-02) **Note:** Version bump only for package @feathersjs/adapter-tests - - - - # [4.3.0-pre.1](https://github.com/feathersjs/feathers/compare/v4.0.0-pre.5...v4.3.0-pre.1) (2019-07-11) **Note:** Version bump only for package @feathersjs/adapter-tests - - - - # [4.0.0-pre.5](https://github.com/feathersjs/feathers/compare/v4.0.0-pre.4...v4.0.0-pre.5) (2019-07-10) - ### Bug Fixes -* Fix feathers-memory dependency that did not get updated ([9422b13](https://github.com/feathersjs/feathers/commit/9422b13)) - - - - +- Fix feathers-memory dependency that did not get updated ([9422b13](https://github.com/feathersjs/feathers/commit/9422b13)) # [4.0.0-pre.4](https://github.com/feathersjs/feathers/compare/v4.0.0-pre.3...v4.0.0-pre.4) (2019-07-05) **Note:** Version bump only for package @feathersjs/adapter-tests - - - - # [4.0.0-pre.3](https://github.com/feathersjs/feathers/compare/v4.0.0-pre.2...v4.0.0-pre.3) (2019-06-01) - ### Bug Fixes -* Update dependencies and fix tests ([#1373](https://github.com/feathersjs/feathers/issues/1373)) ([d743a7f](https://github.com/feathersjs/feathers/commit/d743a7f)) - - - - +- Update dependencies and fix tests ([#1373](https://github.com/feathersjs/feathers/issues/1373)) ([d743a7f](https://github.com/feathersjs/feathers/commit/d743a7f)) # [4.0.0-pre.2](https://github.com/feathersjs/feathers/compare/v4.0.0-pre.1...v4.0.0-pre.2) (2019-05-15) **Note:** Version bump only for package @feathersjs/adapter-tests - - - - # [4.0.0-pre.1](https://github.com/feathersjs/feathers/compare/v4.0.0-pre.0...v4.0.0-pre.1) (2019-05-08) **Note:** Version bump only for package @feathersjs/adapter-tests - - - - # [4.0.0-pre.0](https://github.com/feathersjs/feathers/compare/v3.2.0-pre.1...v4.0.0-pre.0) (2019-04-21) - ### Bug Fixes -* Add test to make sure different id in adapter query works ([#1165](https://github.com/feathersjs/feathers/issues/1165)) ([0ba4580](https://github.com/feathersjs/feathers/commit/0ba4580)) -* Update adapter tests to not rely on error instance ([#1202](https://github.com/feathersjs/feathers/issues/1202)) ([6885e0e](https://github.com/feathersjs/feathers/commit/6885e0e)) -* Update all dependencies to latest ([#1206](https://github.com/feathersjs/feathers/issues/1206)) ([e51e0f6](https://github.com/feathersjs/feathers/commit/e51e0f6)) - +- Add test to make sure different id in adapter query works ([#1165](https://github.com/feathersjs/feathers/issues/1165)) ([0ba4580](https://github.com/feathersjs/feathers/commit/0ba4580)) +- Update adapter tests to not rely on error instance ([#1202](https://github.com/feathersjs/feathers/issues/1202)) ([6885e0e](https://github.com/feathersjs/feathers/commit/6885e0e)) +- Update all dependencies to latest ([#1206](https://github.com/feathersjs/feathers/issues/1206)) ([e51e0f6](https://github.com/feathersjs/feathers/commit/e51e0f6)) ### chore -* **package:** Move adapter tests into their own module ([#1164](https://github.com/feathersjs/feathers/issues/1164)) ([dcc1e6b](https://github.com/feathersjs/feathers/commit/dcc1e6b)) - +- **package:** Move adapter tests into their own module ([#1164](https://github.com/feathersjs/feathers/issues/1164)) ([dcc1e6b](https://github.com/feathersjs/feathers/commit/dcc1e6b)) ### Features -* Add TypeScript definitions ([#1275](https://github.com/feathersjs/feathers/issues/1275)) ([9dd6713](https://github.com/feathersjs/feathers/commit/9dd6713)) -* Authentication v3 core server implementation ([#1205](https://github.com/feathersjs/feathers/issues/1205)) ([1bd7591](https://github.com/feathersjs/feathers/commit/1bd7591)) - +- Add TypeScript definitions ([#1275](https://github.com/feathersjs/feathers/issues/1275)) ([9dd6713](https://github.com/feathersjs/feathers/commit/9dd6713)) +- Authentication v3 core server implementation ([#1205](https://github.com/feathersjs/feathers/issues/1205)) ([1bd7591](https://github.com/feathersjs/feathers/commit/1bd7591)) ### BREAKING CHANGES -* **package:** Removes adapter tests from @feathersjs/adapter-commons - - - - +- **package:** Removes adapter tests from @feathersjs/adapter-commons ## [1.0.1](https://github.com/feathersjs/feathers/compare/@feathersjs/adapter-tests@1.0.0...@feathersjs/adapter-tests@1.0.1) (2019-01-10) - ### Bug Fixes -* Add test to make sure different id in adapter query works ([#1165](https://github.com/feathersjs/feathers/issues/1165)) ([0ba4580](https://github.com/feathersjs/feathers/commit/0ba4580)) - - - - +- Add test to make sure different id in adapter query works ([#1165](https://github.com/feathersjs/feathers/issues/1165)) ([0ba4580](https://github.com/feathersjs/feathers/commit/0ba4580)) # 1.0.0 (2019-01-10) - ### chore -* **package:** Move adapter tests into their own module ([#1164](https://github.com/feathersjs/feathers/issues/1164)) ([dcc1e6b](https://github.com/feathersjs/feathers/commit/dcc1e6b)) - +- **package:** Move adapter tests into their own module ([#1164](https://github.com/feathersjs/feathers/issues/1164)) ([dcc1e6b](https://github.com/feathersjs/feathers/commit/dcc1e6b)) ### BREAKING CHANGES -* **package:** Removes adapter tests from @feathersjs/adapter-commons +- **package:** Removes adapter tests from @feathersjs/adapter-commons diff --git a/packages/adapter-tests/LICENSE b/packages/adapter-tests/LICENSE index 3f395cc665..59604f46f3 100644 --- a/packages/adapter-tests/LICENSE +++ b/packages/adapter-tests/LICENSE @@ -1,6 +1,6 @@ The MIT License (MIT) -Copyright (c) 2021 Feathers +Copyright (c) 2022 Feathers Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated documentation files (the "Software"), to deal diff --git a/packages/adapter-tests/README.md b/packages/adapter-tests/README.md index b5f6fb18da..89769bcc1e 100644 --- a/packages/adapter-tests/README.md +++ b/packages/adapter-tests/README.md @@ -1,8 +1,8 @@ # Feathers Adapter Tests [![CI](https://github.com/feathersjs/feathers/workflows/Node.js%20CI/badge.svg)](https://github.com/feathersjs/feathers/actions?query=workflow%3A%22Node.js+CI%22) -[![Dependency Status](https://img.shields.io/david/feathersjs/feathers.svg?style=flat-square&path=packages/adapter-tests)](https://david-dm.org/feathersjs/feathers?path=packages/adapter-tests) [![Download Status](https://img.shields.io/npm/dm/@feathersjs/adapter-commons.svg?style=flat-square)](https://www.npmjs.com/package/@feathersjs/adapter-commons) +[![Discord](https://badgen.net/badge/icon/discord?icon=discord&label)](https://discord.gg/qa8kez8QBx) > Feathers shared database adapter test suite @@ -16,6 +16,6 @@ This is a repository that contains the test suite for the common database adapte ## License -Copyright (c) 2021 [Feathers contributors](https://github.com/feathersjs/feathers/graphs/contributors) +Copyright (c) 2022 [Feathers contributors](https://github.com/feathersjs/feathers/graphs/contributors) Licensed under the [MIT license](LICENSE). diff --git a/packages/adapter-tests/package.json b/packages/adapter-tests/package.json index 1015e5e970..c34e0ab0db 100644 --- a/packages/adapter-tests/package.json +++ b/packages/adapter-tests/package.json @@ -1,6 +1,6 @@ { "name": "@feathersjs/adapter-tests", - "version": "5.0.0-pre.16", + "version": "5.0.0-pre.31", "description": "Feathers shared database adapter test suite", "homepage": "https://feathersjs.com", "keywords": [ @@ -13,7 +13,8 @@ }, "repository": { "type": "git", - "url": "git://github.com/feathersjs/feathers.git" + "url": "git://github.com/feathersjs/feathers.git", + "directory": "packages/adapter-tests" }, "author": { "name": "Feathers contributor", @@ -27,12 +28,13 @@ "engines": { "node": ">= 12" }, - "main": "lib/index.js", + "main": "lib/", + "types": "lib/", "scripts": { "prepublish": "npm run compile", - "compile": "shx rm -rf lib/ && tsc", - "mocha": "mocha --config ../../.mocharc.json --recursive test/**.test.ts test/**/*.test.ts", - "test": "npm run compile && npm run mocha" + "pack": "npm pack --pack-destination ../cli/test/build", + "compile": "shx rm -rf lib/ && tsc && npm run pack", + "test": "mocha --config ../../.mocharc.json --recursive test/**.test.ts test/**/*.test.ts" }, "directories": { "lib": "lib" @@ -48,12 +50,12 @@ "access": "public" }, "devDependencies": { - "@types/mocha": "^9.0.0", - "@types/node": "^17.0.5", - "mocha": "^9.1.3", - "shx": "^0.3.3", - "ts-node": "^10.4.0", - "typescript": "^4.5.4" - }, - "gitHead": "f0cd227a82d159b528193bd33747c97684a48773" + "@types/mocha": "^10.0.0", + "@types/node": "^18.8.2", + "mocha": "^10.0.0", + "shx": "^0.3.4", + "ts-node": "^10.9.1", + "typescript": "^4.8.4" + }, + "gitHead": "4500dbeb8cea566678cf88b3313a88efd93a2ed9" } diff --git a/packages/adapter-tests/src/basic.ts b/packages/adapter-tests/src/basic.ts index 5353ac1dcd..de24e8c1ce 100644 --- a/packages/adapter-tests/src/basic.ts +++ b/packages/adapter-tests/src/basic.ts @@ -1,53 +1,74 @@ -import assert from 'assert'; +import assert from 'assert' +import { AdapterBasicTest } from './declarations' -export default (test: any, app: any, _errors: any, serviceName: string, idProp: string) => { +export default (test: AdapterBasicTest, app: any, _errors: any, serviceName: string, idProp: string) => { describe('Basic Functionality', () => { - let service: any; + let service: any beforeEach(() => { - service = app.service(serviceName); - }); + service = app.service(serviceName) + }) it('.id', () => { - assert.strictEqual(service.id, idProp, - 'id property is set to expected name' - ); - }); + assert.strictEqual(service.id, idProp, 'id property is set to expected name') + }) test('.options', () => { - assert.ok(service.options, 'Options are available in service.options'); - }); + assert.ok(service.options, 'Options are available in service.options') + }) test('.events', () => { - assert.ok(service.events.includes('testing'), - 'service.events is set and includes "testing"' - ); - }); + assert.ok(service.events.includes('testing'), 'service.events is set and includes "testing"') + }) describe('Raw Methods', () => { test('._get', () => { - assert.strictEqual(typeof service._get, 'function'); - }); + assert.strictEqual(typeof service._get, 'function') + }) test('._find', () => { - assert.strictEqual(typeof service._find, 'function'); - }); + assert.strictEqual(typeof service._find, 'function') + }) test('._create', () => { - assert.strictEqual(typeof service._create, 'function'); - }); + assert.strictEqual(typeof service._create, 'function') + }) test('._update', () => { - assert.strictEqual(typeof service._update, 'function'); - }); + assert.strictEqual(typeof service._update, 'function') + }) test('._patch', () => { - assert.strictEqual(typeof service._patch, 'function'); - }); + assert.strictEqual(typeof service._patch, 'function') + }) test('._remove', () => { - assert.strictEqual(typeof service._remove, 'function'); - }); - }); - }); -}; + assert.strictEqual(typeof service._remove, 'function') + }) + + test('.$get', () => { + assert.strictEqual(typeof service.$get, 'function') + }) + + test('.$find', () => { + assert.strictEqual(typeof service.$find, 'function') + }) + + test('.$create', () => { + assert.strictEqual(typeof service.$create, 'function') + }) + + test('.$update', () => { + assert.strictEqual(typeof service.$update, 'function') + }) + + test('.$patch', () => { + assert.strictEqual(typeof service.$patch, 'function') + }) + + test('.$remove', () => { + assert.strictEqual(typeof service.$remove, 'function') + }) + }) + }) +} diff --git a/packages/adapter-tests/src/declarations.ts b/packages/adapter-tests/src/declarations.ts new file mode 100644 index 0000000000..d3d4f7cf65 --- /dev/null +++ b/packages/adapter-tests/src/declarations.ts @@ -0,0 +1,90 @@ +export type AdapterTest = (name: AdapterTestName, runner: any) => void + +export type AdapterBasicTest = (name: AdapterBasicTestName, runner: any) => void +export type AdapterMethodsTest = (name: AdapterMethodsTestName, runner: any) => void +export type AdapterSyntaxTest = (name: AdapterSyntaxTestName, runner: any) => void + +export type AdapterTestName = AdapterBasicTestName | AdapterMethodsTestName | AdapterSyntaxTestName + +export type AdapterBasicTestName = + | '.id' + | '.options' + | '.events' + | '._get' + | '._find' + | '._create' + | '._update' + | '._patch' + | '._remove' + | '.$get' + | '.$find' + | '.$create' + | '.$update' + | '.$patch' + | '.$remove' + +export type AdapterMethodsTestName = + | '.get' + | '.get + $select' + | '.get + id + query' + | '.get + NotFound' + | '.get + id + query id' + | '.find' + | '.remove' + | '.remove + $select' + | '.remove + id + query' + | '.remove + multi' + | '.remove + multi no pagination' + | '.remove + id + query id' + | '.update' + | '.update + $select' + | '.update + id + query' + | '.update + NotFound' + | '.update + query + NotFound' + | '.update + id + query id' + | '.patch' + | '.patch + $select' + | '.patch + id + query' + | '.patch multiple' + | '.patch multiple no pagination' + | '.patch multi query same' + | '.patch multi query changed' + | '.patch + NotFound' + | '.patch + query + NotFound' + | '.patch + id + query id' + | '.create' + | '.create + $select' + | '.create multi' + | 'internal .find' + | 'internal .get' + | 'internal .create' + | 'internal .update' + | 'internal .patch' + | 'internal .remove' + +export type AdapterSyntaxTestName = + | '.find + equal' + | '.find + equal multiple' + | '.find + $sort' + | '.find + $sort + string' + | '.find + $limit' + | '.find + $limit 0' + | '.find + $skip' + | '.find + $select' + | '.find + $or' + | '.find + $in' + | '.find + $nin' + | '.find + $lt' + | '.find + $lte' + | '.find + $gt' + | '.find + $gte' + | '.find + $ne' + | '.find + $gt + $lt + $sort' + | '.find + $or nested + $sort' + | 'params.adapter + paginate' + | 'params.adapter + multi' + | '.find + paginate' + | '.find + paginate + query' + | '.find + paginate + $limit + $skip' + | '.find + paginate + $limit 0' + | '.find + paginate + params' diff --git a/packages/adapter-tests/src/index.ts b/packages/adapter-tests/src/index.ts index bfb0806e9c..bde34ce7e8 100644 --- a/packages/adapter-tests/src/index.ts +++ b/packages/adapter-tests/src/index.ts @@ -1,49 +1,57 @@ /* eslint-disable no-console */ -import basicTests from './basic'; -import methodTests from './methods'; -import syntaxTests from './syntax'; +import basicTests from './basic' +import { AdapterTestName } from './declarations' +import methodTests from './methods' +import syntaxTests from './syntax' -const adapterTests = (testNames: string[]) => { +const adapterTests = (testNames: AdapterTestName[]) => { return (app: any, errors: any, serviceName: any, idProp = 'id') => { if (!serviceName) { - throw new Error('You must pass a service name'); + throw new Error('You must pass a service name') } - const skippedTests: string[] = []; - const allTests: string[] = []; + const skippedTests: AdapterTestName[] = [] + const allTests: AdapterTestName[] = [] - const test = (name: string, runner: any) => { - const skip = !testNames.includes(name); - const its = skip ? it.skip : it; + const test = (name: AdapterTestName, runner: any) => { + const skip = !testNames.includes(name) + const its = skip ? it.skip : it if (skip) { - skippedTests.push(name); + skippedTests.push(name) } - allTests.push(name); + allTests.push(name) - its(name, runner); - }; + its(name, runner) + } describe(`Adapter tests for '${serviceName}' service with '${idProp}' id property`, () => { after(() => { - console.log('\n'); - testNames.forEach(name => { + testNames.forEach((name) => { if (!allTests.includes(name)) { - console.error(`WARNING: '${name}' test is not part of the test suite`); + console.error(`WARNING: '${name}' test is not part of the test suite`) } - }); + }) if (skippedTests.length) { - console.log(`\nSkipped the following ${skippedTests.length} Feathers adapter test(s) out of ${allTests.length} total:`); - console.log(JSON.stringify(skippedTests, null, ' ')); + console.log( + `\nSkipped the following ${skippedTests.length} Feathers adapter test(s) out of ${allTests.length} total:` + ) + console.log(JSON.stringify(skippedTests, null, ' ')) } - }); + }) + + basicTests(test, app, errors, serviceName, idProp) + methodTests(test, app, errors, serviceName, idProp) + syntaxTests(test, app, errors, serviceName, idProp) + }) + } +} + +export * from './declarations' - basicTests(test, app, errors, serviceName, idProp); - methodTests(test, app, errors, serviceName, idProp); - syntaxTests(test, app, errors, serviceName, idProp); - }); - }; -}; +export default adapterTests -export = adapterTests; +if (typeof module !== 'undefined') { + module.exports = Object.assign(adapterTests, module.exports) +} diff --git a/packages/adapter-tests/src/methods.ts b/packages/adapter-tests/src/methods.ts index 561336a447..9c1c72bff9 100644 --- a/packages/adapter-tests/src/methods.ts +++ b/packages/adapter-tests/src/methods.ts @@ -1,512 +1,622 @@ -import assert from 'assert'; +import assert from 'assert' +import { AdapterMethodsTest } from './declarations' -export default (test: any, app: any, _errors: any, serviceName: string, idProp: string) => { +export default (test: AdapterMethodsTest, app: any, _errors: any, serviceName: string, idProp: string) => { describe(' Methods', () => { - let doug: any; - let service: any; + let doug: any + let service: any beforeEach(async () => { - service = app.service(serviceName); + service = app.service(serviceName) doug = await app.service(serviceName).create({ name: 'Doug', age: 32 - }); - }); + }) + }) afterEach(async () => { try { - await app.service(serviceName).remove(doug[idProp]); + await app.service(serviceName).remove(doug[idProp]) } catch (error: any) {} - }); + }) describe('get', () => { test('.get', async () => { - const data = await service.get(doug[idProp]); + const data = await service.get(doug[idProp]) - assert.strictEqual(data[idProp].toString(), doug[idProp].toString(), - `${idProp} id matches` - ); - assert.strictEqual(data.name, 'Doug', 'data.name matches'); - assert.strictEqual(data.age, 32, 'data.age matches'); - }); + assert.strictEqual(data[idProp].toString(), doug[idProp].toString(), `${idProp} id matches`) + assert.strictEqual(data.name, 'Doug', 'data.name matches') + assert.strictEqual(data.age, 32, 'data.age matches') + }) test('.get + $select', async () => { const data = await service.get(doug[idProp], { - query: { $select: [ 'name' ] } - }); + query: { $select: ['name'] } + }) - assert.strictEqual(data[idProp].toString(), doug[idProp].toString(), - `${idProp} id property matches` - ); - assert.strictEqual(data.name, 'Doug', 'data.name matches'); - assert.ok(!data.age, 'data.age is falsy'); - }); + assert.strictEqual(data[idProp].toString(), doug[idProp].toString(), `${idProp} id property matches`) + assert.strictEqual(data.name, 'Doug', 'data.name matches') + assert.ok(!data.age, 'data.age is falsy') + }) test('.get + id + query', async () => { try { await service.get(doug[idProp], { query: { name: 'Tester' } - }); - throw new Error('Should never get here'); + }) + throw new Error('Should never get here') } catch (error: any) { - assert.strictEqual(error.name, 'NotFound', - 'Got a NotFound Feathers error' - ); + assert.strictEqual(error.name, 'NotFound', 'Got a NotFound Feathers error') } - }); + }) test('.get + NotFound', async () => { try { - await service.get('568225fbfe21222432e836ff'); - throw new Error('Should never get here'); + await service.get('568225fbfe21222432e836ff') + throw new Error('Should never get here') } catch (error: any) { - assert.strictEqual(error.name, 'NotFound', - 'Error is a NotFound Feathers error' - ); + assert.strictEqual(error.name, 'NotFound', 'Error is a NotFound Feathers error') } - }); + }) test('.get + id + query id', async () => { const alice = await service.create({ name: 'Alice', age: 12 - }); + }) try { await service.get(doug[idProp], { query: { [idProp]: alice[idProp] } - }); - throw new Error('Should never get here'); + }) + throw new Error('Should never get here') } catch (error: any) { - assert.strictEqual(error.name, 'NotFound', - 'Got a NotFound Feathers error' - ); + assert.strictEqual(error.name, 'NotFound', 'Got a NotFound Feathers error') } - await service.remove(alice[idProp]); - }); - }); + await service.remove(alice[idProp]) + }) + }) describe('find', () => { test('.find', async () => { - const data = await service.find(); + const data = await service.find() - assert.ok(Array.isArray(data), 'Data is an array'); - assert.strictEqual(data.length, 1, 'Got one entry'); - }); - }); + assert.ok(Array.isArray(data), 'Data is an array') + assert.strictEqual(data.length, 1, 'Got one entry') + }) + }) describe('remove', () => { test('.remove', async () => { - const data = await service.remove(doug[idProp]); + const data = await service.remove(doug[idProp]) - assert.strictEqual(data.name, 'Doug', 'data.name matches'); - }); + assert.strictEqual(data.name, 'Doug', 'data.name matches') + }) test('.remove + $select', async () => { const data = await service.remove(doug[idProp], { - query: { $select: [ 'name' ] } - }); + query: { $select: ['name'] } + }) - assert.strictEqual(data.name, 'Doug', 'data.name matches'); - assert.ok(!data.age, 'data.age is falsy'); - }); + assert.strictEqual(data.name, 'Doug', 'data.name matches') + assert.ok(!data.age, 'data.age is falsy') + }) test('.remove + id + query', async () => { try { await service.remove(doug[idProp], { query: { name: 'Tester' } - }); - throw new Error('Should never get here'); + }) + throw new Error('Should never get here') } catch (error: any) { - assert.strictEqual(error.name, 'NotFound', - 'Got a NotFound Feathers error' - ); + assert.strictEqual(error.name, 'NotFound', 'Got a NotFound Feathers error') } - }); + }) test('.remove + multi', async () => { try { - await service.remove(null); - throw new Error('Should never get here'); + await service.remove(null) + throw new Error('Should never get here') } catch (error: any) { - assert.strictEqual(error.name, 'MethodNotAllowed', + assert.strictEqual( + error.name, + 'MethodNotAllowed', 'Removing multiple without option set throws MethodNotAllowed' - ); + ) } - service.options.multi = [ 'remove' ]; + service.options.multi = ['remove'] - await service.create({ name: 'Dave', age: 29, created: true }); + await service.create({ name: 'Dave', age: 29, created: true }) await service.create({ name: 'David', age: 3, created: true - }); + }) const data = await service.remove(null, { query: { created: true } - }); + }) + + assert.strictEqual(data.length, 2) + + const names = data.map((person: any) => person.name) + + assert.ok(names.includes('Dave'), 'Dave removed') + assert.ok(names.includes('David'), 'David removed') + }) + + test('.remove + multi no pagination', async () => { + try { + await service.remove(doug[idProp]) + } catch (error: any) {} - assert.strictEqual(data.length, 2); + const count = 14 + const defaultPaginate = 10 - const names = data.map((person: any) => person.name); + assert.ok(count > defaultPaginate, 'count is bigger than default pagination') - assert.ok(names.includes('Dave'), 'Dave removed'); - assert.ok(names.includes('David'), 'David removed'); - }); + const multiBefore = service.options.multi + const paginateBefore = service.options.paginate + + try { + service.options.multi = true + service.options.paginate = { + default: defaultPaginate, + max: 100 + } + + const emptyItems = await service.find({ paginate: false }) + assert.strictEqual(emptyItems.length, 0, 'no items before') + + const createdItems = await service.create( + Array.from(Array(count)).map((_, i) => ({ + name: `name-${i}`, + age: 3, + created: true + })) + ) + assert.strictEqual(createdItems.length, count, `created ${count} items`) + + const foundItems = await service.find({ paginate: false }) + assert.strictEqual(foundItems.length, count, `created ${count} items`) + + const foundPaginatedItems = await service.find({}) + assert.strictEqual(foundPaginatedItems.data.length, defaultPaginate, 'found paginated items') + + const allItems = await service.remove(null, { + query: { created: true } + }) + + assert.strictEqual(allItems.length, count, `removed all ${count} items`) + } finally { + await service.remove(null, { + query: { created: true }, + paginate: false + }) + + service.options.multi = multiBefore + service.options.paginate = paginateBefore + } + }) test('.remove + id + query id', async () => { const alice = await service.create({ name: 'Alice', age: 12 - }); + }) try { await service.remove(doug[idProp], { query: { [idProp]: alice[idProp] } - }); - throw new Error('Should never get here'); + }) + throw new Error('Should never get here') } catch (error: any) { - assert.strictEqual(error.name, 'NotFound', - 'Got a NotFound Feathers error' - ); + assert.strictEqual(error.name, 'NotFound', 'Got a NotFound Feathers error') } - await service.remove(alice[idProp]); - }); - }); + await service.remove(alice[idProp]) + }) + }) describe('update', () => { test('.update', async () => { - const originalData = { [idProp]: doug[idProp], name: 'Dougler' }; - const originalCopy = Object.assign({}, originalData); + const originalData = { [idProp]: doug[idProp], name: 'Dougler' } + const originalCopy = Object.assign({}, originalData) - const data = await service.update(doug[idProp], originalData); + const data = await service.update(doug[idProp], originalData) - assert.deepStrictEqual(originalData, originalCopy, - 'data was not modified' - ); - assert.strictEqual(data[idProp].toString(), doug[idProp].toString(), - `${idProp} id matches` - ); - assert.strictEqual(data.name, 'Dougler', 'data.name matches'); - assert.ok(!data.age, 'data.age is falsy'); - }); + assert.deepStrictEqual(originalData, originalCopy, 'data was not modified') + assert.strictEqual(data[idProp].toString(), doug[idProp].toString(), `${idProp} id matches`) + assert.strictEqual(data.name, 'Dougler', 'data.name matches') + assert.ok(!data.age, 'data.age is falsy') + }) test('.update + $select', async () => { const originalData = { [idProp]: doug[idProp], name: 'Dougler', age: 10 - }; + } const data = await service.update(doug[idProp], originalData, { - query: { $select: [ 'name' ] } - }); + query: { $select: ['name'] } + }) - assert.strictEqual(data.name, 'Dougler', 'data.name matches'); - assert.ok(!data.age, 'data.age is falsy'); - }); + assert.strictEqual(data.name, 'Dougler', 'data.name matches') + assert.ok(!data.age, 'data.age is falsy') + }) test('.update + id + query', async () => { try { - await service.update(doug[idProp], { - name: 'Dougler' - }, { - query: { name: 'Tester' } - }); - throw new Error('Should never get here'); + await service.update( + doug[idProp], + { + name: 'Dougler' + }, + { + query: { name: 'Tester' } + } + ) + throw new Error('Should never get here') } catch (error: any) { - assert.strictEqual(error.name, 'NotFound', - 'Got a NotFound Feathers error' - ); + assert.strictEqual(error.name, 'NotFound', 'Got a NotFound Feathers error') } - }); + }) test('.update + NotFound', async () => { try { - await service.update('568225fbfe21222432e836ff', { name: 'NotFound' }); - throw new Error('Should never get here'); + await service.update('568225fbfe21222432e836ff', { + name: 'NotFound' + }) + throw new Error('Should never get here') } catch (error: any) { - assert.strictEqual(error.name, 'NotFound', - 'Error is a NotFound Feathers error' - ); + assert.strictEqual(error.name, 'NotFound', 'Error is a NotFound Feathers error') } - }); + }) test('.update + query + NotFound', async () => { - const dave = await service.create({ name: 'Dave' }); + const dave = await service.create({ name: 'Dave' }) try { - await service.update( - dave[idProp], - { name: 'UpdatedDave' }, - { query: { name: 'NotDave' } } - ); - throw new Error('Should never get here'); + await service.update(dave[idProp], { name: 'UpdatedDave' }, { query: { name: 'NotDave' } }) + throw new Error('Should never get here') } catch (error: any) { - assert.strictEqual(error.name, 'NotFound', - 'Error is a NotFound Feathers error' - ); + assert.strictEqual(error.name, 'NotFound', 'Error is a NotFound Feathers error') } - await service.remove(dave[idProp]); - }); + await service.remove(dave[idProp]) + }) test('.update + id + query id', async () => { const alice = await service.create({ name: 'Alice', age: 12 - }); + }) try { - await service.update(doug[idProp], { - name: 'Dougler', - age: 33 - }, { - query: { [idProp]: alice[idProp] } - }); - throw new Error('Should never get here'); + await service.update( + doug[idProp], + { + name: 'Dougler', + age: 33 + }, + { + query: { [idProp]: alice[idProp] } + } + ) + throw new Error('Should never get here') } catch (error: any) { - assert.strictEqual(error.name, 'NotFound', - 'Got a NotFound Feathers error' - ); + assert.strictEqual(error.name, 'NotFound', 'Got a NotFound Feathers error') } - await service.remove(alice[idProp]); - }); - }); + await service.remove(alice[idProp]) + }) + }) describe('patch', () => { test('.patch', async () => { - const originalData = { [idProp]: doug[idProp], name: 'PatchDoug' }; - const originalCopy = Object.assign({}, originalData); + const originalData = { [idProp]: doug[idProp], name: 'PatchDoug' } + const originalCopy = Object.assign({}, originalData) - const data = await service.patch(doug[idProp], originalData); + const data = await service.patch(doug[idProp], originalData) - assert.deepStrictEqual(originalData, originalCopy, - 'original data was not modified' - ); - assert.strictEqual(data[idProp].toString(), doug[idProp].toString(), - `${idProp} id matches` - ); - assert.strictEqual(data.name, 'PatchDoug', 'data.name matches'); - assert.strictEqual(data.age, 32, 'data.age matches'); - }); + assert.deepStrictEqual(originalData, originalCopy, 'original data was not modified') + assert.strictEqual(data[idProp].toString(), doug[idProp].toString(), `${idProp} id matches`) + assert.strictEqual(data.name, 'PatchDoug', 'data.name matches') + assert.strictEqual(data.age, 32, 'data.age matches') + }) test('.patch + $select', async () => { - const originalData = { [idProp]: doug[idProp], name: 'PatchDoug' }; + const originalData = { [idProp]: doug[idProp], name: 'PatchDoug' } const data = await service.patch(doug[idProp], originalData, { - query: { $select: [ 'name' ] } - }); + query: { $select: ['name'] } + }) - assert.strictEqual(data.name, 'PatchDoug', 'data.name matches'); - assert.ok(!data.age, 'data.age is falsy'); - }); + assert.strictEqual(data.name, 'PatchDoug', 'data.name matches') + assert.ok(!data.age, 'data.age is falsy') + }) test('.patch + id + query', async () => { try { - await service.patch(doug[idProp], { - name: 'id patched doug' - }, { - query: { name: 'Tester' } - }); - throw new Error('Should never get here'); + await service.patch( + doug[idProp], + { + name: 'id patched doug' + }, + { + query: { name: 'Tester' } + } + ) + throw new Error('Should never get here') } catch (error: any) { - assert.strictEqual(error.name, 'NotFound', - 'Got a NotFound Feathers error' - ); + assert.strictEqual(error.name, 'NotFound', 'Got a NotFound Feathers error') } - }); + }) test('.patch multiple', async () => { try { - await service.patch(null, {}); - throw new Error('Should never get here'); + await service.patch(null, {}) + throw new Error('Should never get here') } catch (error: any) { - assert.strictEqual(error.name, 'MethodNotAllowed', + assert.strictEqual( + error.name, + 'MethodNotAllowed', 'Removing multiple without option set throws MethodNotAllowed' - ); + ) } const params = { query: { created: true } - }; + } const dave = await service.create({ name: 'Dave', age: 29, created: true - }); + }) const david = await service.create({ name: 'David', age: 3, created: true - }); + }) + + service.options.multi = ['patch'] + + const data = await service.patch( + null, + { + age: 2 + }, + params + ) + + assert.strictEqual(data.length, 2, 'returned two entries') + assert.strictEqual(data[0].age, 2, 'First entry age was updated') + assert.strictEqual(data[1].age, 2, 'Second entry age was updated') + + await service.remove(dave[idProp]) + await service.remove(david[idProp]) + }) - service.options.multi = [ 'patch' ]; + test('.patch multiple no pagination', async () => { + try { + await service.remove(doug[idProp]) + } catch (error: any) {} + + const count = 14 + const defaultPaginate = 10 + + assert.ok(count > defaultPaginate, 'count is bigger than default pagination') - const data = await service.patch(null, { - age: 2 - }, params); + const multiBefore = service.options.multi + const paginateBefore = service.options.paginate - assert.strictEqual(data.length, 2, 'returned two entries'); - assert.strictEqual(data[0].age, 2, 'First entry age was updated'); - assert.strictEqual(data[1].age, 2, 'Second entry age was updated'); + let ids: any[] - await service.remove(dave[idProp]); - await service.remove(david[idProp]); - }); + try { + service.options.multi = true + service.options.paginate = { + default: defaultPaginate, + max: 100 + } + + const emptyItems = await service.find({ paginate: false }) + assert.strictEqual(emptyItems.length, 0, 'no items before') + + const createdItems = await service.create( + Array.from(Array(count)).map((_, i) => ({ + name: `name-${i}`, + age: 3, + created: true + })) + ) + assert.strictEqual(createdItems.length, count, `created ${count} items`) + ids = createdItems.map((item: any) => item[idProp]) + + const foundItems = await service.find({ paginate: false }) + assert.strictEqual(foundItems.length, count, `created ${count} items`) + + const foundPaginatedItems = await service.find({}) + assert.strictEqual(foundPaginatedItems.data.length, defaultPaginate, 'found paginated data') + + const allItems = await service.patch(null, { age: 4 }, { query: { created: true } }) + + assert.strictEqual(allItems.length, count, `patched all ${count} items`) + } finally { + service.options.multi = multiBefore + service.options.paginate = paginateBefore + if (ids) { + await Promise.all(ids.map((id) => service.remove(id))) + } + } + }) test('.patch multi query same', async () => { - const service = app.service(serviceName); + const service = app.service(serviceName) + const multiBefore = service.options.multi + + service.options.multi = true + const params = { query: { age: { $lt: 10 } } - }; + } const dave = await service.create({ name: 'Dave', age: 8, created: true - }); + }) const david = await service.create({ name: 'David', age: 4, created: true - }); + }) - const data = await service.patch(null, { - age: 2 - }, params); + const data = await service.patch( + null, + { + age: 2 + }, + params + ) + + assert.strictEqual(data.length, 2, 'returned two entries') + assert.strictEqual(data[0].age, 2, 'First entry age was updated') + assert.strictEqual(data[1].age, 2, 'Second entry age was updated') - assert.strictEqual(data.length, 2, 'returned two entries'); - assert.strictEqual(data[0].age, 2, 'First entry age was updated'); - assert.strictEqual(data[1].age, 2, 'Second entry age was updated'); + await service.remove(dave[idProp]) + await service.remove(david[idProp]) - await service.remove(dave[idProp]); - await service.remove(david[idProp]); - }); + service.options.multi = multiBefore + }) test('.patch multi query changed', async () => { - const service = app.service(serviceName); + const service = app.service(serviceName) + const multiBefore = service.options.multi + + service.options.multi = true + const params = { query: { age: 10 } - }; + } const dave = await service.create({ name: 'Dave', age: 10, created: true - }); + }) const david = await service.create({ name: 'David', age: 10, created: true - }); + }) - const data = await service.patch(null, { - age: 2 - }, params); + const data = await service.patch( + null, + { + age: 2 + }, + params + ) - assert.strictEqual(data.length, 2, 'returned two entries'); - assert.strictEqual(data[0].age, 2, 'First entry age was updated'); - assert.strictEqual(data[1].age, 2, 'Second entry age was updated'); + assert.strictEqual(data.length, 2, 'returned two entries') + assert.strictEqual(data[0].age, 2, 'First entry age was updated') + assert.strictEqual(data[1].age, 2, 'Second entry age was updated') - await service.remove(dave[idProp]); - await service.remove(david[idProp]); - }); + await service.remove(dave[idProp]) + await service.remove(david[idProp]) + + service.options.multi = multiBefore + }) test('.patch + NotFound', async () => { try { - await service.patch('568225fbfe21222432e836ff', { name: 'PatchDoug' }); - throw new Error('Should never get here'); + await service.patch('568225fbfe21222432e836ff', { + name: 'PatchDoug' + }) + throw new Error('Should never get here') } catch (error: any) { - assert.strictEqual(error.name, 'NotFound', - 'Error is a NotFound Feathers error' - ); + assert.strictEqual(error.name, 'NotFound', 'Error is a NotFound Feathers error') } - }); + }) test('.patch + query + NotFound', async () => { - const dave = await service.create({ name: 'Dave' }); + const dave = await service.create({ name: 'Dave' }) try { - await service.patch( - dave[idProp], - { name: 'PatchedDave' }, - { query: { name: 'NotDave' } } - ); - throw new Error('Should never get here'); + await service.patch(dave[idProp], { name: 'PatchedDave' }, { query: { name: 'NotDave' } }) + throw new Error('Should never get here') } catch (error: any) { - assert.strictEqual(error.name, 'NotFound', - 'Error is a NotFound Feathers error' - ); + assert.strictEqual(error.name, 'NotFound', 'Error is a NotFound Feathers error') } - await service.remove(dave[idProp]); - }); + await service.remove(dave[idProp]) + }) test('.patch + id + query id', async () => { const alice = await service.create({ name: 'Alice', age: 12 - }); + }) try { - await service.patch(doug[idProp], { - age: 33 - }, { - query: { [idProp]: alice[idProp] } - }); - throw new Error('Should never get here'); + await service.patch( + doug[idProp], + { + age: 33 + }, + { + query: { [idProp]: alice[idProp] } + } + ) + throw new Error('Should never get here') } catch (error: any) { - assert.strictEqual(error.name, 'NotFound', - 'Got a NotFound Feathers error' - ); + assert.strictEqual(error.name, 'NotFound', 'Got a NotFound Feathers error') } - await service.remove(alice[idProp]); - }); - }); + await service.remove(alice[idProp]) + }) + }) describe('create', () => { test('.create', async () => { const originalData = { name: 'Bill', age: 40 - }; - const originalCopy = Object.assign({}, originalData); + } + const originalCopy = Object.assign({}, originalData) - const data = await service.create(originalData); + const data = await service.create(originalData) - assert.deepStrictEqual(originalData, originalCopy, - 'original data was not modified' - ); - assert.ok(data instanceof Object, 'data is an object'); - assert.strictEqual(data.name, 'Bill', 'data.name matches'); + assert.deepStrictEqual(originalData, originalCopy, 'original data was not modified') + assert.ok(data instanceof Object, 'data is an object') + assert.strictEqual(data.name, 'Bill', 'data.name matches') - await service.remove(data[idProp]); - }); + await service.remove(data[idProp]) + }) test('.create + $select', async () => { const originalData = { name: 'William', age: 23 - }; + } const data = await service.create(originalData, { - query: { $select: [ 'name' ] } - }); + query: { $select: ['name'] } + }) - assert.strictEqual(data.name, 'William', 'data.name matches'); - assert.ok(!data.age, 'data.age is falsy'); + assert.strictEqual(data.name, 'William', 'data.name matches') + assert.ok(!data.age, 'data.age is falsy') - await service.remove(data[idProp]); - }); + await service.remove(data[idProp]) + }) test('.create multi', async () => { try { - await service.create([], {}); - throw new Error('Should never get here'); + await service.create([], {}) + throw new Error('Should never get here') } catch (error: any) { - assert.strictEqual(error.name, 'MethodNotAllowed', + assert.strictEqual( + error.name, + 'MethodNotAllowed', 'Removing multiple without option set throws MethodNotAllowed' - ); + ) } const items = [ @@ -518,83 +628,77 @@ export default (test: any, app: any, _errors: any, serviceName: string, idProp: name: 'Herald', age: 18 } - ]; + ] - service.options.multi = [ 'create', 'patch' ]; + service.options.multi = ['create', 'patch'] - const data = await service.create(items); + const data = await service.create(items) - assert.ok(Array.isArray(data), 'data is an array'); - assert.ok(typeof data[0][idProp] !== 'undefined', 'id is set'); - assert.strictEqual(data[0].name, 'Gerald', 'first name matches'); - assert.ok(typeof data[1][idProp] !== 'undefined', 'id is set'); - assert.strictEqual(data[1].name, 'Herald', 'second name macthes'); + assert.ok(Array.isArray(data), 'data is an array') + assert.ok(typeof data[0][idProp] !== 'undefined', 'id is set') + assert.strictEqual(data[0].name, 'Gerald', 'first name matches') + assert.ok(typeof data[1][idProp] !== 'undefined', 'id is set') + assert.strictEqual(data[1].name, 'Herald', 'second name macthes') - await service.remove(data[0][idProp]); - await service.remove(data[1][idProp]); - }); - }); + await service.remove(data[0][idProp]) + await service.remove(data[1][idProp]) + }) + }) - describe('doesn\'t call public methods internally', () => { - let throwing: any; + describe("doesn't call public methods internally", () => { + let throwing: any before(() => { throwing = Object.assign(Object.create(app.service(serviceName)), { - get store () { - return app.service(serviceName).store; + get store() { + return app.service(serviceName).store }, - find () { - throw new Error('find method called'); + find() { + throw new Error('find method called') }, - get () { - throw new Error('get method called'); + get() { + throw new Error('get method called') }, - create () { - throw new Error('create method called'); + create() { + throw new Error('create method called') }, - update () { - throw new Error('update method called'); + update() { + throw new Error('update method called') }, - patch () { - throw new Error('patch method called'); + patch() { + throw new Error('patch method called') }, - remove () { - throw new Error('remove method called'); + remove() { + throw new Error('remove method called') } - }); - }); + }) + }) - test('internal .find', () => app.service(serviceName).find.call(throwing)); + test('internal .find', () => app.service(serviceName).find.call(throwing)) - test('internal .get', () => - service.get.call(throwing, doug[idProp]) - ); + test('internal .get', () => service.get.call(throwing, doug[idProp])) test('internal .create', async () => { const bob = await service.create.call(throwing, { name: 'Bob', age: 25 - }); + }) - await service.remove(bob[idProp]); - }); + await service.remove(bob[idProp]) + }) test('internal .update', () => service.update.call(throwing, doug[idProp], { name: 'Dougler' - }) - ); + })) test('internal .patch', () => service.patch.call(throwing, doug[idProp], { name: 'PatchDoug' - }) - ); - - test('internal .remove', () => - service.remove.call(throwing, doug[idProp]) - ); - }); - }); -}; + })) + + test('internal .remove', () => service.remove.call(throwing, doug[idProp])) + }) + }) +} diff --git a/packages/adapter-tests/src/syntax.ts b/packages/adapter-tests/src/syntax.ts index f6fe1b0e15..3dd73821e9 100644 --- a/packages/adapter-tests/src/syntax.ts +++ b/packages/adapter-tests/src/syntax.ts @@ -1,50 +1,51 @@ -import assert from 'assert'; +import assert from 'assert' +import { AdapterSyntaxTest } from './declarations' -export default (test: any, app: any, _errors: any, serviceName: string, idProp: string) => { +export default (test: AdapterSyntaxTest, app: any, _errors: any, serviceName: string, idProp: string) => { describe('Query Syntax', () => { - let bob: any; - let alice: any; - let doug: any; - let service: any; + let bob: any + let alice: any + let doug: any + let service: any beforeEach(async () => { - service = app.service(serviceName); + service = app.service(serviceName) bob = await app.service(serviceName).create({ name: 'Bob', age: 25 - }); + }) doug = await app.service(serviceName).create({ name: 'Doug', age: 32 - }); + }) alice = await app.service(serviceName).create({ name: 'Alice', age: 19 - }); - }); + }) + }) afterEach(async () => { - await service.remove(bob[idProp]); - await service.remove(alice[idProp]); - await service.remove(doug[idProp]); - }); + await service.remove(bob[idProp]) + await service.remove(alice[idProp]) + await service.remove(doug[idProp]) + }) test('.find + equal', async () => { - const params = { query: { name: 'Alice' } }; - const data = await service.find(params); + const params = { query: { name: 'Alice' } } + const data = await service.find(params) - assert.ok(Array.isArray(data)); - assert.strictEqual(data.length, 1); - assert.strictEqual(data[0].name, 'Alice'); - }); + assert.ok(Array.isArray(data)) + assert.strictEqual(data.length, 1) + assert.strictEqual(data[0].name, 'Alice') + }) test('.find + equal multiple', async () => { const data = await service.find({ query: { name: 'Alice', age: 20 } - }); + }) - assert.strictEqual(data.length, 0); - }); + assert.strictEqual(data.length, 0) + }) describe('special filters', () => { test('.find + $sort', async () => { @@ -52,57 +53,57 @@ export default (test: any, app: any, _errors: any, serviceName: string, idProp: query: { $sort: { name: 1 } } - }); + }) - assert.strictEqual(data.length, 3); - assert.strictEqual(data[0].name, 'Alice'); - assert.strictEqual(data[1].name, 'Bob'); - assert.strictEqual(data[2].name, 'Doug'); + assert.strictEqual(data.length, 3) + assert.strictEqual(data[0].name, 'Alice') + assert.strictEqual(data[1].name, 'Bob') + assert.strictEqual(data[2].name, 'Doug') data = await service.find({ query: { $sort: { name: -1 } } - }); + }) - assert.strictEqual(data.length, 3); - assert.strictEqual(data[0].name, 'Doug'); - assert.strictEqual(data[1].name, 'Bob'); - assert.strictEqual(data[2].name, 'Alice'); - }); + assert.strictEqual(data.length, 3) + assert.strictEqual(data[0].name, 'Doug') + assert.strictEqual(data[1].name, 'Bob') + assert.strictEqual(data[2].name, 'Alice') + }) test('.find + $sort + string', async () => { const data = await service.find({ query: { $sort: { name: '1' } } - }); + }) - assert.strictEqual(data.length, 3); - assert.strictEqual(data[0].name, 'Alice'); - assert.strictEqual(data[1].name, 'Bob'); - assert.strictEqual(data[2].name, 'Doug'); - }); + assert.strictEqual(data.length, 3) + assert.strictEqual(data[0].name, 'Alice') + assert.strictEqual(data[1].name, 'Bob') + assert.strictEqual(data[2].name, 'Doug') + }) test('.find + $limit', async () => { const data = await service.find({ query: { $limit: 2 } - }); + }) - assert.strictEqual(data.length, 2); - }); + assert.strictEqual(data.length, 2) + }) test('.find + $limit 0', async () => { const data = await service.find({ query: { $limit: 0 } - }); + }) - assert.strictEqual(data.length, 0); - }); + assert.strictEqual(data.length, 0) + }) test('.find + $skip', async () => { const data = await service.find({ @@ -110,12 +111,12 @@ export default (test: any, app: any, _errors: any, serviceName: string, idProp: $sort: { name: 1 }, $skip: 1 } - }); + }) - assert.strictEqual(data.length, 2); - assert.strictEqual(data[0].name, 'Bob'); - assert.strictEqual(data[1].name, 'Doug'); - }); + assert.strictEqual(data.length, 2) + assert.strictEqual(data[0].name, 'Bob') + assert.strictEqual(data[1].name, 'Doug') + }) test('.find + $select', async () => { const data = await service.find({ @@ -123,28 +124,25 @@ export default (test: any, app: any, _errors: any, serviceName: string, idProp: name: 'Alice', $select: ['name'] } - }); + }) - assert.strictEqual(data.length, 1); - assert.strictEqual(data[0].name, 'Alice'); - assert.strictEqual(data[0].age, undefined); - }); + assert.strictEqual(data.length, 1) + assert.strictEqual(data[0].name, 'Alice') + assert.strictEqual(data[0].age, undefined) + }) test('.find + $or', async () => { const data = await service.find({ query: { - $or: [ - { name: 'Alice' }, - { name: 'Bob' } - ], + $or: [{ name: 'Alice' }, { name: 'Bob' }], $sort: { name: 1 } } - }); + }) - assert.strictEqual(data.length, 2); - assert.strictEqual(data[0].name, 'Alice'); - assert.strictEqual(data[1].name, 'Bob'); - }); + assert.strictEqual(data.length, 2) + assert.strictEqual(data[0].name, 'Alice') + assert.strictEqual(data[1].name, 'Bob') + }) test('.find + $in', async () => { const data = await service.find({ @@ -154,25 +152,25 @@ export default (test: any, app: any, _errors: any, serviceName: string, idProp: }, $sort: { name: 1 } } - }); + }) - assert.strictEqual(data.length, 2); - assert.strictEqual(data[0].name, 'Alice'); - assert.strictEqual(data[1].name, 'Bob'); - }); + assert.strictEqual(data.length, 2) + assert.strictEqual(data[0].name, 'Alice') + assert.strictEqual(data[1].name, 'Bob') + }) test('.find + $nin', async () => { const data = await service.find({ query: { name: { - $nin: [ 'Alice', 'Bob' ] + $nin: ['Alice', 'Bob'] } } - }); + }) - assert.strictEqual(data.length, 1); - assert.strictEqual(data[0].name, 'Doug'); - }); + assert.strictEqual(data.length, 1) + assert.strictEqual(data[0].name, 'Doug') + }) test('.find + $lt', async () => { const data = await service.find({ @@ -181,10 +179,10 @@ export default (test: any, app: any, _errors: any, serviceName: string, idProp: $lt: 30 } } - }); + }) - assert.strictEqual(data.length, 2); - }); + assert.strictEqual(data.length, 2) + }) test('.find + $lte', async () => { const data = await service.find({ @@ -193,10 +191,10 @@ export default (test: any, app: any, _errors: any, serviceName: string, idProp: $lte: 25 } } - }); + }) - assert.strictEqual(data.length, 2); - }); + assert.strictEqual(data.length, 2) + }) test('.find + $gt', async () => { const data = await service.find({ @@ -205,10 +203,10 @@ export default (test: any, app: any, _errors: any, serviceName: string, idProp: $gt: 30 } } - }); + }) - assert.strictEqual(data.length, 1); - }); + assert.strictEqual(data.length, 1) + }) test('.find + $gte', async () => { const data = await service.find({ @@ -217,10 +215,10 @@ export default (test: any, app: any, _errors: any, serviceName: string, idProp: $gte: 25 } } - }); + }) - assert.strictEqual(data.length, 2); - }); + assert.strictEqual(data.length, 2) + }) test('.find + $ne', async () => { const data = await service.find({ @@ -229,11 +227,11 @@ export default (test: any, app: any, _errors: any, serviceName: string, idProp: $ne: 25 } } - }); + }) - assert.strictEqual(data.length, 2); - }); - }); + assert.strictEqual(data.length, 2) + }) + }) test('.find + $gt + $lt + $sort', async () => { const params = { @@ -244,14 +242,14 @@ export default (test: any, app: any, _errors: any, serviceName: string, idProp: }, $sort: { name: 1 } } - }; + } - const data = await service.find(params); + const data = await service.find(params) - assert.strictEqual(data.length, 2); - assert.strictEqual(data[0].name, 'Alice'); - assert.strictEqual(data[1].name, 'Bob'); - }); + assert.strictEqual(data.length, 2) + assert.strictEqual(data[0].name, 'Alice') + assert.strictEqual(data[1].name, 'Bob') + }) test('.find + $or nested + $sort', async () => { const params = { @@ -267,14 +265,14 @@ export default (test: any, app: any, _errors: any, serviceName: string, idProp: ], $sort: { name: 1 } } - }; + } - const data = await service.find(params); + const data = await service.find(params) - assert.strictEqual(data.length, 2); - assert.strictEqual(data[0].name, 'Alice'); - assert.strictEqual(data[1].name, 'Doug'); - }); + assert.strictEqual(data.length, 2) + assert.strictEqual(data[0].name, 'Alice') + assert.strictEqual(data[1].name, 'Doug') + }) describe('params.adapter', () => { test('params.adapter + paginate', async () => { @@ -282,11 +280,11 @@ export default (test: any, app: any, _errors: any, serviceName: string, idProp: adapter: { paginate: { default: 3 } } - }); - - assert.strictEqual(page.limit, 3); - assert.strictEqual(page.skip, 0); - }); + }) + + assert.strictEqual(page.limit, 3) + assert.strictEqual(page.skip, 0) + }) test('params.adapter + multi', async () => { const items = [ @@ -298,46 +296,46 @@ export default (test: any, app: any, _errors: any, serviceName: string, idProp: name: 'Harald', age: 24 } - ]; + ] const multiParams = { adapter: { multi: ['create'] } - }; - const users = await service.create(items, multiParams); + } + const users = await service.create(items, multiParams) + + assert.strictEqual(users.length, 2) - assert.strictEqual(users.length, 2); - - await service.remove(users[0][idProp]); - await service.remove(users[1][idProp]); + await service.remove(users[0][idProp]) + await service.remove(users[1][idProp]) await assert.rejects(() => service.patch(null, { age: 2 }, multiParams), { message: 'Can not patch multiple entries' - }); - }); - }); + }) + }) + }) describe('paginate', function () { beforeEach(() => { service.options.paginate = { default: 1, max: 2 - }; - }); + } + }) afterEach(() => { - service.options.paginate = {}; - }); + service.options.paginate = {} + }) test('.find + paginate', async () => { const page = await service.find({ query: { $sort: { name: -1 } } - }); + }) - assert.strictEqual(page.total, 3); - assert.strictEqual(page.limit, 1); - assert.strictEqual(page.skip, 0); - assert.strictEqual(page.data[0].name, 'Doug'); - }); + assert.strictEqual(page.total, 3) + assert.strictEqual(page.limit, 1) + assert.strictEqual(page.skip, 0) + assert.strictEqual(page.data[0].name, 'Doug') + }) test('.find + paginate + query', async () => { const page = await service.find({ @@ -345,13 +343,13 @@ export default (test: any, app: any, _errors: any, serviceName: string, idProp: $sort: { name: -1 }, name: 'Doug' } - }); + }) - assert.strictEqual(page.total, 1); - assert.strictEqual(page.limit, 1); - assert.strictEqual(page.skip, 0); - assert.strictEqual(page.data[0].name, 'Doug'); - }); + assert.strictEqual(page.total, 1) + assert.strictEqual(page.limit, 1) + assert.strictEqual(page.skip, 0) + assert.strictEqual(page.data[0].name, 'Doug') + }) test('.find + paginate + $limit + $skip', async () => { const params = { @@ -360,37 +358,37 @@ export default (test: any, app: any, _errors: any, serviceName: string, idProp: $limit: 4, $sort: { name: -1 } } - }; + } - const page = await service.find(params); + const page = await service.find(params) - assert.strictEqual(page.total, 3); - assert.strictEqual(page.limit, 2); - assert.strictEqual(page.skip, 1); - assert.strictEqual(page.data[0].name, 'Bob'); - assert.strictEqual(page.data[1].name, 'Alice'); - }); + assert.strictEqual(page.total, 3) + assert.strictEqual(page.limit, 2) + assert.strictEqual(page.skip, 1) + assert.strictEqual(page.data[0].name, 'Bob') + assert.strictEqual(page.data[1].name, 'Alice') + }) test('.find + paginate + $limit 0', async () => { const page = await service.find({ query: { $limit: 0 } - }); + }) - assert.strictEqual(page.total, 3); - assert.strictEqual(page.data.length, 0); - }); + assert.strictEqual(page.total, 3) + assert.strictEqual(page.data.length, 0) + }) test('.find + paginate + params', async () => { - const page = await service.find({ paginate: { default: 3 } }); + const page = await service.find({ paginate: { default: 3 } }) - assert.strictEqual(page.limit, 3); - assert.strictEqual(page.skip, 0); + assert.strictEqual(page.limit, 3) + assert.strictEqual(page.skip, 0) - const results = await service.find({ paginate: false }); + const results = await service.find({ paginate: false }) - assert.ok(Array.isArray(results)); - assert.strictEqual(results.length, 3); - }); - }); - }); -}; + assert.ok(Array.isArray(results)) + assert.strictEqual(results.length, 3) + }) + }) + }) +} diff --git a/packages/adapter-tests/test/index.test.ts b/packages/adapter-tests/test/index.test.ts index 725c7cae49..fc4a3ad0ec 100644 --- a/packages/adapter-tests/test/index.test.ts +++ b/packages/adapter-tests/test/index.test.ts @@ -1,5 +1,5 @@ -import { strict as assert } from 'assert'; -import adapterTests from '../src'; +import { strict as assert } from 'assert' +import adapterTests from '../src' const testSuite = adapterTests([ '.events', @@ -9,6 +9,12 @@ const testSuite = adapterTests([ '._update', '._patch', '._remove', + '.$get', + '.$find', + '.$create', + '.$update', + '.$patch', + '.$remove', '.get', '.get + $select', '.get + id + query', @@ -18,6 +24,7 @@ const testSuite = adapterTests([ '.remove + $select', '.remove + id + query', '.remove + multi', + '.remove + multi no pagination', '.update', '.update + $select', '.update + id + query', @@ -26,7 +33,9 @@ const testSuite = adapterTests([ '.patch + $select', '.patch + id + query', '.patch multiple', - '.patch multi query', + '.patch multiple no pagination', + '.patch multi query changed', + '.patch multi query same', '.patch + NotFound', '.create', '.create + $select', @@ -63,14 +72,14 @@ const testSuite = adapterTests([ '.remove + id + query id', '.update + id + query id', '.patch + id + query id' -]); +]) describe('Feathers Memory Service', () => { it('loads the test suite', () => { - assert.ok(typeof testSuite === 'function'); - }); + assert.ok(typeof testSuite === 'function') + }) it('exports as CommonJS', () => { - assert.equal(typeof require('../lib'), 'function'); - }); -}); + assert.equal(typeof require('../lib'), 'function') + }) +}) diff --git a/packages/authentication-client/CHANGELOG.md b/packages/authentication-client/CHANGELOG.md index f260845e2d..693eab8697 100644 --- a/packages/authentication-client/CHANGELOG.md +++ b/packages/authentication-client/CHANGELOG.md @@ -3,634 +3,438 @@ All notable changes to this project will be documented in this file. See [Conventional Commits](https://conventionalcommits.org) for commit guidelines. -# [5.0.0-pre.16](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.15...v5.0.0-pre.16) (2022-01-12) +# [5.0.0-pre.31](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.30...v5.0.0-pre.31) (2022-10-12) **Note:** Version bump only for package @feathersjs/authentication-client +# [5.0.0-pre.30](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.29...v5.0.0-pre.30) (2022-10-07) +### Features +- **core:** Allow to unregister services at runtime ([#2756](https://github.com/feathersjs/feathers/issues/2756)) ([d16601f](https://github.com/feathersjs/feathers/commit/d16601f2277dca5357866ffdefba2a611f6dc7fa)) +# [5.0.0-pre.29](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.28...v5.0.0-pre.29) (2022-09-16) -# [5.0.0-pre.15](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.14...v5.0.0-pre.15) (2021-11-27) +**Note:** Version bump only for package @feathersjs/authentication-client +# [5.0.0-pre.28](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.27...v5.0.0-pre.28) (2022-08-03) ### Bug Fixes -* **typescript:** Overall typing improvements ([#2478](https://github.com/feathersjs/feathers/issues/2478)) ([b8eb804](https://github.com/feathersjs/feathers/commit/b8eb804158556d9651a8607e3c3fda15e0bfd110)) - +- **authentication-client:** Properly handle missing token error ([#2700](https://github.com/feathersjs/feathers/issues/2700)) ([160746e](https://github.com/feathersjs/feathers/commit/160746e2bceb465fd1b6a003415f8ab38daba521)) +- **cli:** Improve generated application and client ([#2701](https://github.com/feathersjs/feathers/issues/2701)) ([bd55ffb](https://github.com/feathersjs/feathers/commit/bd55ffb812e89bf215f4515e7f137656ea888c3f)) +# [5.0.0-pre.27](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.26...v5.0.0-pre.27) (2022-07-13) +### Bug Fixes +- **authentication-client:** Ensure reAuthenticate works in parallel with other requests ([#2690](https://github.com/feathersjs/feathers/issues/2690)) ([41b3761](https://github.com/feathersjs/feathers/commit/41b376106b47e2f40a8914db7a5ed2935e070c08)) -# [5.0.0-pre.14](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.13...v5.0.0-pre.14) (2021-10-13) +# [5.0.0-pre.26](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.25...v5.0.0-pre.26) (2022-06-22) **Note:** Version bump only for package @feathersjs/authentication-client +# [5.0.0-pre.25](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.24...v5.0.0-pre.25) (2022-06-22) +**Note:** Version bump only for package @feathersjs/authentication-client - - -# [5.0.0-pre.13](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.12...v5.0.0-pre.13) (2021-10-13) +# [5.0.0-pre.24](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.23...v5.0.0-pre.24) (2022-06-21) **Note:** Version bump only for package @feathersjs/authentication-client +# [5.0.0-pre.23](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.22...v5.0.0-pre.23) (2022-06-06) +**Note:** Version bump only for package @feathersjs/authentication-client +# [5.0.0-pre.22](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.21...v5.0.0-pre.22) (2022-05-24) +**Note:** Version bump only for package @feathersjs/authentication-client -# [5.0.0-pre.12](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.11...v5.0.0-pre.12) (2021-10-12) +# [5.0.0-pre.21](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.20...v5.0.0-pre.21) (2022-05-23) **Note:** Version bump only for package @feathersjs/authentication-client +# [5.0.0-pre.20](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.19...v5.0.0-pre.20) (2022-05-04) +### Bug Fixes +- **dependencies:** Lock monorepo package version numbers ([#2623](https://github.com/feathersjs/feathers/issues/2623)) ([5640c10](https://github.com/feathersjs/feathers/commit/5640c1020cc139994e695d658c08bad3494db507)) - -# [5.0.0-pre.11](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.10...v5.0.0-pre.11) (2021-10-06) +# [5.0.0-pre.19](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.18...v5.0.0-pre.19) (2022-05-01) **Note:** Version bump only for package @feathersjs/authentication-client +# [5.0.0-pre.18](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.17...v5.0.0-pre.18) (2022-04-11) +**Note:** Version bump only for package @feathersjs/authentication-client +# [5.0.0-pre.17](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.16...v5.0.0-pre.17) (2022-02-15) +**Note:** Version bump only for package @feathersjs/authentication-client -# [5.0.0-pre.10](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.9...v5.0.0-pre.10) (2021-09-19) +# [5.0.0-pre.16](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.15...v5.0.0-pre.16) (2022-01-12) **Note:** Version bump only for package @feathersjs/authentication-client +# [5.0.0-pre.15](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.14...v5.0.0-pre.15) (2021-11-27) +### Bug Fixes +- **typescript:** Overall typing improvements ([#2478](https://github.com/feathersjs/feathers/issues/2478)) ([b8eb804](https://github.com/feathersjs/feathers/commit/b8eb804158556d9651a8607e3c3fda15e0bfd110)) - -# [5.0.0-pre.9](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.8...v5.0.0-pre.9) (2021-08-09) +# [5.0.0-pre.14](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.13...v5.0.0-pre.14) (2021-10-13) **Note:** Version bump only for package @feathersjs/authentication-client +# [5.0.0-pre.13](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.12...v5.0.0-pre.13) (2021-10-13) +**Note:** Version bump only for package @feathersjs/authentication-client - - -# [5.0.0-pre.8](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.7...v5.0.0-pre.8) (2021-08-09) +# [5.0.0-pre.12](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.11...v5.0.0-pre.12) (2021-10-12) **Note:** Version bump only for package @feathersjs/authentication-client +# [5.0.0-pre.11](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.10...v5.0.0-pre.11) (2021-10-06) +**Note:** Version bump only for package @feathersjs/authentication-client +# [5.0.0-pre.10](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.9...v5.0.0-pre.10) (2021-09-19) +**Note:** Version bump only for package @feathersjs/authentication-client -# [5.0.0-pre.7](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.6...v5.0.0-pre.7) (2021-08-09) +# [5.0.0-pre.9](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.8...v5.0.0-pre.9) (2021-08-09) **Note:** Version bump only for package @feathersjs/authentication-client +# [5.0.0-pre.8](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.7...v5.0.0-pre.8) (2021-08-09) +**Note:** Version bump only for package @feathersjs/authentication-client +# [5.0.0-pre.7](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.6...v5.0.0-pre.7) (2021-08-09) +**Note:** Version bump only for package @feathersjs/authentication-client # [5.0.0-pre.6](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.5...v5.0.0-pre.6) (2021-08-08) **Note:** Version bump only for package @feathersjs/authentication-client - - - - # [5.0.0-pre.5](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.4...v5.0.0-pre.5) (2021-06-23) - ### Bug Fixes -* **hooks:** Migrate built-in hooks and allow backwards compatibility ([#2358](https://github.com/feathersjs/feathers/issues/2358)) ([759c5a1](https://github.com/feathersjs/feathers/commit/759c5a19327a731af965c3604119393b3d09a406)) -* **koa:** Use extended query parser for compatibility ([#2397](https://github.com/feathersjs/feathers/issues/2397)) ([b2944ba](https://github.com/feathersjs/feathers/commit/b2944bac3ec6d5ecc80dc518cd4e58093692db74)) - +- **hooks:** Migrate built-in hooks and allow backwards compatibility ([#2358](https://github.com/feathersjs/feathers/issues/2358)) ([759c5a1](https://github.com/feathersjs/feathers/commit/759c5a19327a731af965c3604119393b3d09a406)) +- **koa:** Use extended query parser for compatibility ([#2397](https://github.com/feathersjs/feathers/issues/2397)) ([b2944ba](https://github.com/feathersjs/feathers/commit/b2944bac3ec6d5ecc80dc518cd4e58093692db74)) ### Features -* **adapter-commons:** Add support for params.adapter option and move memory adapter to @feathersjs/memory ([#2367](https://github.com/feathersjs/feathers/issues/2367)) ([a43e7da](https://github.com/feathersjs/feathers/commit/a43e7da22b6b981a96d1321736ea9a0cb924fb4f)) - - - - +- **adapter-commons:** Add support for params.adapter option and move memory adapter to @feathersjs/memory ([#2367](https://github.com/feathersjs/feathers/issues/2367)) ([a43e7da](https://github.com/feathersjs/feathers/commit/a43e7da22b6b981a96d1321736ea9a0cb924fb4f)) # [5.0.0-pre.4](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.3...v5.0.0-pre.4) (2021-05-13) **Note:** Version bump only for package @feathersjs/authentication-client - - - - # [5.0.0-pre.3](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.2...v5.0.0-pre.3) (2021-04-21) - ### Bug Fixes -* **typescript:** Improve TypeScript backwards compatibility ([#2310](https://github.com/feathersjs/feathers/issues/2310)) ([f33be73](https://github.com/feathersjs/feathers/commit/f33be73fc46a533efb15df9aab0658e3240d3897)) - +- **typescript:** Improve TypeScript backwards compatibility ([#2310](https://github.com/feathersjs/feathers/issues/2310)) ([f33be73](https://github.com/feathersjs/feathers/commit/f33be73fc46a533efb15df9aab0658e3240d3897)) ### Features -* **dependencies:** Remove direct debug dependency ([#2296](https://github.com/feathersjs/feathers/issues/2296)) ([501d416](https://github.com/feathersjs/feathers/commit/501d4164d30c6a126906dc640cdfdc82207ba34a)) - - - - +- **dependencies:** Remove direct debug dependency ([#2296](https://github.com/feathersjs/feathers/issues/2296)) ([501d416](https://github.com/feathersjs/feathers/commit/501d4164d30c6a126906dc640cdfdc82207ba34a)) # [5.0.0-pre.2](https://github.com/feathersjs/feathers/compare/v5.0.0-beta.1...v5.0.0-pre.2) (2021-04-06) **Note:** Version bump only for package @feathersjs/authentication-client - - - - # [5.0.0-beta.1](https://github.com/feathersjs/feathers/compare/v5.0.0-beta.0...v5.0.0-beta.1) (2021-04-03) **Note:** Version bump only for package @feathersjs/authentication-client - - - - # [5.0.0-beta.0](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.1...v5.0.0-beta.0) (2021-03-28) - ### Bug Fixes -* Update Grant usage and other dependencies ([#2264](https://github.com/feathersjs/feathers/issues/2264)) ([7b0f8fa](https://github.com/feathersjs/feathers/commit/7b0f8fad252419ed0ad0bf259cdf3104d322ab60)) - +- Update Grant usage and other dependencies ([#2264](https://github.com/feathersjs/feathers/issues/2264)) ([7b0f8fa](https://github.com/feathersjs/feathers/commit/7b0f8fad252419ed0ad0bf259cdf3104d322ab60)) ### Features -* Application service types default to any ([#1566](https://github.com/feathersjs/feathers/issues/1566)) ([d93ba9a](https://github.com/feathersjs/feathers/commit/d93ba9a17edd20d3397bb00f4f6e82e804e42ed6)) -* Feathers v5 core refactoring and features ([#2255](https://github.com/feathersjs/feathers/issues/2255)) ([2dafb7c](https://github.com/feathersjs/feathers/commit/2dafb7ce14ba57406aeec13d10ca45b1e709bee9)) -* **authentication-client:** Throw separate OauthError in authentication client ([#2189](https://github.com/feathersjs/feathers/issues/2189)) ([fa45ec5](https://github.com/feathersjs/feathers/commit/fa45ec520b21834e103e6fe4200b06dced56c0e6)) - - - - +- Application service types default to any ([#1566](https://github.com/feathersjs/feathers/issues/1566)) ([d93ba9a](https://github.com/feathersjs/feathers/commit/d93ba9a17edd20d3397bb00f4f6e82e804e42ed6)) +- Feathers v5 core refactoring and features ([#2255](https://github.com/feathersjs/feathers/issues/2255)) ([2dafb7c](https://github.com/feathersjs/feathers/commit/2dafb7ce14ba57406aeec13d10ca45b1e709bee9)) +- **authentication-client:** Throw separate OauthError in authentication client ([#2189](https://github.com/feathersjs/feathers/issues/2189)) ([fa45ec5](https://github.com/feathersjs/feathers/commit/fa45ec520b21834e103e6fe4200b06dced56c0e6)) # [5.0.0-pre.1](https://github.com/feathersjs/feathers/compare/v4.5.11...v5.0.0-pre.1) (2020-12-17) - - # [5.0.0-pre.0](https://github.com/feathersjs/feathers/compare/v4.5.4...v5.0.0-pre.0) (2020-05-19) - ### chore -* **package:** Remove @feathersjs/primus packages from core ([#1919](https://github.com/feathersjs/feathers/issues/1919)) ([d20b7d5](https://github.com/feathersjs/feathers/commit/d20b7d5a70f4d3306e294696156e8aa0337c35e9)), closes [#1899](https://github.com/feathersjs/feathers/issues/1899) - +- **package:** Remove @feathersjs/primus packages from core ([#1919](https://github.com/feathersjs/feathers/issues/1919)) ([d20b7d5](https://github.com/feathersjs/feathers/commit/d20b7d5a70f4d3306e294696156e8aa0337c35e9)), closes [#1899](https://github.com/feathersjs/feathers/issues/1899) ### BREAKING CHANGES -* **package:** Remove primus packages to be moved into the ecosystem. - - - - +- **package:** Remove primus packages to be moved into the ecosystem. # [5.0.0-pre.0](https://github.com/feathersjs/feathers/compare/v4.5.4...v5.0.0-pre.0) (2020-05-19) - ### chore -* **package:** Remove @feathersjs/primus packages from core ([#1919](https://github.com/feathersjs/feathers/issues/1919)) ([d20b7d5](https://github.com/feathersjs/feathers/commit/d20b7d5a70f4d3306e294696156e8aa0337c35e9)), closes [#1899](https://github.com/feathersjs/feathers/issues/1899) - +- **package:** Remove @feathersjs/primus packages from core ([#1919](https://github.com/feathersjs/feathers/issues/1919)) ([d20b7d5](https://github.com/feathersjs/feathers/commit/d20b7d5a70f4d3306e294696156e8aa0337c35e9)), closes [#1899](https://github.com/feathersjs/feathers/issues/1899) ### BREAKING CHANGES -* **package:** Remove primus packages to be moved into the ecosystem. - - +- **package:** Remove primus packages to be moved into the ecosystem. ## [4.5.11](https://github.com/feathersjs/feathers/compare/v4.5.10...v4.5.11) (2020-12-05) - ### Bug Fixes -* **authentication-client:** Allow reAuthentication using specific strategy ([#2140](https://github.com/feathersjs/feathers/issues/2140)) ([2a2bbf7](https://github.com/feathersjs/feathers/commit/2a2bbf7f8ee6d32b9fac8afab3421286b06e6443)) -* **socketio-client:** Throw an error and show a warning if someone tries to use socket.io-client v3 ([#2135](https://github.com/feathersjs/feathers/issues/2135)) ([cc3521c](https://github.com/feathersjs/feathers/commit/cc3521c935a1cbd690e29b7057998e3898f282db)) - - - - +- **authentication-client:** Allow reAuthentication using specific strategy ([#2140](https://github.com/feathersjs/feathers/issues/2140)) ([2a2bbf7](https://github.com/feathersjs/feathers/commit/2a2bbf7f8ee6d32b9fac8afab3421286b06e6443)) +- **socketio-client:** Throw an error and show a warning if someone tries to use socket.io-client v3 ([#2135](https://github.com/feathersjs/feathers/issues/2135)) ([cc3521c](https://github.com/feathersjs/feathers/commit/cc3521c935a1cbd690e29b7057998e3898f282db)) ## [4.5.10](https://github.com/feathersjs/feathers/compare/v4.5.9...v4.5.10) (2020-11-08) **Note:** Version bump only for package @feathersjs/authentication-client - - - - ## [4.5.9](https://github.com/feathersjs/feathers/compare/v4.5.8...v4.5.9) (2020-10-09) **Note:** Version bump only for package @feathersjs/authentication-client - - - - ## [4.5.8](https://github.com/feathersjs/feathers/compare/v4.5.7...v4.5.8) (2020-08-12) - ### Bug Fixes -* **authentication-client:** Fix storage type so it works with all supported interfaces ([#2041](https://github.com/feathersjs/feathers/issues/2041)) ([6ee0e78](https://github.com/feathersjs/feathers/commit/6ee0e78d55cf1214f61458f386b94c350eec32af)) - - - - +- **authentication-client:** Fix storage type so it works with all supported interfaces ([#2041](https://github.com/feathersjs/feathers/issues/2041)) ([6ee0e78](https://github.com/feathersjs/feathers/commit/6ee0e78d55cf1214f61458f386b94c350eec32af)) ## [4.5.7](https://github.com/feathersjs/feathers/compare/v4.5.6...v4.5.7) (2020-07-24) **Note:** Version bump only for package @feathersjs/authentication-client - - - - ## [4.5.6](https://github.com/feathersjs/feathers/compare/v4.5.5...v4.5.6) (2020-07-12) **Note:** Version bump only for package @feathersjs/authentication-client - - - - ## [4.5.5](https://github.com/feathersjs/feathers/compare/v4.5.4...v4.5.5) (2020-07-11) **Note:** Version bump only for package @feathersjs/authentication-client - - - - ## [4.5.4](https://github.com/feathersjs/feathers/compare/v4.5.3...v4.5.4) (2020-04-29) **Note:** Version bump only for package @feathersjs/authentication-client - - - - ## [4.5.3](https://github.com/feathersjs/feathers/compare/v4.5.2...v4.5.3) (2020-04-17) **Note:** Version bump only for package @feathersjs/authentication-client - - - - ## [4.5.2](https://github.com/feathersjs/feathers/compare/v4.5.1...v4.5.2) (2020-03-04) **Note:** Version bump only for package @feathersjs/authentication-client - - - - ## [4.5.1](https://github.com/feathersjs/feathers/compare/v4.5.0...v4.5.1) (2020-01-24) **Note:** Version bump only for package @feathersjs/authentication-client - - - - # [4.5.0](https://github.com/feathersjs/feathers/compare/v4.4.3...v4.5.0) (2020-01-18) **Note:** Version bump only for package @feathersjs/authentication-client - - - - ## [4.4.3](https://github.com/feathersjs/feathers/compare/v4.4.1...v4.4.3) (2019-12-06) **Note:** Version bump only for package @feathersjs/authentication-client - - - - ## [4.4.1](https://github.com/feathersjs/feathers/compare/v4.4.0...v4.4.1) (2019-11-27) **Note:** Version bump only for package @feathersjs/authentication-client - - - - # [4.4.0](https://github.com/feathersjs/feathers/compare/v4.3.11...v4.4.0) (2019-11-27) - ### Bug Fixes -* **authentication-client:** Reset authentication promise on socket disconnect ([#1696](https://github.com/feathersjs/feathers/issues/1696)) ([3951626](https://github.com/feathersjs/feathers/commit/395162633ff22e95833a3c2900cb9464bb5b056f)) - - - - +- **authentication-client:** Reset authentication promise on socket disconnect ([#1696](https://github.com/feathersjs/feathers/issues/1696)) ([3951626](https://github.com/feathersjs/feathers/commit/395162633ff22e95833a3c2900cb9464bb5b056f)) ## [4.3.11](https://github.com/feathersjs/feathers/compare/v4.3.10...v4.3.11) (2019-11-11) **Note:** Version bump only for package @feathersjs/authentication-client - - - - ## [4.3.10](https://github.com/feathersjs/feathers/compare/v4.3.9...v4.3.10) (2019-10-26) **Note:** Version bump only for package @feathersjs/authentication-client - - - - ## [4.3.9](https://github.com/feathersjs/feathers/compare/v4.3.8...v4.3.9) (2019-10-26) **Note:** Version bump only for package @feathersjs/authentication-client - - - - ## [4.3.7](https://github.com/feathersjs/feathers/compare/v4.3.6...v4.3.7) (2019-10-14) - ### Bug Fixes -* Improve authentication client default storage initialization ([#1613](https://github.com/feathersjs/feathers/issues/1613)) ([d7f5107](https://github.com/feathersjs/feathers/commit/d7f5107ef76297b4ca6db580afc5e2b372f5ee4d)) - - - - +- Improve authentication client default storage initialization ([#1613](https://github.com/feathersjs/feathers/issues/1613)) ([d7f5107](https://github.com/feathersjs/feathers/commit/d7f5107ef76297b4ca6db580afc5e2b372f5ee4d)) ## [4.3.5](https://github.com/feathersjs/feathers/compare/v4.3.4...v4.3.5) (2019-10-07) - ### Bug Fixes -* Authentication type improvements and timeout fix ([#1605](https://github.com/feathersjs/feathers/issues/1605)) ([19854d3](https://github.com/feathersjs/feathers/commit/19854d3)) - - - - +- Authentication type improvements and timeout fix ([#1605](https://github.com/feathersjs/feathers/issues/1605)) ([19854d3](https://github.com/feathersjs/feathers/commit/19854d3)) ## [4.3.4](https://github.com/feathersjs/feathers/compare/v4.3.3...v4.3.4) (2019-10-03) - ### Bug Fixes -* Typing improvements ([#1580](https://github.com/feathersjs/feathers/issues/1580)) ([7818aec](https://github.com/feathersjs/feathers/commit/7818aec)) - - - - +- Typing improvements ([#1580](https://github.com/feathersjs/feathers/issues/1580)) ([7818aec](https://github.com/feathersjs/feathers/commit/7818aec)) ## [4.3.3](https://github.com/feathersjs/feathers/compare/v4.3.2...v4.3.3) (2019-09-21) - ### Bug Fixes -* Small improvements in dependencies and code sturcture ([#1562](https://github.com/feathersjs/feathers/issues/1562)) ([42c13e2](https://github.com/feathersjs/feathers/commit/42c13e2)) - - - - +- Small improvements in dependencies and code sturcture ([#1562](https://github.com/feathersjs/feathers/issues/1562)) ([42c13e2](https://github.com/feathersjs/feathers/commit/42c13e2)) ## [4.3.2](https://github.com/feathersjs/feathers/compare/v4.3.1...v4.3.2) (2019-09-16) **Note:** Version bump only for package @feathersjs/authentication-client - - - - ## [4.3.1](https://github.com/feathersjs/feathers/compare/v4.3.0...v4.3.1) (2019-09-09) **Note:** Version bump only for package @feathersjs/authentication-client - - - - # [4.3.0](https://github.com/feathersjs/feathers/compare/v4.3.0-pre.4...v4.3.0) (2019-08-27) - ### Bug Fixes -* Only remove token on NotAuthenticated error in authentication client and handle error better ([#1525](https://github.com/feathersjs/feathers/issues/1525)) ([13a8758](https://github.com/feathersjs/feathers/commit/13a8758)) - - - - +- Only remove token on NotAuthenticated error in authentication client and handle error better ([#1525](https://github.com/feathersjs/feathers/issues/1525)) ([13a8758](https://github.com/feathersjs/feathers/commit/13a8758)) # [4.3.0-pre.4](https://github.com/feathersjs/feathers/compare/v4.3.0-pre.3...v4.3.0-pre.4) (2019-08-22) **Note:** Version bump only for package @feathersjs/authentication-client - - - - # [4.3.0-pre.3](https://github.com/feathersjs/feathers/compare/v4.3.0-pre.2...v4.3.0-pre.3) (2019-08-19) - ### Bug Fixes -* Update all dependencies ([7d53a00](https://github.com/feathersjs/feathers/commit/7d53a00)) - +- Update all dependencies ([7d53a00](https://github.com/feathersjs/feathers/commit/7d53a00)) ### Features -* Let strategies handle the connection ([#1510](https://github.com/feathersjs/feathers/issues/1510)) ([4329feb](https://github.com/feathersjs/feathers/commit/4329feb)) - - - - +- Let strategies handle the connection ([#1510](https://github.com/feathersjs/feathers/issues/1510)) ([4329feb](https://github.com/feathersjs/feathers/commit/4329feb)) # [4.3.0-pre.2](https://github.com/feathersjs/feathers/compare/v4.3.0-pre.1...v4.3.0-pre.2) (2019-08-02) - ### Bug Fixes -* Do not error in authentication client on logout ([#1473](https://github.com/feathersjs/feathers/issues/1473)) ([8211b98](https://github.com/feathersjs/feathers/commit/8211b98)) - - - - +- Do not error in authentication client on logout ([#1473](https://github.com/feathersjs/feathers/issues/1473)) ([8211b98](https://github.com/feathersjs/feathers/commit/8211b98)) # [4.3.0-pre.1](https://github.com/feathersjs/feathers/compare/v4.0.0-pre.5...v4.3.0-pre.1) (2019-07-11) **Note:** Version bump only for package @feathersjs/authentication-client - - - - # [4.0.0-pre.5](https://github.com/feathersjs/feathers/compare/v4.0.0-pre.4...v4.0.0-pre.5) (2019-07-10) **Note:** Version bump only for package @feathersjs/authentication-client - - - - # [4.0.0-pre.4](https://github.com/feathersjs/feathers/compare/v4.0.0-pre.3...v4.0.0-pre.4) (2019-07-05) **Note:** Version bump only for package @feathersjs/authentication-client - - - - # [4.0.0-pre.3](https://github.com/feathersjs/feathers/compare/v4.0.0-pre.2...v4.0.0-pre.3) (2019-06-01) - ### Bug Fixes -* Make oAuth paths more consistent and improve authentication client ([#1377](https://github.com/feathersjs/feathers/issues/1377)) ([adb2543](https://github.com/feathersjs/feathers/commit/adb2543)) -* Typings fix and improvements. ([#1364](https://github.com/feathersjs/feathers/issues/1364)) ([515b916](https://github.com/feathersjs/feathers/commit/515b916)) -* Update dependencies and fix tests ([#1373](https://github.com/feathersjs/feathers/issues/1373)) ([d743a7f](https://github.com/feathersjs/feathers/commit/d743a7f)) - - - - +- Make oAuth paths more consistent and improve authentication client ([#1377](https://github.com/feathersjs/feathers/issues/1377)) ([adb2543](https://github.com/feathersjs/feathers/commit/adb2543)) +- Typings fix and improvements. ([#1364](https://github.com/feathersjs/feathers/issues/1364)) ([515b916](https://github.com/feathersjs/feathers/commit/515b916)) +- Update dependencies and fix tests ([#1373](https://github.com/feathersjs/feathers/issues/1373)) ([d743a7f](https://github.com/feathersjs/feathers/commit/d743a7f)) # [4.0.0-pre.2](https://github.com/feathersjs/feathers/compare/v4.0.0-pre.1...v4.0.0-pre.2) (2019-05-15) **Note:** Version bump only for package @feathersjs/authentication-client - - - - # [4.0.0-pre.1](https://github.com/feathersjs/feathers/compare/v4.0.0-pre.0...v4.0.0-pre.1) (2019-05-08) - ### Bug Fixes -* Guard against null in client side logout function ([#1319](https://github.com/feathersjs/feathers/issues/1319)) ([fa7f057](https://github.com/feathersjs/feathers/commit/fa7f057)) -* Handle error oAuth redirect in authentication client ([#1307](https://github.com/feathersjs/feathers/issues/1307)) ([12d48ee](https://github.com/feathersjs/feathers/commit/12d48ee)) -* Merge httpStrategies and authStrategies option ([#1308](https://github.com/feathersjs/feathers/issues/1308)) ([afa4d55](https://github.com/feathersjs/feathers/commit/afa4d55)) -* Rename jwtStrategies option to authStrategies ([#1305](https://github.com/feathersjs/feathers/issues/1305)) ([4aee151](https://github.com/feathersjs/feathers/commit/4aee151)) -* Update version number check ([53575c5](https://github.com/feathersjs/feathers/commit/53575c5)) - - - - +- Guard against null in client side logout function ([#1319](https://github.com/feathersjs/feathers/issues/1319)) ([fa7f057](https://github.com/feathersjs/feathers/commit/fa7f057)) +- Handle error oAuth redirect in authentication client ([#1307](https://github.com/feathersjs/feathers/issues/1307)) ([12d48ee](https://github.com/feathersjs/feathers/commit/12d48ee)) +- Merge httpStrategies and authStrategies option ([#1308](https://github.com/feathersjs/feathers/issues/1308)) ([afa4d55](https://github.com/feathersjs/feathers/commit/afa4d55)) +- Rename jwtStrategies option to authStrategies ([#1305](https://github.com/feathersjs/feathers/issues/1305)) ([4aee151](https://github.com/feathersjs/feathers/commit/4aee151)) +- Update version number check ([53575c5](https://github.com/feathersjs/feathers/commit/53575c5)) # [4.0.0-pre.0](https://github.com/feathersjs/feathers/compare/v3.2.0-pre.1...v4.0.0-pre.0) (2019-04-21) - ### Bug Fixes -* Authentication core improvements ([#1260](https://github.com/feathersjs/feathers/issues/1260)) ([c5dc7a2](https://github.com/feathersjs/feathers/commit/c5dc7a2)) -* Make Mocha a proper devDependency for every repository ([#1053](https://github.com/feathersjs/feathers/issues/1053)) ([9974803](https://github.com/feathersjs/feathers/commit/9974803)) -* Update adapter common tests ([#1135](https://github.com/feathersjs/feathers/issues/1135)) ([8166dda](https://github.com/feathersjs/feathers/commit/8166dda)) -* Update all dependencies to latest ([#1206](https://github.com/feathersjs/feathers/issues/1206)) ([e51e0f6](https://github.com/feathersjs/feathers/commit/e51e0f6)) -* **package:** update debug to version 3.0.0 ([#61](https://github.com/feathersjs/feathers/issues/61)) ([6f5009c](https://github.com/feathersjs/feathers/commit/6f5009c)) - +- Authentication core improvements ([#1260](https://github.com/feathersjs/feathers/issues/1260)) ([c5dc7a2](https://github.com/feathersjs/feathers/commit/c5dc7a2)) +- Make Mocha a proper devDependency for every repository ([#1053](https://github.com/feathersjs/feathers/issues/1053)) ([9974803](https://github.com/feathersjs/feathers/commit/9974803)) +- Update adapter common tests ([#1135](https://github.com/feathersjs/feathers/issues/1135)) ([8166dda](https://github.com/feathersjs/feathers/commit/8166dda)) +- Update all dependencies to latest ([#1206](https://github.com/feathersjs/feathers/issues/1206)) ([e51e0f6](https://github.com/feathersjs/feathers/commit/e51e0f6)) +- **package:** update debug to version 3.0.0 ([#61](https://github.com/feathersjs/feathers/issues/61)) ([6f5009c](https://github.com/feathersjs/feathers/commit/6f5009c)) ### Features -* @feathersjs/authentication-oauth ([#1299](https://github.com/feathersjs/feathers/issues/1299)) ([656bae7](https://github.com/feathersjs/feathers/commit/656bae7)) -* Add authentication through oAuth redirect to authentication client ([#1301](https://github.com/feathersjs/feathers/issues/1301)) ([35d8043](https://github.com/feathersjs/feathers/commit/35d8043)) -* Add AuthenticationBaseStrategy and make authentication option handling more explicit ([#1284](https://github.com/feathersjs/feathers/issues/1284)) ([2667d92](https://github.com/feathersjs/feathers/commit/2667d92)) -* Add TypeScript definitions ([#1275](https://github.com/feathersjs/feathers/issues/1275)) ([9dd6713](https://github.com/feathersjs/feathers/commit/9dd6713)) -* Authentication v3 client ([#1240](https://github.com/feathersjs/feathers/issues/1240)) ([65b43bd](https://github.com/feathersjs/feathers/commit/65b43bd)) -* Authentication v3 core server implementation ([#1205](https://github.com/feathersjs/feathers/issues/1205)) ([1bd7591](https://github.com/feathersjs/feathers/commit/1bd7591)) - +- @feathersjs/authentication-oauth ([#1299](https://github.com/feathersjs/feathers/issues/1299)) ([656bae7](https://github.com/feathersjs/feathers/commit/656bae7)) +- Add authentication through oAuth redirect to authentication client ([#1301](https://github.com/feathersjs/feathers/issues/1301)) ([35d8043](https://github.com/feathersjs/feathers/commit/35d8043)) +- Add AuthenticationBaseStrategy and make authentication option handling more explicit ([#1284](https://github.com/feathersjs/feathers/issues/1284)) ([2667d92](https://github.com/feathersjs/feathers/commit/2667d92)) +- Add TypeScript definitions ([#1275](https://github.com/feathersjs/feathers/issues/1275)) ([9dd6713](https://github.com/feathersjs/feathers/commit/9dd6713)) +- Authentication v3 client ([#1240](https://github.com/feathersjs/feathers/issues/1240)) ([65b43bd](https://github.com/feathersjs/feathers/commit/65b43bd)) +- Authentication v3 core server implementation ([#1205](https://github.com/feathersjs/feathers/issues/1205)) ([1bd7591](https://github.com/feathersjs/feathers/commit/1bd7591)) ### BREAKING CHANGES -* Rewrite for authentication v3 - - - - +- Rewrite for authentication v3 ## [1.0.11](https://github.com/feathersjs/feathers/compare/@feathersjs/authentication-client@1.0.10...@feathersjs/authentication-client@1.0.11) (2019-01-26) **Note:** Version bump only for package @feathersjs/authentication-client - - - - ## [1.0.10](https://github.com/feathersjs/feathers/compare/@feathersjs/authentication-client@1.0.9...@feathersjs/authentication-client@1.0.10) (2019-01-02) - ### Bug Fixes -* Update adapter common tests ([#1135](https://github.com/feathersjs/feathers/issues/1135)) ([8166dda](https://github.com/feathersjs/feathers/commit/8166dda)) - - - - +- Update adapter common tests ([#1135](https://github.com/feathersjs/feathers/issues/1135)) ([8166dda](https://github.com/feathersjs/feathers/commit/8166dda)) + ## [1.0.9](https://github.com/feathersjs/feathers/compare/@feathersjs/authentication-client@1.0.8...@feathersjs/authentication-client@1.0.9) (2018-12-16) **Note:** Version bump only for package @feathersjs/authentication-client - - - - + ## [1.0.8](https://github.com/feathersjs/feathers/compare/@feathersjs/authentication-client@1.0.7...@feathersjs/authentication-client@1.0.8) (2018-10-26) **Note:** Version bump only for package @feathersjs/authentication-client - - - - -## [1.0.7](https://github.com/feathersjs/feathers/compare/@feathersjs/authentication-client@1.0.6...@feathersjs/authentication-client@1.0.7) (2018-10-25) +## [1.0.7](https://github.com/feathersjs/feathers/compare/@feathersjs/authentication-client@1.0.6...@feathersjs/authentication-client@1.0.7) (2018-10-25) ### Bug Fixes -* Make Mocha a proper devDependency for every repository ([#1053](https://github.com/feathersjs/feathers/issues/1053)) ([9974803](https://github.com/feathersjs/feathers/commit/9974803)) - - - - +- Make Mocha a proper devDependency for every repository ([#1053](https://github.com/feathersjs/feathers/issues/1053)) ([9974803](https://github.com/feathersjs/feathers/commit/9974803)) + ## [1.0.6](https://github.com/feathersjs/feathers/compare/@feathersjs/authentication-client@1.0.5...@feathersjs/authentication-client@1.0.6) (2018-09-21) **Note:** Version bump only for package @feathersjs/authentication-client - - - - + ## [1.0.5](https://github.com/feathersjs/feathers/compare/@feathersjs/authentication-client@1.0.4...@feathersjs/authentication-client@1.0.5) (2018-09-17) **Note:** Version bump only for package @feathersjs/authentication-client - - - - + ## [1.0.4](https://github.com/feathersjs/feathers/compare/@feathersjs/authentication-client@1.0.3...@feathersjs/authentication-client@1.0.4) (2018-09-02) **Note:** Version bump only for package @feathersjs/authentication-client + ## 1.0.3 - Migrate to Monorepo ([feathers#462](https://github.com/feathersjs/feathers/issues/462)) ## [v1.0.2](https://github.com/feathersjs/authentication-client/tree/v1.0.2) (2018-01-03) + [Full Changelog](https://github.com/feathersjs/authentication-client/compare/v1.0.1...v1.0.2) **Closed issues:** @@ -644,6 +448,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Update feathers-memory to the latest version 🚀 [\#82](https://github.com/feathersjs/authentication-client/pull/82) ([greenkeeper[bot]](https://github.com/apps/greenkeeper)) ## [v1.0.1](https://github.com/feathersjs/authentication-client/tree/v1.0.1) (2017-11-16) + [Full Changelog](https://github.com/feathersjs/authentication-client/compare/v1.0.0...v1.0.1) **Merged pull requests:** @@ -652,6 +457,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Update @feathersjs/authentication to the latest version 🚀 [\#79](https://github.com/feathersjs/authentication-client/pull/79) ([greenkeeper[bot]](https://github.com/apps/greenkeeper)) ## [v1.0.0](https://github.com/feathersjs/authentication-client/tree/v1.0.0) (2017-11-01) + [Full Changelog](https://github.com/feathersjs/authentication-client/compare/v1.0.0-pre.1...v1.0.0) **Merged pull requests:** @@ -659,6 +465,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Update dependencies for release [\#78](https://github.com/feathersjs/authentication-client/pull/78) ([daffl](https://github.com/daffl)) ## [v1.0.0-pre.1](https://github.com/feathersjs/authentication-client/tree/v1.0.0-pre.1) (2017-10-25) + [Full Changelog](https://github.com/feathersjs/authentication-client/compare/v0.3.3...v1.0.0-pre.1) **Closed issues:** @@ -675,11 +482,12 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Update to new plugin infrastructure [\#74](https://github.com/feathersjs/authentication-client/pull/74) ([daffl](https://github.com/daffl)) - Update mocha to the latest version 🚀 [\#72](https://github.com/feathersjs/authentication-client/pull/72) ([greenkeeper[bot]](https://github.com/apps/greenkeeper)) - Add babel-polyfill and package-lock.json [\#68](https://github.com/feathersjs/authentication-client/pull/68) ([daffl](https://github.com/daffl)) -- Passport.verifyJWT should return Promise\, not Promise\ [\#65](https://github.com/feathersjs/authentication-client/pull/65) ([zxh19890103](https://github.com/zxh19890103)) +- Passport.verifyJWT should return Promise\, not Promise\ [\#65](https://github.com/feathersjs/authentication-client/pull/65) ([zxh19890103](https://github.com/zxh19890103)) - Update debug to the latest version 🚀 [\#61](https://github.com/feathersjs/authentication-client/pull/61) ([greenkeeper[bot]](https://github.com/apps/greenkeeper)) - Update ws to the latest version 🚀 [\#60](https://github.com/feathersjs/authentication-client/pull/60) ([greenkeeper[bot]](https://github.com/apps/greenkeeper)) ## [v0.3.3](https://github.com/feathersjs/authentication-client/tree/v0.3.3) (2017-07-18) + [Full Changelog](https://github.com/feathersjs/authentication-client/compare/v0.3.2...v0.3.3) **Closed issues:** @@ -697,6 +505,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Update README.md [\#47](https://github.com/feathersjs/authentication-client/pull/47) ([bertho-zero](https://github.com/bertho-zero)) ## [v0.3.2](https://github.com/feathersjs/authentication-client/tree/v0.3.2) (2017-04-30) + [Full Changelog](https://github.com/feathersjs/authentication-client/compare/v0.3.1...v0.3.2) **Closed issues:** @@ -715,6 +524,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Note that auth must be configured after rest/socket clients [\#36](https://github.com/feathersjs/authentication-client/pull/36) ([hubgit](https://github.com/hubgit)) ## [v0.3.1](https://github.com/feathersjs/authentication-client/tree/v0.3.1) (2017-03-10) + [Full Changelog](https://github.com/feathersjs/authentication-client/compare/v0.3.0...v0.3.1) **Closed issues:** @@ -727,9 +537,11 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Fix \#33 exp claim should be optional [\#34](https://github.com/feathersjs/authentication-client/pull/34) ([whollacsek](https://github.com/whollacsek)) ## [v0.3.0](https://github.com/feathersjs/authentication-client/tree/v0.3.0) (2017-03-08) + [Full Changelog](https://github.com/feathersjs/authentication-client/compare/v0.2.0...v0.3.0) ## [v0.2.0](https://github.com/feathersjs/authentication-client/tree/v0.2.0) (2017-03-07) + [Full Changelog](https://github.com/feathersjs/authentication-client/compare/v0.1.10...v0.2.0) **Closed issues:** @@ -746,6 +558,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Add support for socket timeouts and some refactoring [\#30](https://github.com/feathersjs/authentication-client/pull/30) ([daffl](https://github.com/daffl)) ## [v0.1.10](https://github.com/feathersjs/authentication-client/tree/v0.1.10) (2017-03-03) + [Full Changelog](https://github.com/feathersjs/authentication-client/compare/v0.1.9...v0.1.10) **Merged pull requests:** @@ -753,6 +566,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Remove hardcoded values for Config and Credentials typings [\#28](https://github.com/feathersjs/authentication-client/pull/28) ([myknbani](https://github.com/myknbani)) ## [v0.1.9](https://github.com/feathersjs/authentication-client/tree/v0.1.9) (2017-03-01) + [Full Changelog](https://github.com/feathersjs/authentication-client/compare/v0.1.8...v0.1.9) **Merged pull requests:** @@ -760,6 +574,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Typescript Definitions [\#25](https://github.com/feathersjs/authentication-client/pull/25) ([AbraaoAlves](https://github.com/AbraaoAlves)) ## [v0.1.8](https://github.com/feathersjs/authentication-client/tree/v0.1.8) (2017-02-05) + [Full Changelog](https://github.com/feathersjs/authentication-client/compare/v0.1.7...v0.1.8) **Closed issues:** @@ -772,6 +587,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Hoist upgrade handler into current scope by using an arrow function [\#27](https://github.com/feathersjs/authentication-client/pull/27) ([daffl](https://github.com/daffl)) ## [v0.1.7](https://github.com/feathersjs/authentication-client/tree/v0.1.7) (2017-01-29) + [Full Changelog](https://github.com/feathersjs/authentication-client/compare/v0.1.6...v0.1.7) **Closed issues:** @@ -786,6 +602,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Update passport.js [\#20](https://github.com/feathersjs/authentication-client/pull/20) ([bertho-zero](https://github.com/bertho-zero)) ## [v0.1.6](https://github.com/feathersjs/authentication-client/tree/v0.1.6) (2016-12-14) + [Full Changelog](https://github.com/feathersjs/authentication-client/compare/v0.1.5...v0.1.6) **Closed issues:** @@ -797,9 +614,11 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Fix linting [\#13](https://github.com/feathersjs/authentication-client/pull/13) ([marshallswain](https://github.com/marshallswain)) ## [v0.1.5](https://github.com/feathersjs/authentication-client/tree/v0.1.5) (2016-12-13) + [Full Changelog](https://github.com/feathersjs/authentication-client/compare/v0.1.4...v0.1.5) ## [v0.1.4](https://github.com/feathersjs/authentication-client/tree/v0.1.4) (2016-12-13) + [Full Changelog](https://github.com/feathersjs/authentication-client/compare/v0.1.3...v0.1.4) **Closed issues:** @@ -812,6 +631,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - More specific imports for StealJS [\#14](https://github.com/feathersjs/authentication-client/pull/14) ([marshallswain](https://github.com/marshallswain)) ## [v0.1.3](https://github.com/feathersjs/authentication-client/tree/v0.1.3) (2016-11-23) + [Full Changelog](https://github.com/feathersjs/authentication-client/compare/v0.1.2...v0.1.3) **Closed issues:** @@ -823,6 +643,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Socket reconnect [\#9](https://github.com/feathersjs/authentication-client/pull/9) ([ekryski](https://github.com/ekryski)) ## [v0.1.2](https://github.com/feathersjs/authentication-client/tree/v0.1.2) (2016-11-22) + [Full Changelog](https://github.com/feathersjs/authentication-client/compare/v0.1.1...v0.1.2) **Merged pull requests:** @@ -830,6 +651,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Custom jwt strategy names [\#8](https://github.com/feathersjs/authentication-client/pull/8) ([ekryski](https://github.com/ekryski)) ## [v0.1.1](https://github.com/feathersjs/authentication-client/tree/v0.1.1) (2016-11-21) + [Full Changelog](https://github.com/feathersjs/authentication-client/compare/v0.1.0...v0.1.1) **Merged pull requests:** @@ -837,6 +659,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Socket reconnect upgrade auth [\#3](https://github.com/feathersjs/authentication-client/pull/3) ([marshallswain](https://github.com/marshallswain)) ## [v0.1.0](https://github.com/feathersjs/authentication-client/tree/v0.1.0) (2016-11-18) + **Closed issues:** - Relation with feathers-authentication [\#6](https://github.com/feathersjs/authentication-client/issues/6) @@ -846,6 +669,4 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Feathers authentication 1.0 compatible client [\#7](https://github.com/feathersjs/authentication-client/pull/7) ([ekryski](https://github.com/ekryski)) - - -\* *This Change Log was automatically generated by [github_changelog_generator](https://github.com/skywinder/Github-Changelog-Generator)* +\* _This Change Log was automatically generated by [github_changelog_generator](https://github.com/skywinder/Github-Changelog-Generator)_ diff --git a/packages/authentication-client/LICENSE b/packages/authentication-client/LICENSE index 3f395cc665..59604f46f3 100644 --- a/packages/authentication-client/LICENSE +++ b/packages/authentication-client/LICENSE @@ -1,6 +1,6 @@ The MIT License (MIT) -Copyright (c) 2021 Feathers +Copyright (c) 2022 Feathers Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated documentation files (the "Software"), to deal diff --git a/packages/authentication-client/README.md b/packages/authentication-client/README.md index 48bd0216a9..831f271133 100644 --- a/packages/authentication-client/README.md +++ b/packages/authentication-client/README.md @@ -1,8 +1,8 @@ # @feathersjs/authentication-client [![CI](https://github.com/feathersjs/feathers/workflows/CI/badge.svg)](https://github.com/feathersjs/feathers/actions?query=workflow%3ACI) -[![Dependency Status](https://img.shields.io/david/feathersjs/feathers.svg?style=flat-square&path=packages/authentication-client)](https://david-dm.org/feathersjs/feathers?path=packages/authentication-client) [![Download Status](https://img.shields.io/npm/dm/@feathersjs/authentication-client.svg?style=flat-square)](https://www.npmjs.com/package/@feathersjs/authentication-client) +[![Discord](https://badgen.net/badge/icon/discord?icon=discord&label)](https://discord.gg/qa8kez8QBx) > Feathers authentication client @@ -18,6 +18,6 @@ Refer to the [Feathers authentication client API documentation](https://docs.fea ## License -Copyright (c) 2021 [Feathers contributors](https://github.com/feathersjs/feathers/graphs/contributors) +Copyright (c) 2022 [Feathers contributors](https://github.com/feathersjs/feathers/graphs/contributors) Licensed under the [MIT license](LICENSE). diff --git a/packages/authentication-client/package.json b/packages/authentication-client/package.json index 139c109e31..c73c20d21a 100644 --- a/packages/authentication-client/package.json +++ b/packages/authentication-client/package.json @@ -1,7 +1,7 @@ { "name": "@feathersjs/authentication-client", "description": "The authentication plugin for feathers-client", - "version": "5.0.0-pre.16", + "version": "5.0.0-pre.31", "homepage": "https://feathersjs.com", "main": "lib/", "types": "lib/", @@ -16,7 +16,8 @@ }, "repository": { "type": "git", - "url": "git://github.com/feathersjs/feathers.git" + "url": "git://github.com/feathersjs/feathers.git", + "directory": "packages/authentication-client" }, "author": { "name": "Feathers contributors", @@ -41,9 +42,9 @@ ], "scripts": { "prepublish": "npm run compile", - "compile": "shx rm -rf lib/ && tsc", - "test": "npm run compile && npm run mocha", - "mocha": "mocha --config ../../.mocharc.json --recursive test/**.test.ts test/**/*.test.ts" + "pack": "npm pack --pack-destination ../cli/test/build", + "compile": "shx rm -rf lib/ && tsc && npm run pack", + "test": "mocha --config ../../.mocharc.json --recursive test/**.test.ts test/**/*.test.ts" }, "directories": { "lib": "lib" @@ -52,25 +53,25 @@ "access": "public" }, "dependencies": { - "@feathersjs/authentication": "^5.0.0-pre.16", - "@feathersjs/commons": "^5.0.0-pre.16", - "@feathersjs/errors": "^5.0.0-pre.16", - "@feathersjs/feathers": "^5.0.0-pre.16" + "@feathersjs/authentication": "^5.0.0-pre.31", + "@feathersjs/commons": "^5.0.0-pre.31", + "@feathersjs/errors": "^5.0.0-pre.31", + "@feathersjs/feathers": "^5.0.0-pre.31" }, "devDependencies": { - "@feathersjs/authentication-local": "^5.0.0-pre.16", - "@feathersjs/express": "^5.0.0-pre.16", - "@feathersjs/memory": "^5.0.0-pre.16", - "@feathersjs/rest-client": "^5.0.0-pre.16", - "@feathersjs/socketio": "^5.0.0-pre.16", - "@feathersjs/socketio-client": "^5.0.0-pre.16", - "@types/mocha": "^9.0.0", - "@types/node": "^17.0.5", - "axios": "^0.24.0", - "mocha": "^9.1.3", - "shx": "^0.3.3", - "ts-node": "^10.4.0", - "typescript": "^4.5.4" + "@feathersjs/authentication-local": "^5.0.0-pre.31", + "@feathersjs/express": "^5.0.0-pre.31", + "@feathersjs/memory": "^5.0.0-pre.31", + "@feathersjs/rest-client": "^5.0.0-pre.31", + "@feathersjs/socketio": "^5.0.0-pre.31", + "@feathersjs/socketio-client": "^5.0.0-pre.31", + "@types/mocha": "^10.0.0", + "@types/node": "^18.8.2", + "axios": "^0.27.2", + "mocha": "^10.0.0", + "shx": "^0.3.4", + "ts-node": "^10.9.1", + "typescript": "^4.8.4" }, - "gitHead": "f0cd227a82d159b528193bd33747c97684a48773" + "gitHead": "4500dbeb8cea566678cf88b3313a88efd93a2ed9" } diff --git a/packages/authentication-client/src/core.ts b/packages/authentication-client/src/core.ts index 0978243d5d..07db6190f4 100644 --- a/packages/authentication-client/src/core.ts +++ b/packages/authentication-client/src/core.ts @@ -1,200 +1,200 @@ -import { NotAuthenticated, FeathersError } from '@feathersjs/errors'; -import { Application, Params } from '@feathersjs/feathers'; -import { AuthenticationRequest, AuthenticationResult } from '@feathersjs/authentication'; -import { Storage, StorageWrapper } from './storage'; +import { NotAuthenticated, FeathersError } from '@feathersjs/errors' +import { Application, Params } from '@feathersjs/feathers' +import { AuthenticationRequest, AuthenticationResult } from '@feathersjs/authentication' +import { Storage, StorageWrapper } from './storage' class OauthError extends FeathersError { - constructor (message: string, data?: any) { - super(message, 'OauthError', 401, 'oauth-error', data); + constructor(message: string, data?: any) { + super(message, 'OauthError', 401, 'oauth-error', data) } } -const getMatch = (location: Location, key: string): [ string, RegExp ] => { - const regex = new RegExp(`(?:\&?)${key}=([^&]*)`); - const match = location.hash ? location.hash.match(regex) : null; +const getMatch = (location: Location, key: string): [string, RegExp] => { + const regex = new RegExp(`(?:\&?)${key}=([^&]*)`) + const match = location.hash ? location.hash.match(regex) : null if (match !== null) { - const [ , value ] = match; + const [, value] = match - return [ value, regex ]; + return [value, regex] } - return [ null, regex ]; -}; + return [null, regex] +} -export type ClientConstructor = new (app: Application, options: AuthenticationClientOptions) - => AuthenticationClient; +export type ClientConstructor = new ( + app: Application, + options: AuthenticationClientOptions +) => AuthenticationClient export interface AuthenticationClientOptions { - storage: Storage; - header: string; - scheme: string; - storageKey: string; - locationKey: string; - locationErrorKey: string; - jwtStrategy: string; - path: string; - Authentication: ClientConstructor; + storage: Storage + header: string + scheme: string + storageKey: string + locationKey: string + locationErrorKey: string + jwtStrategy: string + path: string + Authentication: ClientConstructor } export class AuthenticationClient { - app: Application; - authenticated: boolean; - options: AuthenticationClientOptions; + app: Application + authenticated: boolean + options: AuthenticationClientOptions - constructor (app: Application, options: AuthenticationClientOptions) { - const socket = app.io; - const storage = new StorageWrapper(app.get('storage') || options.storage); + constructor(app: Application, options: AuthenticationClientOptions) { + const socket = app.io + const storage = new StorageWrapper(app.get('storage') || options.storage) - this.app = app; - this.options = options; - this.authenticated = false; - this.app.set('storage', storage); + this.app = app + this.options = options + this.authenticated = false + this.app.set('storage', storage) if (socket) { - this.handleSocket(socket); + this.handleSocket(socket) } } - get service () { - return this.app.service(this.options.path); + get service() { + return this.app.service(this.options.path) } - get storage () { - return this.app.get('storage') as Storage; + get storage() { + return this.app.get('storage') as Storage } - handleSocket (socket: any) { + handleSocket(socket: any) { // Connection events happen on every reconnect - const connected = this.app.io ? 'connect' : 'open'; - const disconnected = this.app.io ? 'disconnect' : 'disconnection'; + const connected = this.app.io ? 'connect' : 'open' + const disconnected = this.app.io ? 'disconnect' : 'disconnection' socket.on(disconnected, () => { - const authPromise = new Promise(resolve => - socket.once(connected, (data: any) => resolve(data)) - ) - // Only reconnect when `reAuthenticate()` or `authenticate()` - // has been called explicitly first - // Force reauthentication with the server - .then(() => this.authenticated ? this.reAuthenticate(true) : null); - - this.app.set('authentication', authPromise); - }); + const authPromise = new Promise((resolve) => socket.once(connected, (data: any) => resolve(data))) + // Only reconnect when `reAuthenticate()` or `authenticate()` + // has been called explicitly first + // Force reauthentication with the server + .then(() => (this.authenticated ? this.reAuthenticate(true) : null)) + + this.app.set('authentication', authPromise) + }) } - getFromLocation (location: Location) { - const [ accessToken, tokenRegex ] = getMatch(location, this.options.locationKey); + getFromLocation(location: Location) { + const [accessToken, tokenRegex] = getMatch(location, this.options.locationKey) if (accessToken !== null) { - location.hash = location.hash.replace(tokenRegex, ''); + location.hash = location.hash.replace(tokenRegex, '') - return Promise.resolve(accessToken); + return Promise.resolve(accessToken) } - const [ message, errorRegex ] = getMatch(location, this.options.locationErrorKey); + const [message, errorRegex] = getMatch(location, this.options.locationErrorKey) if (message !== null) { - location.hash = location.hash.replace(errorRegex, ''); + location.hash = location.hash.replace(errorRegex, '') - return Promise.reject(new OauthError(decodeURIComponent(message))); + return Promise.reject(new OauthError(decodeURIComponent(message))) } - return Promise.resolve(null); + return Promise.resolve(null) } - setAccessToken (accessToken: string) { - return this.storage.setItem(this.options.storageKey, accessToken); + setAccessToken(accessToken: string) { + return this.storage.setItem(this.options.storageKey, accessToken) } - getAccessToken (): Promise { - return this.storage.getItem(this.options.storageKey) - .then((accessToken: string) => { - if (!accessToken && typeof window !== 'undefined' && window.location) { - return this.getFromLocation(window.location); - } + getAccessToken(): Promise { + return this.storage.getItem(this.options.storageKey).then((accessToken: string) => { + if (!accessToken && typeof window !== 'undefined' && window.location) { + return this.getFromLocation(window.location) + } - return accessToken || null; - }); + return accessToken || null + }) } - removeAccessToken () { - return this.storage.removeItem(this.options.storageKey); + removeAccessToken() { + return this.storage.removeItem(this.options.storageKey) } - reset () { - this.app.set('authentication', null); - this.authenticated = false; + reset() { + this.app.set('authentication', null) + this.authenticated = false - return Promise.resolve(null); + return Promise.resolve(null) } - handleError (error: FeathersError, type: 'authenticate'|'logout') { + handleError(error: FeathersError, type: 'authenticate' | 'logout') { if (error.code === 401 || error.code === 403) { - const promise = this.removeAccessToken().then(() => this.reset()); + const promise = this.removeAccessToken().then(() => this.reset()) - return type === 'logout' ? promise : promise.then(() => Promise.reject(error)); + return type === 'logout' ? promise : promise.then(() => Promise.reject(error)) } - return Promise.reject(error); + return Promise.reject(error) } - reAuthenticate (force = false, strategy?: string): Promise { + reAuthenticate(force = false, strategy?: string): Promise { // Either returns the authentication state or // tries to re-authenticate with the stored JWT and strategy - const authPromise = this.app.get('authentication'); + let authPromise = this.app.get('authentication') if (!authPromise || force === true) { - return this.getAccessToken().then(accessToken => { + authPromise = this.getAccessToken().then((accessToken) => { if (!accessToken) { - throw new NotAuthenticated('No accessToken found in storage'); + return this.handleError(new NotAuthenticated('No accessToken found in storage'), 'authenticate') } return this.authenticate({ strategy: strategy || this.options.jwtStrategy, accessToken - }); - }); + }) + }) + this.app.set('authentication', authPromise) } - return authPromise; + return authPromise } - authenticate (authentication?: AuthenticationRequest, params?: Params): Promise { + authenticate(authentication?: AuthenticationRequest, params?: Params): Promise { if (!authentication) { - return this.reAuthenticate(); + return this.reAuthenticate() } - const promise = this.service.create(authentication, params) + const promise = this.service + .create(authentication, params) .then((authResult: AuthenticationResult) => { - const { accessToken } = authResult; + const { accessToken } = authResult - this.authenticated = true; - this.app.emit('login', authResult); - this.app.emit('authenticated', authResult); + this.authenticated = true + this.app.emit('login', authResult) + this.app.emit('authenticated', authResult) - return this.setAccessToken(accessToken).then(() => authResult); - }).catch((error: FeathersError) => - this.handleError(error, 'authenticate') - ); + return this.setAccessToken(accessToken).then(() => authResult) + }) + .catch((error: FeathersError) => this.handleError(error, 'authenticate')) - this.app.set('authentication', promise); + this.app.set('authentication', promise) - return promise; + return promise } - logout (): Promise { + logout(): Promise { return Promise.resolve(this.app.get('authentication')) - .then(() => this.service.remove(null) - .then((authResult: AuthenticationResult) => this.removeAccessToken() - .then(() => this.reset()) - .then(() => { - this.app.emit('logout', authResult); - - return authResult; - }) - )) - .catch((error: FeathersError) => - this.handleError(error, 'logout') - ); + .then(() => + this.service.remove(null).then((authResult: AuthenticationResult) => + this.removeAccessToken() + .then(() => this.reset()) + .then(() => { + this.app.emit('logout', authResult) + + return authResult + }) + ) + ) + .catch((error: FeathersError) => this.handleError(error, 'logout')) } } diff --git a/packages/authentication-client/src/hooks/authentication.ts b/packages/authentication-client/src/hooks/authentication.ts index 52ce76704d..bba7b2dc2d 100644 --- a/packages/authentication-client/src/hooks/authentication.ts +++ b/packages/authentication-client/src/hooks/authentication.ts @@ -1,18 +1,26 @@ -import { HookContext, NextFunction } from '@feathersjs/feathers'; -import { stripSlashes } from '@feathersjs/commons'; +import { HookContext, NextFunction } from '@feathersjs/feathers' +import { stripSlashes } from '@feathersjs/commons' export const authentication = () => { return (context: HookContext, next: NextFunction) => { - const { app, params, path, method, app: { authentication: service } } = context; + const { + app, + params, + path, + method, + app: { authentication: service } + } = context if (stripSlashes(service.options.path) === path && method === 'create') { - return next(); + return next() } - return Promise.resolve(app.get('authentication')).then(authResult => { - if (authResult) { - context.params = Object.assign({}, authResult, params); - } - }).then(next); - }; -}; + return Promise.resolve(app.get('authentication')) + .then((authResult) => { + if (authResult) { + context.params = Object.assign({}, authResult, params) + } + }) + .then(next) + } +} diff --git a/packages/authentication-client/src/hooks/index.ts b/packages/authentication-client/src/hooks/index.ts index 3165598426..ef7cf4ea53 100644 --- a/packages/authentication-client/src/hooks/index.ts +++ b/packages/authentication-client/src/hooks/index.ts @@ -1,2 +1,2 @@ -export { authentication } from './authentication'; -export { populateHeader } from './populate-header'; +export { authentication } from './authentication' +export { populateHeader } from './populate-header' diff --git a/packages/authentication-client/src/hooks/populate-header.ts b/packages/authentication-client/src/hooks/populate-header.ts index ebafe8811d..1b4776187a 100644 --- a/packages/authentication-client/src/hooks/populate-header.ts +++ b/packages/authentication-client/src/hooks/populate-header.ts @@ -1,20 +1,27 @@ -import { HookContext, NextFunction } from '@feathersjs/feathers'; +import { HookContext, NextFunction } from '@feathersjs/feathers' export const populateHeader = () => { return (context: HookContext, next: NextFunction) => { - const { app, params: { accessToken } } = context; - const authentication = app.authentication; + const { + app, + params: { accessToken } + } = context + const authentication = app.authentication // Set REST header if necessary if (app.rest && accessToken) { - const { scheme, header } = authentication.options; - const authHeader = `${scheme} ${accessToken}`; + const { scheme, header } = authentication.options + const authHeader = `${scheme} ${accessToken}` - context.params.headers = Object.assign({}, { - [header]: authHeader - }, context.params.headers); + context.params.headers = Object.assign( + {}, + { + [header]: authHeader + }, + context.params.headers + ) } - return next(); - }; -}; + return next() + } +} diff --git a/packages/authentication-client/src/index.ts b/packages/authentication-client/src/index.ts index 9ae2e4423b..674b0a0bb7 100644 --- a/packages/authentication-client/src/index.ts +++ b/packages/authentication-client/src/index.ts @@ -1,32 +1,37 @@ -import { AuthenticationClient, AuthenticationClientOptions } from './core'; -import * as hooks from './hooks'; -import { Application } from '@feathersjs/feathers'; -import { Storage, MemoryStorage, StorageWrapper } from './storage'; +import { AuthenticationClient, AuthenticationClientOptions } from './core' +import * as hooks from './hooks' +import { Application } from '@feathersjs/feathers' +import { Storage, MemoryStorage, StorageWrapper } from './storage' declare module '@feathersjs/feathers/lib/declarations' { - interface Application { // eslint-disable-line - io?: any; - rest?: any; - authentication: AuthenticationClient; - authenticate: AuthenticationClient['authenticate']; - reAuthenticate: AuthenticationClient['reAuthenticate']; - logout: AuthenticationClient['logout']; + // eslint-disable-next-line @typescript-eslint/no-unused-vars + interface Application { + // eslint-disable-line + io?: any + rest?: any + authentication: AuthenticationClient + authenticate: AuthenticationClient['authenticate'] + reAuthenticate: AuthenticationClient['reAuthenticate'] + logout: AuthenticationClient['logout'] } } export const getDefaultStorage = () => { try { - return new StorageWrapper(window.localStorage); + return new StorageWrapper(window.localStorage) } catch (error: any) {} - return new MemoryStorage(); -}; + return new MemoryStorage() +} -export { AuthenticationClient, AuthenticationClientOptions, Storage, MemoryStorage, hooks }; +export { AuthenticationClient, AuthenticationClientOptions, Storage, MemoryStorage, hooks } -export type ClientConstructor = new (app: Application, options: AuthenticationClientOptions) => AuthenticationClient; +export type ClientConstructor = new ( + app: Application, + options: AuthenticationClientOptions +) => AuthenticationClient -export const defaultStorage: Storage = getDefaultStorage(); +export const defaultStorage: Storage = getDefaultStorage() export const defaults: AuthenticationClientOptions = { header: 'Authorization', @@ -38,29 +43,26 @@ export const defaults: AuthenticationClientOptions = { path: '/authentication', Authentication: AuthenticationClient, storage: defaultStorage -}; +} const init = (_options: Partial = {}) => { - const options: AuthenticationClientOptions = Object.assign({}, defaults, _options); - const { Authentication } = options; + const options: AuthenticationClientOptions = Object.assign({}, defaults, _options) + const { Authentication } = options return (app: Application) => { - const authentication = new Authentication(app, options); + const authentication = new Authentication(app, options) - app.authentication = authentication; - app.authenticate = authentication.authenticate.bind(authentication); - app.reAuthenticate = authentication.reAuthenticate.bind(authentication); - app.logout = authentication.logout.bind(authentication); + app.authentication = authentication + app.authenticate = authentication.authenticate.bind(authentication) + app.reAuthenticate = authentication.reAuthenticate.bind(authentication) + app.logout = authentication.logout.bind(authentication) - app.hooks([ - hooks.authentication(), - hooks.populateHeader() - ]); - }; -}; + app.hooks([hooks.authentication(), hooks.populateHeader()]) + } +} -export default init; +export default init if (typeof module !== 'undefined') { - module.exports = Object.assign(init, module.exports); + module.exports = Object.assign(init, module.exports) } diff --git a/packages/authentication-client/src/storage.ts b/packages/authentication-client/src/storage.ts index 97f96b113c..39e6817455 100644 --- a/packages/authentication-client/src/storage.ts +++ b/packages/authentication-client/src/storage.ts @@ -1,49 +1,49 @@ export interface Storage { - getItem (key: string): any; - setItem? (key: string, value: any): any; - removeItem? (key: string): any; + getItem(key: string): any + setItem?(key: string, value: any): any + removeItem?(key: string): any } export class MemoryStorage implements Storage { - store: { [key: string]: any }; + store: { [key: string]: any } - constructor () { - this.store = {}; + constructor() { + this.store = {} } - getItem (key: string) { - return Promise.resolve(this.store[key]); + getItem(key: string) { + return Promise.resolve(this.store[key]) } - setItem (key: string, value: any) { - return Promise.resolve(this.store[key] = value); + setItem(key: string, value: any) { + return Promise.resolve((this.store[key] = value)) } - removeItem (key: string) { - const value = this.store[key]; + removeItem(key: string) { + const value = this.store[key] - delete this.store[key]; + delete this.store[key] - return Promise.resolve(value); + return Promise.resolve(value) } } export class StorageWrapper implements Storage { - storage: any; + storage: any - constructor (storage: any) { - this.storage = storage; + constructor(storage: any) { + this.storage = storage } - getItem (key: string) { - return Promise.resolve(this.storage.getItem(key)); + getItem(key: string) { + return Promise.resolve(this.storage.getItem(key)) } - setItem (key: string, value: any) { - return Promise.resolve(this.storage.setItem(key, value)); + setItem(key: string, value: any) { + return Promise.resolve(this.storage.setItem(key, value)) } - removeItem (key: string) { - return Promise.resolve(this.storage.removeItem(key)); + removeItem(key: string) { + return Promise.resolve(this.storage.removeItem(key)) } } diff --git a/packages/authentication-client/test/index.test.ts b/packages/authentication-client/test/index.test.ts index 593e85163c..de8f9210e6 100644 --- a/packages/authentication-client/test/index.test.ts +++ b/packages/authentication-client/test/index.test.ts @@ -1,228 +1,237 @@ -import assert from 'assert'; -import { feathers, Application } from '@feathersjs/feathers'; +import assert from 'assert' +import { feathers, Application } from '@feathersjs/feathers' -import client from '../src'; -import { AuthenticationClient } from '../src'; -import { NotAuthenticated } from '@feathersjs/errors'; +import client from '../src' +import { AuthenticationClient } from '../src' +import { NotAuthenticated } from '@feathersjs/errors' describe('@feathersjs/authentication-client', () => { - const accessToken = 'testing'; + const accessToken = 'testing' const user = { name: 'Test User' - }; - let app: Application; + } + let app: Application beforeEach(() => { - app = feathers(); + app = feathers() - app.configure(client()); + app.configure(client()) app.use('/authentication', { - create (data: any) { + create(data: any) { if (data.error) { - return Promise.reject(new Error('Did not work')); + return Promise.reject(new Error('Did not work')) } return Promise.resolve({ accessToken, data, user - }); + }) }, - remove (id) { + remove(id) { if (!app.get('authentication')) { - throw new NotAuthenticated('Not logged in'); + throw new NotAuthenticated('Not logged in') } - return Promise.resolve({ id }); + return Promise.resolve({ id }) } - }); + }) app.use('dummy', { - find (params) { - return Promise.resolve(params); + find(params) { + return Promise.resolve(params) } - }); - }); + }) + }) it('initializes', () => { - assert.ok(app.authentication instanceof AuthenticationClient); - assert.strictEqual(app.get('storage'), app.authentication.storage); - assert.strictEqual(typeof app.authenticate, 'function'); - assert.strictEqual(typeof app.logout, 'function'); - }); + assert.ok(app.authentication instanceof AuthenticationClient) + assert.strictEqual(app.get('storage'), app.authentication.storage) + assert.strictEqual(typeof app.authenticate, 'function') + assert.strictEqual(typeof app.logout, 'function') + }) it('setAccessToken, getAccessToken, removeAccessToken', async () => { - const auth = app.authentication; - const token = 'hi'; + const auth = app.authentication + const token = 'hi' - await auth.setAccessToken(token); + await auth.setAccessToken(token) - const res = await auth.getAccessToken(); + const res = await auth.getAccessToken() - assert.strictEqual(res, token); + assert.strictEqual(res, token) - await auth.removeAccessToken(); - assert.strictEqual(await auth.getAccessToken(), null); - }); + await auth.removeAccessToken() + assert.strictEqual(await auth.getAccessToken(), null) + }) it('getFromLocation', async () => { - const auth = app.authentication; - let dummyLocation = { hash: 'access_token=testing' } as Location; + const auth = app.authentication + let dummyLocation = { hash: 'access_token=testing' } as Location - let token = await auth.getFromLocation(dummyLocation); + let token = await auth.getFromLocation(dummyLocation) - assert.strictEqual(token, 'testing'); - assert.strictEqual(dummyLocation.hash, ''); + assert.strictEqual(token, 'testing') + assert.strictEqual(dummyLocation.hash, '') - dummyLocation.hash = 'a=b&access_token=otherTest&c=d'; - token = await auth.getFromLocation(dummyLocation); + dummyLocation.hash = 'a=b&access_token=otherTest&c=d' + token = await auth.getFromLocation(dummyLocation) - assert.strictEqual(token, 'otherTest'); - assert.strictEqual(dummyLocation.hash, 'a=b&c=d'); + assert.strictEqual(token, 'otherTest') + assert.strictEqual(dummyLocation.hash, 'a=b&c=d') - dummyLocation = { search: 'access_token=testing' } as Location; - token = await auth.getFromLocation(dummyLocation); + dummyLocation = { search: 'access_token=testing' } as Location + token = await auth.getFromLocation(dummyLocation) - assert.strictEqual(await auth.getFromLocation({} as Location), null); + assert.strictEqual(await auth.getFromLocation({} as Location), null) try { await auth.getFromLocation({ hash: 'error=Error Happened&x=y' - } as Location); - assert.fail('Should never get here'); + } as Location) + assert.fail('Should never get here') } catch (error: any) { - assert.strictEqual(error.name, 'OauthError'); - assert.strictEqual(error.message, 'Error Happened'); + assert.strictEqual(error.name, 'OauthError') + assert.strictEqual(error.message, 'Error Happened') } - }); + }) - it('authenticate, authentication hook, login event', () => { + it('authenticate, authentication hook, login event', async () => { const data = { strategy: 'testing' - }; + } - const promise = new Promise(resolve => { - app.once('login', resolve); - }); + const promise = new Promise((resolve) => { + app.once('login', resolve) + }) - app.authenticate(data); + app.authenticate(data) - return promise.then(result => { - assert.deepStrictEqual(result, { - accessToken, - data, - user - }); + const result = await promise - return app.authentication.getAccessToken(); - }).then(at => { - assert.strictEqual(at, accessToken, 'Set accessToken in storage'); + assert.deepStrictEqual(result, { + accessToken, + data, + user + }) - return Promise.resolve(app.get('storage').getItem('feathers-jwt')); - }).then(at => { - assert.strictEqual(at, accessToken, 'Set accessToken in storage'); + let at = await app.authentication.getAccessToken() - return app.service('dummy').find(); - }).then(result => { - assert.deepStrictEqual(result.accessToken, accessToken); - assert.deepStrictEqual(result.user, user); - }); - }); + assert.strictEqual(at, accessToken, 'Set accessToken in storage') - it('logout event', () => { - const promise = new Promise(resolve => app.once('logout', resolve)); + at = await Promise.resolve(app.get('storage').getItem('feathers-jwt')) - app.authenticate({ - strategy: 'testing' - }).then(() => app.logout()); + assert.strictEqual(at, accessToken, 'Set accessToken in storage') - return promise.then(result => { - assert.deepStrictEqual(result, { id: null }); - }); - }); + const found = await app.service('dummy').find() + assert.deepStrictEqual(found.accessToken, accessToken) + assert.deepStrictEqual(found.user, user) + }) - it('does not remove AccessToken on other errors', () => { - return app.authenticate({ - strategy: 'testing' - }).then(() => app.authenticate({ - strategy: 'testing' - })).then(() => app.authentication.getAccessToken()) - .then(at => assert.strictEqual(at, accessToken)); - }); + it('logout event', async () => { + const promise = new Promise((resolve) => app.once('logout', resolve)) + + app.authenticate({ strategy: 'testing' }).then(() => app.logout()) + + const result = await promise + + assert.deepStrictEqual(result, { id: null }) + }) + + it('does not remove AccessToken on other errors', async () => { + await app.authenticate({ strategy: 'testing' }) + await app.authenticate({ strategy: 'testing' }) + + const at = await app.authentication.getAccessToken() + + assert.strictEqual(at, accessToken) + }) it('logout when not logged in without error', async () => { - const result = await app.logout(); + const result = await app.logout() - assert.strictEqual(result, null); - }); + assert.strictEqual(result, null) + }) describe('reauthenticate', () => { - it('fails when no token in storage', () => { - return app.authentication.reAuthenticate().then(() => { - assert.fail('Should never get here'); - }).catch(error => { - assert.strictEqual(error.message, 'No accessToken found in storage'); - }); - }); - - it('reauthenticates when token is in storage', () => { + it('fails when no token in storage and resets authentication state', async () => { + await assert.rejects(() => app.authentication.reAuthenticate(), { + message: 'No accessToken found in storage' + }) + assert.ok(!app.get('authentication'), 'Reset authentication') + }) + + it('reauthenticates when token is in storage', async () => { const data = { strategy: 'testing' - }; + } - app.authenticate(data).then(result => { - assert.deepStrictEqual(result, { - accessToken, - data, - user - }); - - return result; - }).then(() => app.authentication.reAuthenticate()) - .then(() => - app.authentication.reset() - ).then(() => { - return Promise.resolve(app.get('storage').getItem('feathers-jwt')); - }).then(at => { - assert.strictEqual(at, accessToken, 'Set accessToken in storage'); - - return app.authentication.reAuthenticate(); - }).then(at => { - assert.deepStrictEqual(at, { - accessToken, - data: { strategy: 'jwt', accessToken: 'testing' }, - user - }); - - return app.logout(); - }).then(() => { - return Promise.resolve(app.get('storage').getItem('feathers-jwt')); - }).then(at => { - assert.ok(!at); - assert.ok(!app.get('authentication')); - }); - }); + const result = await app.authenticate(data) + + assert.deepStrictEqual(result, { + accessToken, + data, + user + }) + await app.authentication.reAuthenticate() + await app.authentication.reset() + + let at = await Promise.resolve(app.get('storage').getItem('feathers-jwt')) + + assert.strictEqual(at, accessToken, 'Set accessToken in storage') + + at = await app.authentication.reAuthenticate() + + assert.deepStrictEqual(at, { + accessToken, + data: { strategy: 'jwt', accessToken: 'testing' }, + user + }) + + await app.logout() + + at = await Promise.resolve(app.get('storage').getItem('feathers-jwt')) + assert.ok(!at) + assert.ok(!app.get('authentication')) + }) + + it('reAuthenticate works with parallel requests', async () => { + const data = { + strategy: 'testing' + } + + await app.authenticate(data) + await app.reAuthenticate() + await app.authentication.reset() + + app.reAuthenticate() + + const found = await app.service('dummy').find() + + assert.deepStrictEqual(found.accessToken, accessToken) + assert.deepStrictEqual(found.user, user) + }) it('reauthenticates using different strategy', async () => { - app.configure(client({ jwtStrategy: 'any' })); + app.configure(client({ jwtStrategy: 'any' })) const data = { strategy: 'testing' - }; + } - let result = await app.authenticate(data); + let result = await app.authenticate(data) assert.deepStrictEqual(result, { accessToken, data, user - }); + }) - result = await app.authentication.reAuthenticate(false, 'jwt'); + result = await app.authentication.reAuthenticate(false, 'jwt') assert.deepStrictEqual(result, { accessToken, data, user - }); + }) }) - }); -}); + }) +}) diff --git a/packages/authentication-client/test/integration/commons.ts b/packages/authentication-client/test/integration/commons.ts index 2d6bfeb3a0..b9eef46587 100644 --- a/packages/authentication-client/test/integration/commons.ts +++ b/packages/authentication-client/test/integration/commons.ts @@ -1,112 +1,129 @@ -import assert from 'assert'; -import { Application } from '@feathersjs/feathers'; -import '../../src'; +import assert from 'assert' +import { Application } from '@feathersjs/feathers' +import '../../src' -export default (getApp: () => Application, getClient: () => Application, { - provider, email, password -}: { provider: string, email: string, password: string }) => { +export default ( + getApp: () => Application, + getClient: () => Application, + { provider, email, password }: { provider: string; email: string; password: string } +) => { describe('common tests', () => { - let client: Application; - let user: any; + let client: Application + let user: any - before(() => getApp().service('users').create({ - email, password - }).then((result: any) => { - user = result; - })); + before(() => + getApp() + .service('users') + .create({ + email, + password + }) + .then((result: any) => { + user = result + }) + ) beforeEach(() => { - client = getClient(); - }); + client = getClient() + }) it('authenticates with local strategy', () => { - return client.authenticate({ - strategy: 'local', - email, - password - }).then(result => { - assert.ok(result.accessToken); - assert.strictEqual(result.authentication.strategy, 'local'); - assert.strictEqual(result.user.email, email); - }); - }); + return client + .authenticate({ + strategy: 'local', + email, + password + }) + .then((result) => { + assert.ok(result.accessToken) + assert.strictEqual(result.authentication.strategy, 'local') + assert.strictEqual(result.user.email, email) + }) + }) it('authentication with wrong credentials fails, does not maintain state', () => { - return client.authenticate({ - strategy: 'local', - email, - password: 'blabla' - }) + return client + .authenticate({ + strategy: 'local', + email, + password: 'blabla' + }) .then(() => assert.fail('Should never get here')) - .catch(error => { - assert.strictEqual(error.name, 'NotAuthenticated'); - assert.strictEqual(error.message, 'Invalid login'); - assert.ok(!client.get('authentication'), 'Reset client state'); - }); - }); + .catch((error) => { + assert.strictEqual(error.name, 'NotAuthenticated') + assert.strictEqual(error.message, 'Invalid login') + assert.ok(!client.get('authentication'), 'Reset client state') + }) + }) it('errors when not authenticated', () => { - return client.service('dummy').find() + return client + .service('dummy') + .find() .then(() => assert.fail('Should never get here')) .catch((error: any) => { - assert.strictEqual(error.name, 'NotAuthenticated'); - assert.strictEqual(error.code, 401); - assert.strictEqual(error.message, 'Not authenticated'); - }); - }); + assert.strictEqual(error.name, 'NotAuthenticated') + assert.strictEqual(error.code, 401) + assert.strictEqual(error.message, 'Not authenticated') + }) + }) it('authenticates and allows access', () => { - return client.authenticate({ - strategy: 'local', - email, - password - }).then(() => - client.service('dummy').find() - ).then(result => { - assert.strictEqual(result.provider, provider); - assert.ok(result.authentication); - assert.ok(result.authentication.payload); - assert.strictEqual(result.user.email, user.email); - assert.strictEqual(result.user.id, user.id); - }); - }); + return client + .authenticate({ + strategy: 'local', + email, + password + }) + .then(() => client.service('dummy').find()) + .then((result) => { + assert.strictEqual(result.provider, provider) + assert.ok(result.authentication) + assert.ok(result.authentication.payload) + assert.strictEqual(result.user.email, user.email) + assert.strictEqual(result.user.id, user.id) + }) + }) it('re-authenticates', () => { - return client.authenticate({ - strategy: 'local', - email, - password - }) + return client + .authenticate({ + strategy: 'local', + email, + password + }) .then(() => client.authentication.reset()) .then(() => client.authenticate()) .then(() => client.service('dummy').find()) - .then(result => { - assert.strictEqual(result.provider, provider); - assert.ok(result.authentication); - assert.ok(result.authentication.payload); - assert.strictEqual(result.user.email, user.email); - assert.strictEqual(result.user.id, user.id); - }); - }); + .then((result) => { + assert.strictEqual(result.provider, provider) + assert.ok(result.authentication) + assert.ok(result.authentication.payload) + assert.strictEqual(result.user.email, user.email) + assert.strictEqual(result.user.id, user.id) + }) + }) it('after logout does not allow subsequent access', () => { - return client.authenticate({ - strategy: 'local', - email, - password - }).then(() => client.logout()) - .then(result => { - assert.ok(result.accessToken); - assert.ok(result.user); + return client + .authenticate({ + strategy: 'local', + email, + password + }) + .then(() => client.logout()) + .then((result) => { + assert.ok(result.accessToken) + assert.ok(result.user) - return client.service('dummy').find(); + return client.service('dummy').find() }) .then(() => assert.fail('Should never get here')) - .catch(error => { - assert.strictEqual(error.name, 'NotAuthenticated'); - assert.strictEqual(error.code, 401); - assert.strictEqual(error.message, 'Not authenticated'); - }); - }); - }); -}; + .catch((error) => { + assert.strictEqual(error.name, 'NotAuthenticated') + assert.strictEqual(error.code, 401) + assert.strictEqual(error.message, 'Not authenticated') + }) + }) + }) +} diff --git a/packages/authentication-client/test/integration/express.test.ts b/packages/authentication-client/test/integration/express.test.ts index 7e0cc4b533..e5f7709c6b 100644 --- a/packages/authentication-client/test/integration/express.test.ts +++ b/packages/authentication-client/test/integration/express.test.ts @@ -1,37 +1,40 @@ -import axios from 'axios'; -import { Server } from 'http'; -import { feathers, Application as FeathersApplication } from '@feathersjs/feathers'; -import * as express from '@feathersjs/express'; -import rest from '@feathersjs/rest-client'; +import axios from 'axios' +import { Server } from 'http' +import { feathers, Application as FeathersApplication } from '@feathersjs/feathers' +import * as express from '@feathersjs/express' +import rest from '@feathersjs/rest-client' -import authClient from '../../src'; -import getApp from './fixture'; -import commonTests from './commons'; +import authClient from '../../src' +import getApp from './fixture' +import commonTests from './commons' describe('@feathersjs/authentication-client Express integration', () => { - let app: express.Application; - let server: Server; + let app: express.Application + let server: Server before(async () => { - const restApp = express.default(feathers()) + const restApp = express + .default(feathers()) .use(express.json()) .configure(express.rest()) - .use(express.parseAuthentication()); - app = getApp(restApp as unknown as FeathersApplication) as express.Application; - app.use(express.errorHandler()); + .use(express.parseAuthentication()) + app = getApp(restApp as unknown as FeathersApplication) as express.Application + app.use(express.errorHandler()) - server = await app.listen(9776); - }); + server = await app.listen(9776) + }) - after(done => server.close(() => done())); + after((done) => server.close(() => done())) - commonTests(() => app, () => { - return feathers() - .configure(rest('http://localhost:9776').axios(axios)) - .configure(authClient()); - }, { - email: 'expressauth@feathersjs.com', - password: 'secret', - provider: 'rest' - }); -}); + commonTests( + () => app, + () => { + return feathers().configure(rest('http://localhost:9776').axios(axios)).configure(authClient()) + }, + { + email: 'expressauth@feathersjs.com', + password: 'secret', + provider: 'rest' + } + ) +}) diff --git a/packages/authentication-client/test/integration/fixture.ts b/packages/authentication-client/test/integration/fixture.ts index 53950b1efc..1ecef9f9b0 100644 --- a/packages/authentication-client/test/integration/fixture.ts +++ b/packages/authentication-client/test/integration/fixture.ts @@ -1,62 +1,65 @@ -import { authenticate } from '@feathersjs/authentication'; -import { HookContext, Application } from '@feathersjs/feathers'; -import { memory } from '@feathersjs/memory'; -import { AuthenticationService, JWTStrategy } from '@feathersjs/authentication'; -import { LocalStrategy, hooks } from '@feathersjs/authentication-local'; +import { authenticate } from '@feathersjs/authentication' +import { HookContext, Application } from '@feathersjs/feathers' +import { memory } from '@feathersjs/memory' +import { AuthenticationService, JWTStrategy } from '@feathersjs/authentication' +import { LocalStrategy, hooks } from '@feathersjs/authentication-local' -const { hashPassword, protect } = hooks; +const { hashPassword, protect } = hooks export default (app: Application) => { - const authentication = new AuthenticationService(app); + const authentication = new AuthenticationService(app) app.set('authentication', { entity: 'user', service: 'users', secret: 'supersecret', - authStrategies: [ 'local', 'jwt' ], + authStrategies: ['local', 'jwt'], local: { usernameField: 'email', passwordField: 'password' } - }); + }) - authentication.register('jwt', new JWTStrategy()); - authentication.register('local', new LocalStrategy()); + authentication.register('jwt', new JWTStrategy()) + authentication.register('local', new LocalStrategy()) - app.use('/authentication', authentication); - app.use('/users', memory({ - paginate: { - default: 10, - max: 20 - } - })); + app.use('/authentication', authentication) + app.use( + '/users', + memory({ + paginate: { + default: 10, + max: 20 + } + }) + ) app.service('users').hooks({ before: { create: hashPassword('password') }, after: protect('password') - }); + }) app.use('/dummy', { - find (params) { - return Promise.resolve(params); + find(params) { + return Promise.resolve(params) } - }); + }) app.service('dummy').hooks({ before: authenticate('jwt') - }); + }) app.service('users').hooks({ - before (context: HookContext) { + before(context: HookContext) { if (context.id !== undefined && context.id !== null) { - context.id = parseInt(context.id as string, 10); + context.id = parseInt(context.id as string, 10) } - return context; + return context } - }); + }) - return app; -}; + return app +} diff --git a/packages/authentication-client/test/integration/socketio.test.ts b/packages/authentication-client/test/integration/socketio.test.ts index 0df89b1c5c..dc5f0789a7 100644 --- a/packages/authentication-client/test/integration/socketio.test.ts +++ b/packages/authentication-client/test/integration/socketio.test.ts @@ -1,36 +1,36 @@ -import { io } from 'socket.io-client'; -import assert from 'assert'; -import { feathers, Application } from '@feathersjs/feathers'; -import socketio from '@feathersjs/socketio'; -import socketioClient from '@feathersjs/socketio-client'; +import { io } from 'socket.io-client' +import assert from 'assert' +import { feathers, Application } from '@feathersjs/feathers' +import socketio from '@feathersjs/socketio' +import socketioClient from '@feathersjs/socketio-client' -import authClient from '../../src'; -import getApp from './fixture'; -import commonTests from './commons'; +import authClient from '../../src' +import getApp from './fixture' +import commonTests from './commons' describe('@feathersjs/authentication-client Socket.io integration', () => { - let app: Application; + let app: Application before(async () => { - app = getApp(feathers().configure(socketio())); + app = getApp(feathers().configure(socketio())) - await app.listen(9777); - }); + await app.listen(9777) + }) - after(done => app.io.close(() => done())); + after((done) => app.io.close(() => done())) it('allows to authenticate with handshake headers and sends login event', async () => { - const user = { email: 'authtest@example.com', password: 'alsosecret' }; + const user = { email: 'authtest@example.com', password: 'alsosecret' } - await app.service('users').create(user); + await app.service('users').create(user) const { accessToken } = await app.service('authentication').create({ strategy: 'local', ...user - }); + }) const socket = io('http://localhost:9777', { - transports: [ 'websocket' ], + transports: ['websocket'], transportOptions: { websocket: { extraHeaders: { @@ -38,31 +38,31 @@ describe('@feathersjs/authentication-client Socket.io integration', () => { } } } - }); - const authResult: any = await new Promise(resolve => - app.once('login', res => resolve(res)) - ); + }) + const authResult: any = await new Promise((resolve) => app.once('login', (res) => resolve(res))) - assert.strictEqual(authResult.accessToken, accessToken); + assert.strictEqual(authResult.accessToken, accessToken) const dummy: any = await new Promise((resolve, reject) => { - socket.emit('find', 'dummy', {}, (error: Error, page: any) => - error ? reject(error) : resolve(page) - ); - }); + socket.emit('find', 'dummy', {}, (error: Error, page: any) => (error ? reject(error) : resolve(page))) + }) - assert.strictEqual(dummy.user.email, user.email); - assert.strictEqual(dummy.authentication.accessToken, accessToken); - assert.strictEqual(dummy.headers.authorization, `Bearer ${accessToken}`); - }); + assert.strictEqual(dummy.user.email, user.email) + assert.strictEqual(dummy.authentication.accessToken, accessToken) + assert.strictEqual(dummy.headers.authorization, `Bearer ${accessToken}`) + }) - commonTests(() => app, () => { - return feathers() - .configure(socketioClient(io('http://localhost:9777'))) - .configure(authClient()); - }, { - email: 'socketioauth@feathersjs.com', - password: 'secretive', - provider: 'socketio' - }); -}); + commonTests( + () => app, + () => { + return feathers() + .configure(socketioClient(io('http://localhost:9777'))) + .configure(authClient()) + }, + { + email: 'socketioauth@feathersjs.com', + password: 'secretive', + provider: 'socketio' + } + ) +}) diff --git a/packages/authentication-local/CHANGELOG.md b/packages/authentication-local/CHANGELOG.md index eba3bd3ca7..4e386026ee 100644 --- a/packages/authentication-local/CHANGELOG.md +++ b/packages/authentication-local/CHANGELOG.md @@ -3,576 +3,406 @@ All notable changes to this project will be documented in this file. See [Conventional Commits](https://conventionalcommits.org) for commit guidelines. -# [5.0.0-pre.16](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.15...v5.0.0-pre.16) (2022-01-12) +# [5.0.0-pre.31](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.30...v5.0.0-pre.31) (2022-10-12) **Note:** Version bump only for package @feathersjs/authentication-local +# [5.0.0-pre.30](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.29...v5.0.0-pre.30) (2022-10-07) +### Features +- **core:** Allow to unregister services at runtime ([#2756](https://github.com/feathersjs/feathers/issues/2756)) ([d16601f](https://github.com/feathersjs/feathers/commit/d16601f2277dca5357866ffdefba2a611f6dc7fa)) +# [5.0.0-pre.29](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.28...v5.0.0-pre.29) (2022-09-16) -# [5.0.0-pre.15](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.14...v5.0.0-pre.15) (2021-11-27) +### Features + +- **authentication-oauth:** Koa and transport independent oAuth authentication ([#2737](https://github.com/feathersjs/feathers/issues/2737)) ([9231525](https://github.com/feathersjs/feathers/commit/9231525a24bb790ba9c5d940f2867a9c727691c9)) +# [5.0.0-pre.28](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.27...v5.0.0-pre.28) (2022-08-03) ### Bug Fixes -* **typescript:** Overall typing improvements ([#2478](https://github.com/feathersjs/feathers/issues/2478)) ([b8eb804](https://github.com/feathersjs/feathers/commit/b8eb804158556d9651a8607e3c3fda15e0bfd110)) +- **cli:** Improve generated application and client ([#2701](https://github.com/feathersjs/feathers/issues/2701)) ([bd55ffb](https://github.com/feathersjs/feathers/commit/bd55ffb812e89bf215f4515e7f137656ea888c3f)) +# [5.0.0-pre.27](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.26...v5.0.0-pre.27) (2022-07-13) +**Note:** Version bump only for package @feathersjs/authentication-local +# [5.0.0-pre.26](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.25...v5.0.0-pre.26) (2022-06-22) +**Note:** Version bump only for package @feathersjs/authentication-local -# [5.0.0-pre.14](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.13...v5.0.0-pre.14) (2021-10-13) +# [5.0.0-pre.25](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.24...v5.0.0-pre.25) (2022-06-22) **Note:** Version bump only for package @feathersjs/authentication-local +# [5.0.0-pre.24](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.23...v5.0.0-pre.24) (2022-06-21) +### Features +- **authentication-local:** Add passwordHash property resolver ([#2660](https://github.com/feathersjs/feathers/issues/2660)) ([b41279b](https://github.com/feathersjs/feathers/commit/b41279b55eea3771a6fa4983a37be2413287bbc6)) - -# [5.0.0-pre.13](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.12...v5.0.0-pre.13) (2021-10-13) +# [5.0.0-pre.23](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.22...v5.0.0-pre.23) (2022-06-06) **Note:** Version bump only for package @feathersjs/authentication-local +# [5.0.0-pre.22](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.21...v5.0.0-pre.22) (2022-05-24) +**Note:** Version bump only for package @feathersjs/authentication-local +# [5.0.0-pre.21](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.20...v5.0.0-pre.21) (2022-05-23) +**Note:** Version bump only for package @feathersjs/authentication-local -# [5.0.0-pre.12](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.11...v5.0.0-pre.12) (2021-10-12) +# [5.0.0-pre.20](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.19...v5.0.0-pre.20) (2022-05-04) -**Note:** Version bump only for package @feathersjs/authentication-local +### Bug Fixes +- **dependencies:** Lock monorepo package version numbers ([#2623](https://github.com/feathersjs/feathers/issues/2623)) ([5640c10](https://github.com/feathersjs/feathers/commit/5640c1020cc139994e695d658c08bad3494db507)) +# [5.0.0-pre.19](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.18...v5.0.0-pre.19) (2022-05-01) +### Features +- **typescript:** Improve adapter typings ([#2605](https://github.com/feathersjs/feathers/issues/2605)) ([3b2ca0a](https://github.com/feathersjs/feathers/commit/3b2ca0a6a8e03e8390272c4d7e930b4bffdaacf5)) -# [5.0.0-pre.11](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.10...v5.0.0-pre.11) (2021-10-06) +# [5.0.0-pre.18](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.17...v5.0.0-pre.18) (2022-04-11) **Note:** Version bump only for package @feathersjs/authentication-local +# [5.0.0-pre.17](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.16...v5.0.0-pre.17) (2022-02-15) +### Bug Fixes +- **hooks:** Allow all built-in hooks to be used the async and regular way ([#2559](https://github.com/feathersjs/feathers/issues/2559)) ([8f9f631](https://github.com/feathersjs/feathers/commit/8f9f631e0ce89de349207db72def84e7ab496a4a)) +# [5.0.0-pre.16](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.15...v5.0.0-pre.16) (2022-01-12) -# [5.0.0-pre.10](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.9...v5.0.0-pre.10) (2021-09-19) +**Note:** Version bump only for package @feathersjs/authentication-local +# [5.0.0-pre.15](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.14...v5.0.0-pre.15) (2021-11-27) ### Bug Fixes -* **authentication-local:** adds error handling for undefined/null password field ([#2444](https://github.com/feathersjs/feathers/issues/2444)) ([4323f98](https://github.com/feathersjs/feathers/commit/4323f9859a66a7fe3f7f15d81476bd81b735c226)) - - - - +- **typescript:** Overall typing improvements ([#2478](https://github.com/feathersjs/feathers/issues/2478)) ([b8eb804](https://github.com/feathersjs/feathers/commit/b8eb804158556d9651a8607e3c3fda15e0bfd110)) -# [5.0.0-pre.9](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.8...v5.0.0-pre.9) (2021-08-09) +# [5.0.0-pre.14](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.13...v5.0.0-pre.14) (2021-10-13) **Note:** Version bump only for package @feathersjs/authentication-local +# [5.0.0-pre.13](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.12...v5.0.0-pre.13) (2021-10-13) +**Note:** Version bump only for package @feathersjs/authentication-local +# [5.0.0-pre.12](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.11...v5.0.0-pre.12) (2021-10-12) +**Note:** Version bump only for package @feathersjs/authentication-local -# [5.0.0-pre.8](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.7...v5.0.0-pre.8) (2021-08-09) +# [5.0.0-pre.11](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.10...v5.0.0-pre.11) (2021-10-06) **Note:** Version bump only for package @feathersjs/authentication-local +# [5.0.0-pre.10](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.9...v5.0.0-pre.10) (2021-09-19) +### Bug Fixes +- **authentication-local:** adds error handling for undefined/null password field ([#2444](https://github.com/feathersjs/feathers/issues/2444)) ([4323f98](https://github.com/feathersjs/feathers/commit/4323f9859a66a7fe3f7f15d81476bd81b735c226)) - -# [5.0.0-pre.7](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.6...v5.0.0-pre.7) (2021-08-09) +# [5.0.0-pre.9](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.8...v5.0.0-pre.9) (2021-08-09) **Note:** Version bump only for package @feathersjs/authentication-local +# [5.0.0-pre.8](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.7...v5.0.0-pre.8) (2021-08-09) +**Note:** Version bump only for package @feathersjs/authentication-local +# [5.0.0-pre.7](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.6...v5.0.0-pre.7) (2021-08-09) +**Note:** Version bump only for package @feathersjs/authentication-local # [5.0.0-pre.6](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.5...v5.0.0-pre.6) (2021-08-08) **Note:** Version bump only for package @feathersjs/authentication-local - - - - # [5.0.0-pre.5](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.4...v5.0.0-pre.5) (2021-06-23) - ### Bug Fixes -* **hooks:** Migrate built-in hooks and allow backwards compatibility ([#2358](https://github.com/feathersjs/feathers/issues/2358)) ([759c5a1](https://github.com/feathersjs/feathers/commit/759c5a19327a731af965c3604119393b3d09a406)) -* **koa:** Use extended query parser for compatibility ([#2397](https://github.com/feathersjs/feathers/issues/2397)) ([b2944ba](https://github.com/feathersjs/feathers/commit/b2944bac3ec6d5ecc80dc518cd4e58093692db74)) - +- **hooks:** Migrate built-in hooks and allow backwards compatibility ([#2358](https://github.com/feathersjs/feathers/issues/2358)) ([759c5a1](https://github.com/feathersjs/feathers/commit/759c5a19327a731af965c3604119393b3d09a406)) +- **koa:** Use extended query parser for compatibility ([#2397](https://github.com/feathersjs/feathers/issues/2397)) ([b2944ba](https://github.com/feathersjs/feathers/commit/b2944bac3ec6d5ecc80dc518cd4e58093692db74)) ### Features -* **adapter-commons:** Add support for params.adapter option and move memory adapter to @feathersjs/memory ([#2367](https://github.com/feathersjs/feathers/issues/2367)) ([a43e7da](https://github.com/feathersjs/feathers/commit/a43e7da22b6b981a96d1321736ea9a0cb924fb4f)) - - - - +- **adapter-commons:** Add support for params.adapter option and move memory adapter to @feathersjs/memory ([#2367](https://github.com/feathersjs/feathers/issues/2367)) ([a43e7da](https://github.com/feathersjs/feathers/commit/a43e7da22b6b981a96d1321736ea9a0cb924fb4f)) # [5.0.0-pre.4](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.3...v5.0.0-pre.4) (2021-05-13) **Note:** Version bump only for package @feathersjs/authentication-local - - - - # [5.0.0-pre.3](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.2...v5.0.0-pre.3) (2021-04-21) - ### Bug Fixes -* **typescript:** Improve TypeScript backwards compatibility ([#2310](https://github.com/feathersjs/feathers/issues/2310)) ([f33be73](https://github.com/feathersjs/feathers/commit/f33be73fc46a533efb15df9aab0658e3240d3897)) - +- **typescript:** Improve TypeScript backwards compatibility ([#2310](https://github.com/feathersjs/feathers/issues/2310)) ([f33be73](https://github.com/feathersjs/feathers/commit/f33be73fc46a533efb15df9aab0658e3240d3897)) ### Features -* **dependencies:** Remove direct debug dependency ([#2296](https://github.com/feathersjs/feathers/issues/2296)) ([501d416](https://github.com/feathersjs/feathers/commit/501d4164d30c6a126906dc640cdfdc82207ba34a)) - - - - +- **dependencies:** Remove direct debug dependency ([#2296](https://github.com/feathersjs/feathers/issues/2296)) ([501d416](https://github.com/feathersjs/feathers/commit/501d4164d30c6a126906dc640cdfdc82207ba34a)) # [5.0.0-pre.2](https://github.com/feathersjs/feathers/compare/v5.0.0-beta.1...v5.0.0-pre.2) (2021-04-06) **Note:** Version bump only for package @feathersjs/authentication-local - - - - # [5.0.0-beta.1](https://github.com/feathersjs/feathers/compare/v5.0.0-beta.0...v5.0.0-beta.1) (2021-04-03) **Note:** Version bump only for package @feathersjs/authentication-local - - - - # [5.0.0-beta.0](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.1...v5.0.0-beta.0) (2021-03-28) - ### Bug Fixes -* Update Grant usage and other dependencies ([#2264](https://github.com/feathersjs/feathers/issues/2264)) ([7b0f8fa](https://github.com/feathersjs/feathers/commit/7b0f8fad252419ed0ad0bf259cdf3104d322ab60)) - +- Update Grant usage and other dependencies ([#2264](https://github.com/feathersjs/feathers/issues/2264)) ([7b0f8fa](https://github.com/feathersjs/feathers/commit/7b0f8fad252419ed0ad0bf259cdf3104d322ab60)) ### Features -* Feathers v5 core refactoring and features ([#2255](https://github.com/feathersjs/feathers/issues/2255)) ([2dafb7c](https://github.com/feathersjs/feathers/commit/2dafb7ce14ba57406aeec13d10ca45b1e709bee9)) - - - - +- Feathers v5 core refactoring and features ([#2255](https://github.com/feathersjs/feathers/issues/2255)) ([2dafb7c](https://github.com/feathersjs/feathers/commit/2dafb7ce14ba57406aeec13d10ca45b1e709bee9)) # [5.0.0-pre.1](https://github.com/feathersjs/feathers/compare/v4.5.11...v5.0.0-pre.1) (2020-12-17) - - # [5.0.0-pre.0](https://github.com/feathersjs/feathers/compare/v4.5.4...v5.0.0-pre.0) (2020-05-19) **Note:** Version bump only for package @feathersjs/authentication-local - - - - # [5.0.0-pre.0](https://github.com/feathersjs/feathers/compare/v4.5.4...v5.0.0-pre.0) (2020-05-19) **Note:** Version bump only for package @feathersjs/authentication-local - - ## [4.5.8](https://github.com/feathersjs/feathers/compare/v4.5.7...v4.5.8) (2020-08-12) **Note:** Version bump only for package @feathersjs/authentication-local - - - - ## [4.5.7](https://github.com/feathersjs/feathers/compare/v4.5.6...v4.5.7) (2020-07-24) - ### Bug Fixes -* **authentication:** Add JWT getEntityQuery ([#2013](https://github.com/feathersjs/feathers/issues/2013)) ([e0e7fb5](https://github.com/feathersjs/feathers/commit/e0e7fb5162940fe776731283b40026c61d9c8a33)) - - - - +- **authentication:** Add JWT getEntityQuery ([#2013](https://github.com/feathersjs/feathers/issues/2013)) ([e0e7fb5](https://github.com/feathersjs/feathers/commit/e0e7fb5162940fe776731283b40026c61d9c8a33)) ## [4.5.6](https://github.com/feathersjs/feathers/compare/v4.5.5...v4.5.6) (2020-07-12) **Note:** Version bump only for package @feathersjs/authentication-local - - - - ## [4.5.5](https://github.com/feathersjs/feathers/compare/v4.5.4...v4.5.5) (2020-07-11) **Note:** Version bump only for package @feathersjs/authentication-local - - - - ## [4.5.4](https://github.com/feathersjs/feathers/compare/v4.5.3...v4.5.4) (2020-04-29) - ### Bug Fixes -* **authentication-local:** Allow to hash passwords in array data ([#1936](https://github.com/feathersjs/feathers/issues/1936)) ([64705f5](https://github.com/feathersjs/feathers/commit/64705f5d9d4dc27f799da3a074efaf74379a3398)) - - - - +- **authentication-local:** Allow to hash passwords in array data ([#1936](https://github.com/feathersjs/feathers/issues/1936)) ([64705f5](https://github.com/feathersjs/feathers/commit/64705f5d9d4dc27f799da3a074efaf74379a3398)) ## [4.5.3](https://github.com/feathersjs/feathers/compare/v4.5.2...v4.5.3) (2020-04-17) **Note:** Version bump only for package @feathersjs/authentication-local - - - - ## [4.5.2](https://github.com/feathersjs/feathers/compare/v4.5.1...v4.5.2) (2020-03-04) - ### Bug Fixes -* **test:** typo in password ([#1797](https://github.com/feathersjs/feathers/issues/1797)) ([dfba6ec](https://github.com/feathersjs/feathers/commit/dfba6ec2f21adf3aa739218cf870eaaaa5df6e9c)) - - - - +- **test:** typo in password ([#1797](https://github.com/feathersjs/feathers/issues/1797)) ([dfba6ec](https://github.com/feathersjs/feathers/commit/dfba6ec2f21adf3aa739218cf870eaaaa5df6e9c)) ## [4.5.1](https://github.com/feathersjs/feathers/compare/v4.5.0...v4.5.1) (2020-01-24) **Note:** Version bump only for package @feathersjs/authentication-local - - - - # [4.5.0](https://github.com/feathersjs/feathers/compare/v4.4.3...v4.5.0) (2020-01-18) **Note:** Version bump only for package @feathersjs/authentication-local - - - - ## [4.4.3](https://github.com/feathersjs/feathers/compare/v4.4.1...v4.4.3) (2019-12-06) **Note:** Version bump only for package @feathersjs/authentication-local - - - - ## [4.4.1](https://github.com/feathersjs/feathers/compare/v4.4.0...v4.4.1) (2019-11-27) **Note:** Version bump only for package @feathersjs/authentication-local - - - - # [4.4.0](https://github.com/feathersjs/feathers/compare/v4.3.11...v4.4.0) (2019-11-27) - ### Features -* **authentication:** Add parseStrategies to allow separate strategies for creating JWTs and parsing headers ([#1708](https://github.com/feathersjs/feathers/issues/1708)) ([5e65629](https://github.com/feathersjs/feathers/commit/5e65629b924724c3e81d7c81df047e123d1c8bd7)) - - - - +- **authentication:** Add parseStrategies to allow separate strategies for creating JWTs and parsing headers ([#1708](https://github.com/feathersjs/feathers/issues/1708)) ([5e65629](https://github.com/feathersjs/feathers/commit/5e65629b924724c3e81d7c81df047e123d1c8bd7)) ## [4.3.11](https://github.com/feathersjs/feathers/compare/v4.3.10...v4.3.11) (2019-11-11) **Note:** Version bump only for package @feathersjs/authentication-local - - - - ## [4.3.10](https://github.com/feathersjs/feathers/compare/v4.3.9...v4.3.10) (2019-10-26) **Note:** Version bump only for package @feathersjs/authentication-local - - - - ## [4.3.9](https://github.com/feathersjs/feathers/compare/v4.3.8...v4.3.9) (2019-10-26) **Note:** Version bump only for package @feathersjs/authentication-local - - - - ## [4.3.7](https://github.com/feathersjs/feathers/compare/v4.3.6...v4.3.7) (2019-10-14) **Note:** Version bump only for package @feathersjs/authentication-local - - - - ## [4.3.5](https://github.com/feathersjs/feathers/compare/v4.3.4...v4.3.5) (2019-10-07) **Note:** Version bump only for package @feathersjs/authentication-local - - - - ## [4.3.4](https://github.com/feathersjs/feathers/compare/v4.3.3...v4.3.4) (2019-10-03) **Note:** Version bump only for package @feathersjs/authentication-local - - - - ## [4.3.3](https://github.com/feathersjs/feathers/compare/v4.3.2...v4.3.3) (2019-09-21) - ### Bug Fixes -* Small improvements in dependencies and code sturcture ([#1562](https://github.com/feathersjs/feathers/issues/1562)) ([42c13e2](https://github.com/feathersjs/feathers/commit/42c13e2)) - - - - +- Small improvements in dependencies and code sturcture ([#1562](https://github.com/feathersjs/feathers/issues/1562)) ([42c13e2](https://github.com/feathersjs/feathers/commit/42c13e2)) ## [4.3.2](https://github.com/feathersjs/feathers/compare/v4.3.1...v4.3.2) (2019-09-16) - ### Bug Fixes -* LocalStrategy authenticates without username ([#1560](https://github.com/feathersjs/feathers/issues/1560)) ([2b258fd](https://github.com/feathersjs/feathers/commit/2b258fd)), closes [#1559](https://github.com/feathersjs/feathers/issues/1559) - - - - +- LocalStrategy authenticates without username ([#1560](https://github.com/feathersjs/feathers/issues/1560)) ([2b258fd](https://github.com/feathersjs/feathers/commit/2b258fd)), closes [#1559](https://github.com/feathersjs/feathers/issues/1559) ## [4.3.1](https://github.com/feathersjs/feathers/compare/v4.3.0...v4.3.1) (2019-09-09) **Note:** Version bump only for package @feathersjs/authentication-local - - - - # [4.3.0](https://github.com/feathersjs/feathers/compare/v4.3.0-pre.4...v4.3.0) (2019-08-27) **Note:** Version bump only for package @feathersjs/authentication-local - - - - # [4.3.0-pre.4](https://github.com/feathersjs/feathers/compare/v4.3.0-pre.3...v4.3.0-pre.4) (2019-08-22) **Note:** Version bump only for package @feathersjs/authentication-local - - - - # [4.3.0-pre.3](https://github.com/feathersjs/feathers/compare/v4.3.0-pre.2...v4.3.0-pre.3) (2019-08-19) - ### Bug Fixes -* Update all dependencies ([7d53a00](https://github.com/feathersjs/feathers/commit/7d53a00)) - - - - +- Update all dependencies ([7d53a00](https://github.com/feathersjs/feathers/commit/7d53a00)) # [4.3.0-pre.2](https://github.com/feathersjs/feathers/compare/v4.3.0-pre.1...v4.3.0-pre.2) (2019-08-02) - ### Bug Fixes -* Add method to reliably get default authentication service ([#1470](https://github.com/feathersjs/feathers/issues/1470)) ([e542cb3](https://github.com/feathersjs/feathers/commit/e542cb3)) - - - - +- Add method to reliably get default authentication service ([#1470](https://github.com/feathersjs/feathers/issues/1470)) ([e542cb3](https://github.com/feathersjs/feathers/commit/e542cb3)) # [4.3.0-pre.1](https://github.com/feathersjs/feathers/compare/v4.0.0-pre.5...v4.3.0-pre.1) (2019-07-11) **Note:** Version bump only for package @feathersjs/authentication-local - - - - # [4.0.0-pre.5](https://github.com/feathersjs/feathers/compare/v4.0.0-pre.4...v4.0.0-pre.5) (2019-07-10) **Note:** Version bump only for package @feathersjs/authentication-local - - - - # [4.0.0-pre.4](https://github.com/feathersjs/feathers/compare/v4.0.0-pre.3...v4.0.0-pre.4) (2019-07-05) **Note:** Version bump only for package @feathersjs/authentication-local - - - - # [4.0.0-pre.3](https://github.com/feathersjs/feathers/compare/v4.0.0-pre.2...v4.0.0-pre.3) (2019-06-01) - ### Bug Fixes -* Update dependencies and fix tests ([#1373](https://github.com/feathersjs/feathers/issues/1373)) ([d743a7f](https://github.com/feathersjs/feathers/commit/d743a7f)) - - - - +- Update dependencies and fix tests ([#1373](https://github.com/feathersjs/feathers/issues/1373)) ([d743a7f](https://github.com/feathersjs/feathers/commit/d743a7f)) # [4.0.0-pre.2](https://github.com/feathersjs/feathers/compare/v4.0.0-pre.1...v4.0.0-pre.2) (2019-05-15) **Note:** Version bump only for package @feathersjs/authentication-local - - - - # [4.0.0-pre.1](https://github.com/feathersjs/feathers/compare/v4.0.0-pre.0...v4.0.0-pre.1) (2019-05-08) - ### Bug Fixes -* Always require strategy parameter in authentication ([#1327](https://github.com/feathersjs/feathers/issues/1327)) ([d4a8021](https://github.com/feathersjs/feathers/commit/d4a8021)) -* Improve authentication parameter handling ([#1333](https://github.com/feathersjs/feathers/issues/1333)) ([6e77204](https://github.com/feathersjs/feathers/commit/6e77204)) -* Merge httpStrategies and authStrategies option ([#1308](https://github.com/feathersjs/feathers/issues/1308)) ([afa4d55](https://github.com/feathersjs/feathers/commit/afa4d55)) -* Rename jwtStrategies option to authStrategies ([#1305](https://github.com/feathersjs/feathers/issues/1305)) ([4aee151](https://github.com/feathersjs/feathers/commit/4aee151)) - +- Always require strategy parameter in authentication ([#1327](https://github.com/feathersjs/feathers/issues/1327)) ([d4a8021](https://github.com/feathersjs/feathers/commit/d4a8021)) +- Improve authentication parameter handling ([#1333](https://github.com/feathersjs/feathers/issues/1333)) ([6e77204](https://github.com/feathersjs/feathers/commit/6e77204)) +- Merge httpStrategies and authStrategies option ([#1308](https://github.com/feathersjs/feathers/issues/1308)) ([afa4d55](https://github.com/feathersjs/feathers/commit/afa4d55)) +- Rename jwtStrategies option to authStrategies ([#1305](https://github.com/feathersjs/feathers/issues/1305)) ([4aee151](https://github.com/feathersjs/feathers/commit/4aee151)) ### Features -* Change and *JWT methods to *accessToken ([#1304](https://github.com/feathersjs/feathers/issues/1304)) ([5ac826b](https://github.com/feathersjs/feathers/commit/5ac826b)) - - - - +- Change and *JWT methods to *accessToken ([#1304](https://github.com/feathersjs/feathers/issues/1304)) ([5ac826b](https://github.com/feathersjs/feathers/commit/5ac826b)) # [4.0.0-pre.0](https://github.com/feathersjs/feathers/compare/v3.2.0-pre.1...v4.0.0-pre.0) (2019-04-21) - ### Bug Fixes -* Authentication core improvements ([#1260](https://github.com/feathersjs/feathers/issues/1260)) ([c5dc7a2](https://github.com/feathersjs/feathers/commit/c5dc7a2)) -* Make Mocha a proper devDependency for every repository ([#1053](https://github.com/feathersjs/feathers/issues/1053)) ([9974803](https://github.com/feathersjs/feathers/commit/9974803)) -* Update adapter common tests ([#1135](https://github.com/feathersjs/feathers/issues/1135)) ([8166dda](https://github.com/feathersjs/feathers/commit/8166dda)) -* Update all dependencies to latest ([#1206](https://github.com/feathersjs/feathers/issues/1206)) ([e51e0f6](https://github.com/feathersjs/feathers/commit/e51e0f6)) -* **package:** update debug to version 3.0.0 ([#31](https://github.com/feathersjs/feathers/issues/31)) ([f23d617](https://github.com/feathersjs/feathers/commit/f23d617)) - +- Authentication core improvements ([#1260](https://github.com/feathersjs/feathers/issues/1260)) ([c5dc7a2](https://github.com/feathersjs/feathers/commit/c5dc7a2)) +- Make Mocha a proper devDependency for every repository ([#1053](https://github.com/feathersjs/feathers/issues/1053)) ([9974803](https://github.com/feathersjs/feathers/commit/9974803)) +- Update adapter common tests ([#1135](https://github.com/feathersjs/feathers/issues/1135)) ([8166dda](https://github.com/feathersjs/feathers/commit/8166dda)) +- Update all dependencies to latest ([#1206](https://github.com/feathersjs/feathers/issues/1206)) ([e51e0f6](https://github.com/feathersjs/feathers/commit/e51e0f6)) +- **package:** update debug to version 3.0.0 ([#31](https://github.com/feathersjs/feathers/issues/31)) ([f23d617](https://github.com/feathersjs/feathers/commit/f23d617)) ### Features -* @feathersjs/authentication-oauth ([#1299](https://github.com/feathersjs/feathers/issues/1299)) ([656bae7](https://github.com/feathersjs/feathers/commit/656bae7)) -* Add AuthenticationBaseStrategy and make authentication option handling more explicit ([#1284](https://github.com/feathersjs/feathers/issues/1284)) ([2667d92](https://github.com/feathersjs/feathers/commit/2667d92)) -* Add TypeScript definitions ([#1275](https://github.com/feathersjs/feathers/issues/1275)) ([9dd6713](https://github.com/feathersjs/feathers/commit/9dd6713)) -* Authentication v3 core server implementation ([#1205](https://github.com/feathersjs/feathers/issues/1205)) ([1bd7591](https://github.com/feathersjs/feathers/commit/1bd7591)) -* Authentication v3 local authentication ([#1211](https://github.com/feathersjs/feathers/issues/1211)) ([0fa5f7c](https://github.com/feathersjs/feathers/commit/0fa5f7c)) - +- @feathersjs/authentication-oauth ([#1299](https://github.com/feathersjs/feathers/issues/1299)) ([656bae7](https://github.com/feathersjs/feathers/commit/656bae7)) +- Add AuthenticationBaseStrategy and make authentication option handling more explicit ([#1284](https://github.com/feathersjs/feathers/issues/1284)) ([2667d92](https://github.com/feathersjs/feathers/commit/2667d92)) +- Add TypeScript definitions ([#1275](https://github.com/feathersjs/feathers/issues/1275)) ([9dd6713](https://github.com/feathersjs/feathers/commit/9dd6713)) +- Authentication v3 core server implementation ([#1205](https://github.com/feathersjs/feathers/issues/1205)) ([1bd7591](https://github.com/feathersjs/feathers/commit/1bd7591)) +- Authentication v3 local authentication ([#1211](https://github.com/feathersjs/feathers/issues/1211)) ([0fa5f7c](https://github.com/feathersjs/feathers/commit/0fa5f7c)) ### BREAKING CHANGES -* Update authentication strategies for @feathersjs/authentication v3 - - - - +- Update authentication strategies for @feathersjs/authentication v3 ## [1.2.9](https://github.com/feathersjs/feathers/compare/@feathersjs/authentication-local@1.2.8...@feathersjs/authentication-local@1.2.9) (2019-01-02) - ### Bug Fixes -* Update adapter common tests ([#1135](https://github.com/feathersjs/feathers/issues/1135)) ([8166dda](https://github.com/feathersjs/feathers/commit/8166dda)) - - - - +- Update adapter common tests ([#1135](https://github.com/feathersjs/feathers/issues/1135)) ([8166dda](https://github.com/feathersjs/feathers/commit/8166dda)) + ## [1.2.8](https://github.com/feathersjs/feathers/compare/@feathersjs/authentication-local@1.2.7...@feathersjs/authentication-local@1.2.8) (2018-12-16) **Note:** Version bump only for package @feathersjs/authentication-local - - - - + ## [1.2.7](https://github.com/feathersjs/feathers/compare/@feathersjs/authentication-local@1.2.6...@feathersjs/authentication-local@1.2.7) (2018-10-26) **Note:** Version bump only for package @feathersjs/authentication-local - - - - -## [1.2.6](https://github.com/feathersjs/feathers/compare/@feathersjs/authentication-local@1.2.5...@feathersjs/authentication-local@1.2.6) (2018-10-25) +## [1.2.6](https://github.com/feathersjs/feathers/compare/@feathersjs/authentication-local@1.2.5...@feathersjs/authentication-local@1.2.6) (2018-10-25) ### Bug Fixes -* Make Mocha a proper devDependency for every repository ([#1053](https://github.com/feathersjs/feathers/issues/1053)) ([9974803](https://github.com/feathersjs/feathers/commit/9974803)) - - - - +- Make Mocha a proper devDependency for every repository ([#1053](https://github.com/feathersjs/feathers/issues/1053)) ([9974803](https://github.com/feathersjs/feathers/commit/9974803)) + ## [1.2.5](https://github.com/feathersjs/feathers/compare/@feathersjs/authentication-local@1.2.4...@feathersjs/authentication-local@1.2.5) (2018-09-21) **Note:** Version bump only for package @feathersjs/authentication-local - - - - + ## [1.2.4](https://github.com/feathersjs/feathers/compare/@feathersjs/authentication-local@1.2.3...@feathersjs/authentication-local@1.2.4) (2018-09-17) **Note:** Version bump only for package @feathersjs/authentication-local - - - - + ## [1.2.3](https://github.com/feathersjs/feathers/compare/@feathersjs/authentication-local@1.2.2...@feathersjs/authentication-local@1.2.3) (2018-09-02) **Note:** Version bump only for package @feathersjs/authentication-local + ## 1.2.2 - Migrate to Monorepo ([feathers#462](https://github.com/feathersjs/feathers/issues/462)) ## [v1.2.1](https://github.com/feathersjs/authentication-local/tree/v1.2.1) (2018-05-02) + [Full Changelog](https://github.com/feathersjs/authentication-local/compare/v1.2.0...v1.2.1) **Merged pull requests:** @@ -580,6 +410,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Make sure the original object is not modified [\#65](https://github.com/feathersjs/authentication-local/pull/65) ([daffl](https://github.com/daffl)) ## [v1.2.0](https://github.com/feathersjs/authentication-local/tree/v1.2.0) (2018-05-02) + [Full Changelog](https://github.com/feathersjs/authentication-local/compare/v1.1.3...v1.2.0) **Merged pull requests:** @@ -587,6 +418,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - added support for nested password fields option in hash password hook [\#64](https://github.com/feathersjs/authentication-local/pull/64) ([ThePesta](https://github.com/ThePesta)) ## [v1.1.3](https://github.com/feathersjs/authentication-local/tree/v1.1.3) (2018-04-20) + [Full Changelog](https://github.com/feathersjs/authentication-local/compare/v1.1.2...v1.1.3) **Merged pull requests:** @@ -594,6 +426,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Adding tests and calling to hasOwnProperty on Object.prototype instead of assuming valid prototype [\#63](https://github.com/feathersjs/authentication-local/pull/63) ([pmabres](https://github.com/pmabres)) ## [v1.1.2](https://github.com/feathersjs/authentication-local/tree/v1.1.2) (2018-04-15) + [Full Changelog](https://github.com/feathersjs/authentication-local/compare/v1.1.1...v1.1.2) **Closed issues:** @@ -605,6 +438,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Use latest version of Lodash [\#62](https://github.com/feathersjs/authentication-local/pull/62) ([daffl](https://github.com/daffl)) ## [v1.1.1](https://github.com/feathersjs/authentication-local/tree/v1.1.1) (2018-03-25) + [Full Changelog](https://github.com/feathersjs/authentication-local/compare/v1.1.0...v1.1.1) **Closed issues:** @@ -619,6 +453,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Update sinon-chai to the latest version 🚀 [\#57](https://github.com/feathersjs/authentication-local/pull/57) ([greenkeeper[bot]](https://github.com/apps/greenkeeper)) ## [v1.1.0](https://github.com/feathersjs/authentication-local/tree/v1.1.0) (2018-01-23) + [Full Changelog](https://github.com/feathersjs/authentication-local/compare/v1.0.4...v1.1.0) **Closed issues:** @@ -634,9 +469,11 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Update mocha to the latest version 🚀 [\#51](https://github.com/feathersjs/authentication-local/pull/51) ([greenkeeper[bot]](https://github.com/apps/greenkeeper)) ## [v1.0.4](https://github.com/feathersjs/authentication-local/tree/v1.0.4) (2018-01-03) + [Full Changelog](https://github.com/feathersjs/authentication-local/compare/v1.0.3...v1.0.4) ## [v1.0.3](https://github.com/feathersjs/authentication-local/tree/v1.0.3) (2018-01-03) + [Full Changelog](https://github.com/feathersjs/authentication-local/compare/v1.0.2...v1.0.3) **Closed issues:** @@ -649,6 +486,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Update semistandard to the latest version 🚀 [\#49](https://github.com/feathersjs/authentication-local/pull/49) ([greenkeeper[bot]](https://github.com/apps/greenkeeper)) ## [v1.0.2](https://github.com/feathersjs/authentication-local/tree/v1.0.2) (2017-12-06) + [Full Changelog](https://github.com/feathersjs/authentication-local/compare/v1.0.1...v1.0.2) **Closed issues:** @@ -661,6 +499,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Update feathers-memory to the latest version 🚀 [\#45](https://github.com/feathersjs/authentication-local/pull/45) ([greenkeeper[bot]](https://github.com/apps/greenkeeper)) ## [v1.0.1](https://github.com/feathersjs/authentication-local/tree/v1.0.1) (2017-11-16) + [Full Changelog](https://github.com/feathersjs/authentication-local/compare/v1.0.0...v1.0.1) **Merged pull requests:** @@ -669,6 +508,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Update @feathersjs/authentication to the latest version 🚀 [\#42](https://github.com/feathersjs/authentication-local/pull/42) ([greenkeeper[bot]](https://github.com/apps/greenkeeper)) ## [v1.0.0](https://github.com/feathersjs/authentication-local/tree/v1.0.0) (2017-11-01) + [Full Changelog](https://github.com/feathersjs/authentication-local/compare/v1.0.0-pre.2...v1.0.0) **Merged pull requests:** @@ -676,6 +516,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Update dependencies for release [\#41](https://github.com/feathersjs/authentication-local/pull/41) ([daffl](https://github.com/daffl)) ## [v1.0.0-pre.2](https://github.com/feathersjs/authentication-local/tree/v1.0.0-pre.2) (2017-10-27) + [Full Changelog](https://github.com/feathersjs/authentication-local/compare/v1.0.0-pre.1...v1.0.0-pre.2) **Merged pull requests:** @@ -683,6 +524,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Safely dispatch without password [\#40](https://github.com/feathersjs/authentication-local/pull/40) ([daffl](https://github.com/daffl)) ## [v1.0.0-pre.1](https://github.com/feathersjs/authentication-local/tree/v1.0.0-pre.1) (2017-10-25) + [Full Changelog](https://github.com/feathersjs/authentication-local/compare/v0.4.4...v1.0.0-pre.1) **Closed issues:** @@ -701,6 +543,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Update sinon to the latest version 🚀 [\#29](https://github.com/feathersjs/authentication-local/pull/29) ([greenkeeper[bot]](https://github.com/apps/greenkeeper)) ## [v0.4.4](https://github.com/feathersjs/authentication-local/tree/v0.4.4) (2017-08-11) + [Full Changelog](https://github.com/feathersjs/authentication-local/compare/v0.4.3...v0.4.4) **Closed issues:** @@ -715,6 +558,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Increase bcrypt cost factor, add future cost factor auto-optimization [\#30](https://github.com/feathersjs/authentication-local/pull/30) ([micaksica2](https://github.com/micaksica2)) ## [v0.4.3](https://github.com/feathersjs/authentication-local/tree/v0.4.3) (2017-06-22) + [Full Changelog](https://github.com/feathersjs/authentication-local/compare/v0.4.2...v0.4.3) **Closed issues:** @@ -726,9 +570,11 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - throw error if service.id is missing [\#27](https://github.com/feathersjs/authentication-local/pull/27) ([marshallswain](https://github.com/marshallswain)) ## [v0.4.2](https://github.com/feathersjs/authentication-local/tree/v0.4.2) (2017-06-22) + [Full Changelog](https://github.com/feathersjs/authentication-local/compare/v0.4.1...v0.4.2) ## [v0.4.1](https://github.com/feathersjs/authentication-local/tree/v0.4.1) (2017-06-22) + [Full Changelog](https://github.com/feathersjs/authentication-local/compare/v0.4.0...v0.4.1) **Merged pull requests:** @@ -736,6 +582,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Resolves \#14 - Passes Feathers params to service hooks [\#15](https://github.com/feathersjs/authentication-local/pull/15) ([thomas-p-wilson](https://github.com/thomas-p-wilson)) ## [v0.4.0](https://github.com/feathersjs/authentication-local/tree/v0.4.0) (2017-06-22) + [Full Changelog](https://github.com/feathersjs/authentication-local/compare/v0.3.4...v0.4.0) **Closed issues:** @@ -756,6 +603,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Update dependencies to enable Greenkeeper 🌴 [\#13](https://github.com/feathersjs/authentication-local/pull/13) ([greenkeeper[bot]](https://github.com/apps/greenkeeper)) ## [v0.3.4](https://github.com/feathersjs/authentication-local/tree/v0.3.4) (2017-03-28) + [Full Changelog](https://github.com/feathersjs/authentication-local/compare/v0.3.3...v0.3.4) **Closed issues:** @@ -767,6 +615,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Fix default authentication config name [\#12](https://github.com/feathersjs/authentication-local/pull/12) ([marshallswain](https://github.com/marshallswain)) ## [v0.3.3](https://github.com/feathersjs/authentication-local/tree/v0.3.3) (2017-01-27) + [Full Changelog](https://github.com/feathersjs/authentication-local/compare/v0.3.2...v0.3.3) **Closed issues:** @@ -779,9 +628,11 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Add support for dot notation, fix some whitespace [\#8](https://github.com/feathersjs/authentication-local/pull/8) ([elfey](https://github.com/elfey)) ## [v0.3.2](https://github.com/feathersjs/authentication-local/tree/v0.3.2) (2016-12-14) + [Full Changelog](https://github.com/feathersjs/authentication-local/compare/v0.3.1...v0.3.2) ## [v0.3.1](https://github.com/feathersjs/authentication-local/tree/v0.3.1) (2016-12-14) + [Full Changelog](https://github.com/feathersjs/authentication-local/compare/v0.3.0...v0.3.1) **Closed issues:** @@ -793,6 +644,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Document expected request data [\#6](https://github.com/feathersjs/authentication-local/pull/6) ([marshallswain](https://github.com/marshallswain)) ## [v0.3.0](https://github.com/feathersjs/authentication-local/tree/v0.3.0) (2016-11-23) + [Full Changelog](https://github.com/feathersjs/authentication-local/compare/v0.2.0...v0.3.0) **Closed issues:** @@ -805,9 +657,9 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Payload support [\#3](https://github.com/feathersjs/authentication-local/pull/3) ([ekryski](https://github.com/ekryski)) ## [v0.2.0](https://github.com/feathersjs/authentication-local/tree/v0.2.0) (2016-11-16) + [Full Changelog](https://github.com/feathersjs/authentication-local/compare/v0.1.0...v0.2.0) ## [v0.1.0](https://github.com/feathersjs/authentication-local/tree/v0.1.0) (2016-11-09) - -\* *This Change Log was automatically generated by [github_changelog_generator](https://github.com/skywinder/Github-Changelog-Generator)* +\* _This Change Log was automatically generated by [github_changelog_generator](https://github.com/skywinder/Github-Changelog-Generator)_ diff --git a/packages/authentication-local/LICENSE b/packages/authentication-local/LICENSE index 3f395cc665..59604f46f3 100644 --- a/packages/authentication-local/LICENSE +++ b/packages/authentication-local/LICENSE @@ -1,6 +1,6 @@ The MIT License (MIT) -Copyright (c) 2021 Feathers +Copyright (c) 2022 Feathers Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated documentation files (the "Software"), to deal diff --git a/packages/authentication-local/README.md b/packages/authentication-local/README.md index 89b1e2dc0d..5dc51c0cf3 100644 --- a/packages/authentication-local/README.md +++ b/packages/authentication-local/README.md @@ -1,8 +1,8 @@ # @feathersjs/authentication-local [![CI](https://github.com/feathersjs/feathers/workflows/CI/badge.svg)](https://github.com/feathersjs/feathers/actions?query=workflow%3ACI) -[![Dependency Status](https://img.shields.io/david/feathersjs/feathers.svg?style=flat-square&path=packages/authentication-local)](https://david-dm.org/feathersjs/feathers?path=packages/authentication-local) [![Download Status](https://img.shields.io/npm/dm/@feathersjs/authentication-local.svg?style=flat-square)](https://www.npmjs.com/package/@feathersjs/authentication-local) +[![Discord](https://badgen.net/badge/icon/discord?icon=discord&label)](https://discord.gg/qa8kez8QBx) > Local username and password authentication strategy for Feathers authentication @@ -18,6 +18,6 @@ Refer to the [Feathers local authentication API documentation](https://docs.feat ## License -Copyright (c) 2021 [Feathers contributors](https://github.com/feathersjs/feathers/graphs/contributors) +Copyright (c) 2022 [Feathers contributors](https://github.com/feathersjs/feathers/graphs/contributors) Licensed under the [MIT license](LICENSE). diff --git a/packages/authentication-local/package.json b/packages/authentication-local/package.json index fbd3fe2191..afeabcc77d 100644 --- a/packages/authentication-local/package.json +++ b/packages/authentication-local/package.json @@ -1,7 +1,7 @@ { "name": "@feathersjs/authentication-local", "description": "Local authentication strategy for @feathers/authentication", - "version": "5.0.0-pre.16", + "version": "5.0.0-pre.31", "homepage": "https://feathersjs.com", "main": "lib/", "types": "lib/", @@ -16,7 +16,8 @@ }, "repository": { "type": "git", - "url": "git://github.com/feathersjs/feathers.git" + "url": "git://github.com/feathersjs/feathers.git", + "directory": "packages/authentication-local" }, "author": { "name": "Feathers contributors", @@ -41,9 +42,9 @@ ], "scripts": { "prepublish": "npm run compile", - "compile": "shx rm -rf lib/ && tsc", - "test": "npm run compile && npm run mocha", - "mocha": "mocha --config ../../.mocharc.json --recursive test/**.test.ts test/**/*.test.ts" + "pack": "npm pack --pack-destination ../cli/test/build", + "compile": "shx rm -rf lib/ && tsc && npm run pack", + "test": "mocha --config ../../.mocharc.json --recursive test/**.test.ts test/**/*.test.ts" }, "directories": { "lib": "lib" @@ -52,23 +53,24 @@ "access": "public" }, "dependencies": { - "@feathersjs/authentication": "^5.0.0-pre.16", - "@feathersjs/commons": "^5.0.0-pre.16", - "@feathersjs/errors": "^5.0.0-pre.16", - "@feathersjs/feathers": "^5.0.0-pre.16", + "@feathersjs/authentication": "^5.0.0-pre.31", + "@feathersjs/commons": "^5.0.0-pre.31", + "@feathersjs/errors": "^5.0.0-pre.31", + "@feathersjs/feathers": "^5.0.0-pre.31", "bcryptjs": "^2.4.3", "lodash": "^4.17.21" }, "devDependencies": { - "@feathersjs/memory": "^5.0.0-pre.16", + "@feathersjs/memory": "^5.0.0-pre.31", + "@feathersjs/schema": "^5.0.0-pre.31", "@types/bcryptjs": "^2.4.2", - "@types/lodash": "^4.14.178", - "@types/mocha": "^9.0.0", - "@types/node": "^17.0.5", - "mocha": "^9.1.3", - "shx": "^0.3.3", - "ts-node": "^10.4.0", - "typescript": "^4.5.4" + "@types/lodash": "^4.14.186", + "@types/mocha": "^10.0.0", + "@types/node": "^18.8.2", + "mocha": "^10.0.0", + "shx": "^0.3.4", + "ts-node": "^10.9.1", + "typescript": "^4.8.4" }, - "gitHead": "f0cd227a82d159b528193bd33747c97684a48773" + "gitHead": "4500dbeb8cea566678cf88b3313a88efd93a2ed9" } diff --git a/packages/authentication-local/src/hooks/hash-password.ts b/packages/authentication-local/src/hooks/hash-password.ts index 7fa13237d6..acbccf24a5 100644 --- a/packages/authentication-local/src/hooks/hash-password.ts +++ b/packages/authentication-local/src/hooks/hash-password.ts @@ -1,59 +1,66 @@ -import get from 'lodash/get'; -import set from 'lodash/set'; -import cloneDeep from 'lodash/cloneDeep'; -import { BadRequest } from '@feathersjs/errors'; -import { createDebug } from '@feathersjs/commons'; -import { HookContext, NextFunction } from '@feathersjs/feathers'; -import { LocalStrategy } from '../strategy'; +import get from 'lodash/get' +import set from 'lodash/set' +import cloneDeep from 'lodash/cloneDeep' +import { BadRequest } from '@feathersjs/errors' +import { createDebug } from '@feathersjs/commons' +import { HookContext, NextFunction } from '@feathersjs/feathers' +import { LocalStrategy } from '../strategy' -const debug = createDebug('@feathersjs/authentication-local/hooks/hash-password'); +const debug = createDebug('@feathersjs/authentication-local/hooks/hash-password') export interface HashPasswordOptions { - authentication?: string; - strategy?: string; + authentication?: string + strategy?: string } -export default function hashPassword (field: string, options: HashPasswordOptions = {}) { +/** + * @deprecated Use Feathers schema resolvers and the `passwordHash` resolver instead + * @param field + * @param options + * @returns + */ +export default function hashPassword(field: string, options: HashPasswordOptions = {}) { if (!field) { - throw new Error('The hashPassword hook requires a field name option'); + throw new Error('The hashPassword hook requires a field name option') } return async (context: HookContext, next?: NextFunction) => { - const { app, data, params } = context; + const { app, data, params } = context if (data !== undefined) { - const authService = app.defaultAuthentication(options.authentication); - const { strategy = 'local' } = options; + const authService = app.defaultAuthentication(options.authentication) + const { strategy = 'local' } = options if (!authService || typeof authService.getStrategies !== 'function') { - throw new BadRequest('Could not find an authentication service to hash password'); + throw new BadRequest('Could not find an authentication service to hash password') } - const [ localStrategy ] = authService.getStrategies(strategy) as LocalStrategy[]; + const [localStrategy] = authService.getStrategies(strategy) as LocalStrategy[] if (!localStrategy || typeof localStrategy.hashPassword !== 'function') { - throw new BadRequest(`Could not find '${strategy}' strategy to hash password`); + throw new BadRequest(`Could not find '${strategy}' strategy to hash password`) } const addHashedPassword = async (data: any) => { - const password = get(data, field); + const password = get(data, field) if (password === undefined) { - debug(`hook.data.${field} is undefined, not hashing password`); - return data; + debug(`hook.data.${field} is undefined, not hashing password`) + return data } - const hashedPassword: string = await localStrategy.hashPassword(password, params); + const hashedPassword: string = await localStrategy.hashPassword(password, params) - return set(cloneDeep(data), field, hashedPassword); + return set(cloneDeep(data), field, hashedPassword) } - context.data = Array.isArray(data) ? await Promise.all(data.map(addHashedPassword)) : - await addHashedPassword(data); + context.data = Array.isArray(data) + ? await Promise.all(data.map(addHashedPassword)) + : await addHashedPassword(data) } if (typeof next === 'function') { - await next(); + return next() } - }; + } } diff --git a/packages/authentication-local/src/hooks/protect.ts b/packages/authentication-local/src/hooks/protect.ts index 5313f3f058..51ad69a8e3 100644 --- a/packages/authentication-local/src/hooks/protect.ts +++ b/packages/authentication-local/src/hooks/protect.ts @@ -1,37 +1,42 @@ -import omit from 'lodash/omit'; -import { HookContext, NextFunction } from '@feathersjs/feathers'; +import omit from 'lodash/omit' +import { HookContext, NextFunction } from '@feathersjs/feathers' -export default (...fields: string[]) => async (context: HookContext, next?: NextFunction) => { +/** + * @deprecated For reliable safe data representations use Feathers schema dispatch resolvers. + * See https://dove.docs.feathersjs.com/api/schema/resolvers.html#safe-data-resolvers for more information. + */ +export default (...fields: string[]) => { const o = (current: any) => { if (typeof current === 'object' && !Array.isArray(current)) { - const data = typeof current.toJSON === 'function' - ? current.toJSON() : current; + const data = typeof current.toJSON === 'function' ? current.toJSON() : current - return omit(data, fields); + return omit(data, fields) } - return current; - }; - - if (typeof next === 'function') { - await next(); + return current } - const result = context.dispatch || context.result; - - if (result) { - if (Array.isArray(result)) { - context.dispatch = result.map(o); - } else if (result.data && context.method === 'find') { - context.dispatch = Object.assign({}, result, { - data: result.data.map(o) - }); - } else { - context.dispatch = o(result); + return async (context: HookContext, next?: NextFunction) => { + if (typeof next === 'function') { + await next() } - if (context.params && context.params.provider) { - context.result = context.dispatch; + const result = context.dispatch || context.result + + if (result) { + if (Array.isArray(result)) { + context.dispatch = result.map(o) + } else if (result.data && context.method === 'find') { + context.dispatch = Object.assign({}, result, { + data: result.data.map(o) + }) + } else { + context.dispatch = o(result) + } + + if (context.params && context.params.provider) { + context.result = context.dispatch + } } } -}; +} diff --git a/packages/authentication-local/src/index.ts b/packages/authentication-local/src/index.ts index c713c66cc6..5e9b827e73 100644 --- a/packages/authentication-local/src/index.ts +++ b/packages/authentication-local/src/index.ts @@ -1,5 +1,28 @@ -import hashPassword from './hooks/hash-password'; -import protect from './hooks/protect'; +import { HookContext } from '@feathersjs/feathers' +import hashPassword from './hooks/hash-password' +import protect from './hooks/protect' +import { LocalStrategy } from './strategy' -export const hooks = { hashPassword, protect }; -export { LocalStrategy } from './strategy'; +export const hooks = { hashPassword, protect } +export { LocalStrategy } + +/** + * Returns as property resolver that hashes a given plain text password using a Local + * authentication strategy. + * + * @param options The authentication `service` and `strategy` name + * @returns + */ +export const passwordHash = + (options: { service?: string; strategy: string }) => + async >(value: string | undefined, _data: any, context: H) => { + if (value === undefined) { + return value + } + + const { app, params } = context + const authService = app.defaultAuthentication(options.service) + const localStrategy = authService.getStrategy(options.strategy) as LocalStrategy + + return localStrategy.hashPassword(value, params) + } diff --git a/packages/authentication-local/src/strategy.ts b/packages/authentication-local/src/strategy.ts index 354ca80d88..e1f579273c 100644 --- a/packages/authentication-local/src/strategy.ts +++ b/packages/authentication-local/src/strategy.ts @@ -1,30 +1,28 @@ /* eslint-disable @typescript-eslint/no-unused-vars */ -import bcrypt from 'bcryptjs'; -import get from 'lodash/get'; -import omit from 'lodash/omit'; -import { NotAuthenticated } from '@feathersjs/errors'; -import { Query, Params } from '@feathersjs/feathers'; -import { - AuthenticationRequest, AuthenticationBaseStrategy -} from '@feathersjs/authentication'; -import { createDebug } from '@feathersjs/commons'; - -const debug = createDebug('@feathersjs/authentication-local/strategy'); +import bcrypt from 'bcryptjs' +import get from 'lodash/get' +import omit from 'lodash/omit' +import { NotAuthenticated } from '@feathersjs/errors' +import { Query, Params } from '@feathersjs/feathers' +import { AuthenticationRequest, AuthenticationBaseStrategy } from '@feathersjs/authentication' +import { createDebug } from '@feathersjs/commons' + +const debug = createDebug('@feathersjs/authentication-local/strategy') export class LocalStrategy extends AuthenticationBaseStrategy { - verifyConfiguration () { - const config = this.configuration; + verifyConfiguration() { + const config = this.configuration - [ 'usernameField', 'passwordField' ].forEach(prop => { + ;['usernameField', 'passwordField'].forEach((prop) => { if (typeof config[prop] !== 'string') { - throw new Error(`'${this.name}' authentication strategy requires a '${prop}' setting`); + throw new Error(`'${this.name}' authentication strategy requires a '${prop}' setting`) } - }); + }) } - get configuration () { - const authConfig = this.authentication.configuration; - const config = super.configuration || {}; + get configuration() { + const authConfig = this.authentication.configuration + const config = super.configuration || {} return { hashSize: 10, @@ -35,105 +33,110 @@ export class LocalStrategy extends AuthenticationBaseStrategy { entityPasswordField: config.passwordField, entityUsernameField: config.usernameField, ...config - }; + } } - async getEntityQuery (query: Query, _params: Params) { + async getEntityQuery(query: Query, _params: Params) { return { $limit: 1, ...query - }; + } } - async findEntity (username: string, params: Params) { - const { entityUsernameField, errorMessage } = this.configuration; - if (!username) { // don't query for users without any condition set. - throw new NotAuthenticated(errorMessage); + async findEntity(username: string, params: Params) { + const { entityUsernameField, errorMessage } = this.configuration + if (!username) { + // don't query for users without any condition set. + throw new NotAuthenticated(errorMessage) } - const query = await this.getEntityQuery({ - [entityUsernameField]: username - }, params); + const query = await this.getEntityQuery( + { + [entityUsernameField]: username + }, + params + ) - const findParams = Object.assign({}, params, { query }); - const entityService = this.entityService; + const findParams = Object.assign({}, params, { query }) + const entityService = this.entityService - debug('Finding entity with query', params.query); + debug('Finding entity with query', params.query) - const result = await entityService.find(findParams); - const list = Array.isArray(result) ? result : result.data; + const result = await entityService.find(findParams) + const list = Array.isArray(result) ? result : result.data if (!Array.isArray(list) || list.length === 0) { - debug('No entity found'); + debug('No entity found') - throw new NotAuthenticated(errorMessage); + throw new NotAuthenticated(errorMessage) } - const [ entity ] = list; + const [entity] = list - return entity; + return entity } - async getEntity (result: any, params: Params) { - const entityService = this.entityService; - const { entityId = (entityService as any).id, entity } = this.configuration; + async getEntity(result: any, params: Params) { + const entityService = this.entityService + const { entityId = (entityService as any).id, entity } = this.configuration if (!entityId || result[entityId] === undefined) { - throw new NotAuthenticated('Could not get local entity'); + throw new NotAuthenticated('Could not get local entity') } if (!params.provider) { - return result; + return result } return entityService.get(result[entityId], { ...params, [entity]: result - }); + }) } - async comparePassword (entity: any, password: string) { - const { entityPasswordField, errorMessage } = this.configuration; + async comparePassword(entity: any, password: string) { + const { entityPasswordField, errorMessage } = this.configuration // find password in entity, this allows for dot notation - const hash = get(entity, entityPasswordField); + const hash = get(entity, entityPasswordField) if (!hash) { - debug(`Record is missing the '${entityPasswordField}' password field`); + debug(`Record is missing the '${entityPasswordField}' password field`) - throw new NotAuthenticated(errorMessage); + throw new NotAuthenticated(errorMessage) } - debug('Verifying password'); + debug('Verifying password') - const result = await bcrypt.compare(password, hash); + const result = await bcrypt.compare(password, hash) if (result) { - return entity; + return entity } - throw new NotAuthenticated(errorMessage); + throw new NotAuthenticated(errorMessage) } - async hashPassword (password: string, _params: Params) { - return bcrypt.hash(password, this.configuration.hashSize); + async hashPassword(password: string, _params: Params) { + return bcrypt.hash(password, this.configuration.hashSize) } - async authenticate (data: AuthenticationRequest, params: Params) { - const { passwordField, usernameField, entity, errorMessage } = this.configuration; - const username = data[usernameField]; - const password = data[passwordField]; + async authenticate(data: AuthenticationRequest, params: Params) { + const { passwordField, usernameField, entity, errorMessage } = this.configuration + const username = data[usernameField] + const password = data[passwordField] - if (!password) { // exit early if there is no password - throw new NotAuthenticated(errorMessage); + if (!password) { + // exit early if there is no password + throw new NotAuthenticated(errorMessage) } - const result = await this.findEntity(username, omit(params, 'provider')); + const result = await this.findEntity(username, omit(params, 'provider')) - await this.comparePassword(result, password); + await this.comparePassword(result, password) return { authentication: { strategy: this.name }, [entity]: await this.getEntity(result, params) - }; + } } } diff --git a/packages/authentication-local/test/fixture.ts b/packages/authentication-local/test/fixture.ts index 2bea3964f9..e7a20eebc0 100644 --- a/packages/authentication-local/test/fixture.ts +++ b/packages/authentication-local/test/fixture.ts @@ -1,57 +1,58 @@ -import { feathers } from '@feathersjs/feathers'; -import { memory, Service as MemoryService } from '@feathersjs/memory'; -import { AuthenticationService, JWTStrategy } from '@feathersjs/authentication'; +import { feathers } from '@feathersjs/feathers' +import { memory, MemoryService } from '@feathersjs/memory' +import { AuthenticationService, JWTStrategy } from '@feathersjs/authentication' -import { LocalStrategy, hooks } from '../src'; -const { hashPassword, protect } = hooks; +import { LocalStrategy, hooks } from '../src' +const { hashPassword, protect } = hooks export type ServiceTypes = { - authentication: AuthenticationService; - users: MemoryService; + authentication: AuthenticationService + users: MemoryService } -export function createApplication (app = feathers()) { - const authentication = new AuthenticationService(app); +export function createApplication(app = feathers()) { + const authentication = new AuthenticationService(app) app.set('authentication', { entity: 'user', service: 'users', secret: 'supersecret', - authStrategies: [ 'local', 'jwt' ], - parseStrategies: [ 'jwt' ], + authStrategies: ['local', 'jwt'], + parseStrategies: ['jwt'], local: { usernameField: 'email', passwordField: 'password' } - }); - - authentication.register('jwt', new JWTStrategy()); - authentication.register('local', new LocalStrategy()); - - app.use('authentication', authentication); - app.use('users', memory({ - multi: [ 'create' ], - paginate: { - default: 10, - max: 20 - } - })); + }) + + authentication.register('jwt', new JWTStrategy()) + authentication.register('local', new LocalStrategy()) + + app.use('authentication', authentication) + app.use( + 'users', + memory({ + multi: ['create'], + paginate: { + default: 10, + max: 20 + } + }) + ) - app.service('users').hooks([ - protect('password') - ]); + app.service('users').hooks([protect('password')]) app.service('users').hooks({ - create: [ - hashPassword('password') - ], - get: [ async (context, next) => { - await next(); - - if (context.params.provider) { - context.result.fromGet = true; + create: [hashPassword('password')], + get: [ + async (context, next) => { + await next() + + if (context.params.provider) { + context.result.fromGet = true + } } - }] - }); + ] + }) - return app; + return app } diff --git a/packages/authentication-local/test/hooks/hash-password.test.ts b/packages/authentication-local/test/hooks/hash-password.test.ts index 44df0ea810..fb45bc928e 100644 --- a/packages/authentication-local/test/hooks/hash-password.test.ts +++ b/packages/authentication-local/test/hooks/hash-password.test.ts @@ -1,91 +1,91 @@ -import assert from 'assert'; -import { Application } from '@feathersjs/feathers'; +/* eslint-disable @typescript-eslint/ban-ts-comment */ +import assert from 'assert' +import { Application } from '@feathersjs/feathers' -import { hooks } from '../../src'; -import { createApplication, ServiceTypes } from '../fixture'; +import { hooks } from '../../src' +import { createApplication, ServiceTypes } from '../fixture' -const { hashPassword } = hooks; +const { hashPassword } = hooks describe('@feathersjs/authentication-local/hooks/hash-password', () => { - let app: Application; + let app: Application beforeEach(() => { - app = createApplication(); - }); + app = createApplication() + }) it('throws error when no field provided', () => { try { // @ts-ignore - hashPassword(); - assert.fail('Should never get here'); + hashPassword() + assert.fail('Should never get here') } catch (error: any) { - assert.strictEqual(error.message, 'The hashPassword hook requires a field name option'); + assert.strictEqual(error.message, 'The hashPassword hook requires a field name option') } - }); + }) it('errors when authentication service does not exist', async () => { - delete app.services.authentication; + delete app.services.authentication try { await app.service('users').create({ email: 'dave@hashpassword.com', password: 'supersecret' - }); - assert.fail('Should never get here'); + }) + assert.fail('Should never get here') } catch (error: any) { - assert.strictEqual(error.message, - 'Could not find an authentication service to hash password' - ); + assert.strictEqual(error.message, 'Could not find an authentication service to hash password') } - }); + }) it('errors when authentication strategy does not exist', async () => { - delete app.services.authentication.strategies.local; + delete app.services.authentication.strategies.local try { await app.service('users').create({ email: 'dave@hashpassword.com', password: 'supersecret' - }); - assert.fail('Should never get here'); + }) + assert.fail('Should never get here') } catch (error: any) { - assert.strictEqual(error.message, - 'Could not find \'local\' strategy to hash password' - ); + assert.strictEqual(error.message, "Could not find 'local' strategy to hash password") } - }); + }) it('hashes password on field', async () => { - const password = 'supersecret'; + const password = 'supersecret' const user = await app.service('users').create({ email: 'dave@hashpassword.com', password - }); + }) - assert.notStrictEqual(user.password, password); - }); + assert.notStrictEqual(user.password, password) + }) it('hashes password on array data', async () => { - const password = 'supersecret'; + const password = 'supersecret' - const users = await app.service('users').create([{ - email: 'dave@hashpassword.com', - password - }, { - email: 'dave2@hashpassword.com', - password: 'secret2' - }]); - - assert.notStrictEqual(users[0].password, password); - assert.notStrictEqual(users[1].password, 'secret2'); - }); + const users = await app.service('users').create([ + { + email: 'dave@hashpassword.com', + password + }, + { + email: 'dave2@hashpassword.com', + password: 'secret2' + } + ]) + + assert.notStrictEqual(users[0].password, password) + assert.notStrictEqual(users[1].password, 'secret2') + }) it('does nothing when field is not present', async () => { const user = await app.service('users').create({ email: 'dave@hashpassword.com' - }); + }) - assert.strictEqual(user.password, undefined); - }); -}); + assert.strictEqual(user.password, undefined) + }) +}) diff --git a/packages/authentication-local/test/hooks/protect.test.ts b/packages/authentication-local/test/hooks/protect.test.ts index a5971644f5..20e1320c3d 100644 --- a/packages/authentication-local/test/hooks/protect.test.ts +++ b/packages/authentication-local/test/hooks/protect.test.ts @@ -1,188 +1,183 @@ -import assert from 'assert'; -import { HookContext } from '@feathersjs/feathers'; -import { hooks } from '../../src'; +import assert from 'assert' +import { HookContext } from '@feathersjs/feathers' +import { hooks } from '../../src' -const { protect } = hooks; +const { protect } = hooks -function testOmit (title: string, property: string) { +function testOmit(title: string, property: string) { describe(title, () => { - const fn = protect('password'); + const fn = protect('password') it('omits from object', async () => { const data = { email: 'test@user.com', password: 'supersecret' - }; + } const context = { [property]: data - } as unknown as HookContext; + } as unknown as HookContext - await fn(context); + await fn(context) assert.deepStrictEqual(context, { [property]: data, dispatch: { email: 'test@user.com' } - }); - }); + }) + }) it('omits from nested object', async () => { - const hook = protect('user.password'); + const hook = protect('user.password') const data = { user: { email: 'test@user.com', password: 'supersecret' } - }; + } const context = { [property]: data - } as unknown as HookContext; + } as unknown as HookContext - await hook(context); + await hook(context) assert.deepStrictEqual(context, { [property]: data, dispatch: { user: { email: 'test@user.com' } } - }); - }); + }) + }) it('handles `data` property only for find', async () => { const data = { email: 'test@user.com', password: 'supersecret', data: 'yes' - }; + } const context = { [property]: data - } as unknown as HookContext; + } as unknown as HookContext - await fn(context); + await fn(context) assert.deepStrictEqual(context, { [property]: data, dispatch: { email: 'test@user.com', data: 'yes' } - }); - }); + }) + }) it('uses .toJSON (#48)', async () => { class MyUser { - toJSON () { + toJSON() { return { email: 'test@user.com', password: 'supersecret' - }; + } } } - const data = new MyUser(); + const data = new MyUser() const context = { [property]: data - } as unknown as HookContext; + } as unknown as HookContext - await fn(context); + await fn(context) assert.deepStrictEqual(context, { [property]: data, dispatch: { email: 'test@user.com' } - }); - }); + }) + }) it('omits from array but only objects (#2053)', async () => { - const data = [{ - email: 'test1@user.com', - password: 'supersecret' - }, { - email: 'test2@user.com', - password: 'othersecret' - }, [ - 'one', 'two', 'three' - ], 'test']; + const data = [ + { + email: 'test1@user.com', + password: 'supersecret' + }, + { + email: 'test2@user.com', + password: 'othersecret' + }, + ['one', 'two', 'three'], + 'test' + ] const context = { [property]: data - } as unknown as HookContext; + } as unknown as HookContext - await fn(context); + await fn(context) assert.deepStrictEqual(context, { [property]: data, - dispatch: [ - { email: 'test1@user.com' }, - { email: 'test2@user.com' }, [ - 'one', 'two', 'three' - ], 'test' - ] - }); - }); + dispatch: [{ email: 'test1@user.com' }, { email: 'test2@user.com' }, ['one', 'two', 'three'], 'test'] + }) + }) it('omits from pagination object', async () => { const data = { total: 2, - data: [{ - email: 'test1@user.com', - password: 'supersecret' - }, { - email: 'test2@user.com', - password: 'othersecret' - }] - }; + data: [ + { + email: 'test1@user.com', + password: 'supersecret' + }, + { + email: 'test2@user.com', + password: 'othersecret' + } + ] + } const context = { method: 'find', [property]: data - } as unknown as HookContext; + } as unknown as HookContext - await fn(context); + await fn(context) assert.deepStrictEqual(context, { method: 'find', [property]: data, dispatch: { total: 2, - data: [ - { email: 'test1@user.com' }, - { email: 'test2@user.com' } - ] + data: [{ email: 'test1@user.com' }, { email: 'test2@user.com' }] } - }); - }); + }) + }) it('updates result if params.provider is set', async () => { - const data = [{ - email: 'test1@user.com', - password: 'supersecret' - }, { - email: 'test2@user.com', - password: 'othersecret' - }]; - const params = { provider: 'test' }; + const data = [ + { + email: 'test1@user.com', + password: 'supersecret' + }, + { + email: 'test2@user.com', + password: 'othersecret' + } + ] + const params = { provider: 'test' } const context = { [property]: data, params - } as unknown as HookContext; + } as unknown as HookContext - await fn(context); + await fn(context) assert.deepStrictEqual(context, { [property]: data, params, - result: [ - { email: 'test1@user.com' }, - { email: 'test2@user.com' } - ], - dispatch: [ - { email: 'test1@user.com' }, - { email: 'test2@user.com' } - ] - }); - }); - }); + result: [{ email: 'test1@user.com' }, { email: 'test2@user.com' }], + dispatch: [{ email: 'test1@user.com' }, { email: 'test2@user.com' }] + }) + }) + }) } describe('@feathersjs/authentication-local/hooks/protect', () => { it('does nothing when called with no result', async () => { - const fn = protect(); + const fn = protect() - assert.deepStrictEqual(await fn({} as any), undefined); - }); + assert.deepStrictEqual(await fn({} as any), undefined) + }) - testOmit('with hook.result', 'result'); - testOmit('with hook.dispatch already set', 'dispatch'); -}); + testOmit('with hook.result', 'result') + testOmit('with hook.dispatch already set', 'dispatch') +}) diff --git a/packages/authentication-local/test/strategy.test.ts b/packages/authentication-local/test/strategy.test.ts index d7da98cc3c..f700ae1ed9 100644 --- a/packages/authentication-local/test/strategy.test.ts +++ b/packages/authentication-local/test/strategy.test.ts @@ -1,172 +1,198 @@ -import assert from 'assert'; -import omit from 'lodash/omit'; -import { Application } from '@feathersjs/feathers'; +import assert from 'assert' +import omit from 'lodash/omit' +import { Application, HookContext } from '@feathersjs/feathers' +import { resolve } from '@feathersjs/schema' -import { LocalStrategy } from '../src'; -import { createApplication, ServiceTypes } from './fixture'; +import { LocalStrategy, passwordHash } from '../src' +import { createApplication, ServiceTypes } from './fixture' describe('@feathersjs/authentication-local/strategy', () => { - const password = 'localsecret'; - const email = 'localtester@feathersjs.com'; + const password = 'localsecret' + const email = 'localtester@feathersjs.com' - let app: Application; - let user: any; + let app: Application + let user: any beforeEach(async () => { - app = createApplication(); - user = await app.service('users').create({ email, password }); - }); + app = createApplication() + user = await app.service('users').create({ email, password }) + }) it('throw error when configuration is not set', () => { - const auth = app.service('authentication'); + const auth = app.service('authentication') try { - auth.register('something', new LocalStrategy()); - assert.fail('Should never get here'); + auth.register('something', new LocalStrategy()) + assert.fail('Should never get here') } catch (error: any) { - assert.strictEqual(error.message, - '\'something\' authentication strategy requires a \'usernameField\' setting' - ); + assert.strictEqual( + error.message, + "'something' authentication strategy requires a 'usernameField' setting" + ) } - }); + }) it('fails when entity not found', async () => { - const authService = app.service('authentication'); + const authService = app.service('authentication') try { await authService.create({ strategy: 'local', email: 'not in database', password - }); - assert.fail('Should never get here'); + }) + assert.fail('Should never get here') } catch (error: any) { - assert.strictEqual(error.name, 'NotAuthenticated'); - assert.strictEqual(error.message, 'Invalid login'); + assert.strictEqual(error.name, 'NotAuthenticated') + assert.strictEqual(error.message, 'Invalid login') } - }); + }) it('getEntity', async () => { - const [ strategy ] = app.service('authentication').getStrategies('local') as [ LocalStrategy ]; - let entity = await strategy.getEntity(user, {}); + const [strategy] = app.service('authentication').getStrategies('local') as [LocalStrategy] + let entity = await strategy.getEntity(user, {}) - assert.deepStrictEqual(entity, user); + assert.deepStrictEqual(entity, user) entity = await strategy.getEntity(user, { provider: 'testing' - }); + }) assert.deepStrictEqual(entity, { ...omit(user, 'password'), fromGet: true - }); + }) try { - await strategy.getEntity({}, {}); - assert.fail('Should never get here'); + await strategy.getEntity({}, {}) + assert.fail('Should never get here') } catch (error: any) { - assert.strictEqual(error.message, 'Could not get local entity'); + assert.strictEqual(error.message, 'Could not get local entity') } - }); + }) it('strategy fails when strategy is different', async () => { - const [ local ] = app.service('authentication').getStrategies('local'); - - await assert.rejects(() => local.authenticate({ - strategy: 'not-me', - password: 'dummy', - email - }, {}), { - name: 'NotAuthenticated', - message: 'Invalid login' - }); - }); + const [local] = app.service('authentication').getStrategies('local') + + await assert.rejects( + () => + local.authenticate( + { + strategy: 'not-me', + password: 'dummy', + email + }, + {} + ), + { + name: 'NotAuthenticated', + message: 'Invalid login' + } + ) + }) it('fails when password is wrong', async () => { - const authService = app.service('authentication'); + const authService = app.service('authentication') try { await authService.create({ strategy: 'local', email, password: 'dummy' - }); - assert.fail('Should never get here'); + }) + assert.fail('Should never get here') } catch (error: any) { - assert.strictEqual(error.name, 'NotAuthenticated'); - assert.strictEqual(error.message, 'Invalid login'); + assert.strictEqual(error.name, 'NotAuthenticated') + assert.strictEqual(error.message, 'Invalid login') } - }); + }) it('fails when password is not provided', async () => { - const authService = app.service('authentication'); + const authService = app.service('authentication') try { await authService.create({ strategy: 'local', - email, - }); - assert.fail('Should never get here'); + email + }) + assert.fail('Should never get here') } catch (error: any) { - assert.strictEqual(error.name, 'NotAuthenticated'); - assert.strictEqual(error.message, 'Invalid login'); + assert.strictEqual(error.name, 'NotAuthenticated') + assert.strictEqual(error.message, 'Invalid login') } - }); + }) it('fails when password field is not available', async () => { - const userEmail = 'someuser@localtest.com'; - const authService = app.service('authentication'); + const userEmail = 'someuser@localtest.com' + const authService = app.service('authentication') try { await app.service('users').create({ email: userEmail - }); + }) await authService.create({ strategy: 'local', password: 'dummy', email: userEmail - }); - assert.fail('Should never get here'); + }) + assert.fail('Should never get here') } catch (error: any) { - assert.strictEqual(error.name, 'NotAuthenticated'); - assert.strictEqual(error.message, 'Invalid login'); + assert.strictEqual(error.name, 'NotAuthenticated') + assert.strictEqual(error.message, 'Invalid login') } - }); + }) it('authenticates an existing user', async () => { - const authService = app.service('authentication'); + const authService = app.service('authentication') const authResult = await authService.create({ strategy: 'local', email, password - }); - const { accessToken } = authResult; + }) + const { accessToken } = authResult - assert.ok(accessToken); - assert.strictEqual(authResult.user.email, email); + assert.ok(accessToken) + assert.strictEqual(authResult.user.email, email) - const decoded = await authService.verifyAccessToken(accessToken); + const decoded = await authService.verifyAccessToken(accessToken) - assert.strictEqual(decoded.sub, `${user.id}`); - }); + assert.strictEqual(decoded.sub, `${user.id}`) + }) it('returns safe result when params.provider is set, works without pagination', async () => { - const authService = app.service('authentication'); - const authResult = await authService.create({ - strategy: 'local', - email, - password - }, { - provider: 'rest', - paginate: false - }); - const { accessToken } = authResult; - - assert.ok(accessToken); - assert.strictEqual(authResult.user.email, email); - assert.strictEqual(authResult.user.password, undefined); - assert.ok(authResult.user.fromGet); - - const decoded = await authService.verifyAccessToken(accessToken); - - assert.strictEqual(decoded.sub, `${user.id}`); - }); -}); + const authService = app.service('authentication') + const authResult = await authService.create( + { + strategy: 'local', + email, + password + }, + { + provider: 'rest', + paginate: false + } + ) + const { accessToken } = authResult + + assert.ok(accessToken) + assert.strictEqual(authResult.user.email, email) + assert.strictEqual(authResult.user.password, undefined) + assert.ok(authResult.user.fromGet) + + const decoded = await authService.verifyAccessToken(accessToken) + + assert.strictEqual(decoded.sub, `${user.id}`) + }) + + it('passwordHash property resolver', async () => { + const userResolver = resolve<{ password: string }, HookContext>({ + properties: { + password: passwordHash({ + strategy: 'local' + }) + } + }) + + const resolvedData = await userResolver.resolve({ password: 'supersecret' }, { app } as HookContext) + + assert.notStrictEqual(resolvedData.password, 'supersecret') + }) +}) diff --git a/packages/authentication-oauth/CHANGELOG.md b/packages/authentication-oauth/CHANGELOG.md index db9a37bc20..87d139663d 100644 --- a/packages/authentication-oauth/CHANGELOG.md +++ b/packages/authentication-oauth/CHANGELOG.md @@ -3,518 +3,379 @@ All notable changes to this project will be documented in this file. See [Conventional Commits](https://conventionalcommits.org) for commit guidelines. -# [5.0.0-pre.16](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.15...v5.0.0-pre.16) (2022-01-12) +# [5.0.0-pre.31](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.30...v5.0.0-pre.31) (2022-10-12) + +**Note:** Version bump only for package @feathersjs/authentication-oauth +# [5.0.0-pre.30](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.29...v5.0.0-pre.30) (2022-10-07) ### Bug Fixes -* **authentication-oauth:** OAuth redirect lost sometimes due to session store race ([#2514](https://github.com/feathersjs/feathers/issues/2514)) ([#2515](https://github.com/feathersjs/feathers/issues/2515)) ([6109c44](https://github.com/feathersjs/feathers/commit/6109c44428c6b8f6bb4e089be760ea1a4ef3d01e)) - +- **authentication-oauth:** Fix regression with prefix handling in OAuth ([#2773](https://github.com/feathersjs/feathers/issues/2773)) ([b1844b1](https://github.com/feathersjs/feathers/commit/b1844b1f27feeb7e66920ec9e318872857711834)) +### Features +- **core:** Allow to unregister services at runtime ([#2756](https://github.com/feathersjs/feathers/issues/2756)) ([d16601f](https://github.com/feathersjs/feathers/commit/d16601f2277dca5357866ffdefba2a611f6dc7fa)) +# [5.0.0-pre.29](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.28...v5.0.0-pre.29) (2022-09-16) -# [5.0.0-pre.15](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.14...v5.0.0-pre.15) (2021-11-27) +### Bug Fixes +- **authentication-oauth:** Fix oAuth origin and error handling ([#2752](https://github.com/feathersjs/feathers/issues/2752)) ([f7e1c33](https://github.com/feathersjs/feathers/commit/f7e1c33de1b7af0672a302d2ba6e15d997f0aa83)) ### Features -* **authentication-oauth:** Allow dynamic oAuth redirect ([#2469](https://github.com/feathersjs/feathers/issues/2469)) ([b7143d4](https://github.com/feathersjs/feathers/commit/b7143d4c0fbe961e714f79512be04449b9bbd7d9)) - +- Add CORS support to oAuth, Express, Koa and generated application ([#2744](https://github.com/feathersjs/feathers/issues/2744)) ([fd218f2](https://github.com/feathersjs/feathers/commit/fd218f289f8ca4c101e9938e8683e2efef6e8131)) +- **authentication-oauth:** Koa and transport independent oAuth authentication ([#2737](https://github.com/feathersjs/feathers/issues/2737)) ([9231525](https://github.com/feathersjs/feathers/commit/9231525a24bb790ba9c5d940f2867a9c727691c9)) +# [5.0.0-pre.28](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.27...v5.0.0-pre.28) (2022-08-03) +### Bug Fixes +- **cli:** Improve generated application and client ([#2701](https://github.com/feathersjs/feathers/issues/2701)) ([bd55ffb](https://github.com/feathersjs/feathers/commit/bd55ffb812e89bf215f4515e7f137656ea888c3f)) -# [5.0.0-pre.14](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.13...v5.0.0-pre.14) (2021-10-13) +# [5.0.0-pre.27](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.26...v5.0.0-pre.27) (2022-07-13) **Note:** Version bump only for package @feathersjs/authentication-oauth +# [5.0.0-pre.26](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.25...v5.0.0-pre.26) (2022-06-22) +**Note:** Version bump only for package @feathersjs/authentication-oauth - - -# [5.0.0-pre.13](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.12...v5.0.0-pre.13) (2021-10-13) +# [5.0.0-pre.25](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.24...v5.0.0-pre.25) (2022-06-22) **Note:** Version bump only for package @feathersjs/authentication-oauth +# [5.0.0-pre.24](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.23...v5.0.0-pre.24) (2022-06-21) + +### Bug Fixes +- **authentication-oauth:** Fix bug and properly set Grant defaults ([#2659](https://github.com/feathersjs/feathers/issues/2659)) ([cb93bb9](https://github.com/feathersjs/feathers/commit/cb93bb911fd92282424da2db805cd685b7e4a45b)) +### Features +- **cli:** Add typed client to a generated app ([#2669](https://github.com/feathersjs/feathers/issues/2669)) ([5b801b5](https://github.com/feathersjs/feathers/commit/5b801b5017ddc3eaa95622b539f51d605916bc86)) -# [5.0.0-pre.12](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.11...v5.0.0-pre.12) (2021-10-12) +# [5.0.0-pre.23](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.22...v5.0.0-pre.23) (2022-06-06) **Note:** Version bump only for package @feathersjs/authentication-oauth +# [5.0.0-pre.22](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.21...v5.0.0-pre.22) (2022-05-24) +**Note:** Version bump only for package @feathersjs/authentication-oauth +# [5.0.0-pre.21](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.20...v5.0.0-pre.21) (2022-05-23) +### Bug Fixes -# [5.0.0-pre.11](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.10...v5.0.0-pre.11) (2021-10-06) - -**Note:** Version bump only for package @feathersjs/authentication-oauth +- **authentication-oauth:** Fix regression using incorrect callback and redirect_uri ([#2631](https://github.com/feathersjs/feathers/issues/2631)) ([43d8a08](https://github.com/feathersjs/feathers/commit/43d8a082d7e1807f8a431c44a1dbd9b04c3af0d2)) +# [5.0.0-pre.20](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.19...v5.0.0-pre.20) (2022-05-04) +### Bug Fixes +- **authentication-oauth:** Don't send origins in Grant's config, as it will be considered another provider ([#2617](https://github.com/feathersjs/feathers/issues/2617)) ([ae3dddd](https://github.com/feathersjs/feathers/commit/ae3dddd8a654924465512d56b4651413912c6932)) +- **dependencies:** Lock monorepo package version numbers ([#2623](https://github.com/feathersjs/feathers/issues/2623)) ([5640c10](https://github.com/feathersjs/feathers/commit/5640c1020cc139994e695d658c08bad3494db507)) +# [5.0.0-pre.19](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.18...v5.0.0-pre.19) (2022-05-01) -# [5.0.0-pre.10](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.9...v5.0.0-pre.10) (2021-09-19) +### Bug Fixes -**Note:** Version bump only for package @feathersjs/authentication-oauth +- **authentication-oauth:** Fix issue with overriding the default Grant configuration ([#2615](https://github.com/feathersjs/feathers/issues/2615)) ([b345857](https://github.com/feathersjs/feathers/commit/b3458578532f9750de2940aeb8afdc75cb0b46f2)) +- **authentication-oauth:** Make oAuth authentication work with cookie-session ([#2614](https://github.com/feathersjs/feathers/issues/2614)) ([9f10bfc](https://github.com/feathersjs/feathers/commit/9f10bfc75083d5bcabea77cfb385aa3965cdf6d6)) +### Features +- **typescript:** Improve params and query typeability ([#2600](https://github.com/feathersjs/feathers/issues/2600)) ([df28b76](https://github.com/feathersjs/feathers/commit/df28b7619161f1df5e700326f52cca1a92dc5d28)) +# [5.0.0-pre.18](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.17...v5.0.0-pre.18) (2022-04-11) +**Note:** Version bump only for package @feathersjs/authentication-oauth -# [5.0.0-pre.9](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.8...v5.0.0-pre.9) (2021-08-09) +# [5.0.0-pre.17](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.16...v5.0.0-pre.17) (2022-02-15) **Note:** Version bump only for package @feathersjs/authentication-oauth +# [5.0.0-pre.16](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.15...v5.0.0-pre.16) (2022-01-12) +### Bug Fixes +- **authentication-oauth:** OAuth redirect lost sometimes due to session store race ([#2514](https://github.com/feathersjs/feathers/issues/2514)) ([#2515](https://github.com/feathersjs/feathers/issues/2515)) ([6109c44](https://github.com/feathersjs/feathers/commit/6109c44428c6b8f6bb4e089be760ea1a4ef3d01e)) +# [5.0.0-pre.15](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.14...v5.0.0-pre.15) (2021-11-27) -# [5.0.0-pre.8](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.7...v5.0.0-pre.8) (2021-08-09) +### Features + +- **authentication-oauth:** Allow dynamic oAuth redirect ([#2469](https://github.com/feathersjs/feathers/issues/2469)) ([b7143d4](https://github.com/feathersjs/feathers/commit/b7143d4c0fbe961e714f79512be04449b9bbd7d9)) + +# [5.0.0-pre.14](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.13...v5.0.0-pre.14) (2021-10-13) **Note:** Version bump only for package @feathersjs/authentication-oauth +# [5.0.0-pre.13](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.12...v5.0.0-pre.13) (2021-10-13) +**Note:** Version bump only for package @feathersjs/authentication-oauth +# [5.0.0-pre.12](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.11...v5.0.0-pre.12) (2021-10-12) +**Note:** Version bump only for package @feathersjs/authentication-oauth -# [5.0.0-pre.7](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.6...v5.0.0-pre.7) (2021-08-09) +# [5.0.0-pre.11](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.10...v5.0.0-pre.11) (2021-10-06) **Note:** Version bump only for package @feathersjs/authentication-oauth +# [5.0.0-pre.10](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.9...v5.0.0-pre.10) (2021-09-19) +**Note:** Version bump only for package @feathersjs/authentication-oauth +# [5.0.0-pre.9](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.8...v5.0.0-pre.9) (2021-08-09) +**Note:** Version bump only for package @feathersjs/authentication-oauth -# [5.0.0-pre.6](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.5...v5.0.0-pre.6) (2021-08-08) +# [5.0.0-pre.8](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.7...v5.0.0-pre.8) (2021-08-09) **Note:** Version bump only for package @feathersjs/authentication-oauth +# [5.0.0-pre.7](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.6...v5.0.0-pre.7) (2021-08-09) +**Note:** Version bump only for package @feathersjs/authentication-oauth +# [5.0.0-pre.6](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.5...v5.0.0-pre.6) (2021-08-08) +**Note:** Version bump only for package @feathersjs/authentication-oauth # [5.0.0-pre.5](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.4...v5.0.0-pre.5) (2021-06-23) - ### Bug Fixes -* **authentication-oauth:** Omit query from internal calls ([#2398](https://github.com/feathersjs/feathers/issues/2398)) ([04c7c83](https://github.com/feathersjs/feathers/commit/04c7c83eeaa6a7466c84b958071b468ed42f0b0f)) -* **koa:** Use extended query parser for compatibility ([#2397](https://github.com/feathersjs/feathers/issues/2397)) ([b2944ba](https://github.com/feathersjs/feathers/commit/b2944bac3ec6d5ecc80dc518cd4e58093692db74)) - +- **authentication-oauth:** Omit query from internal calls ([#2398](https://github.com/feathersjs/feathers/issues/2398)) ([04c7c83](https://github.com/feathersjs/feathers/commit/04c7c83eeaa6a7466c84b958071b468ed42f0b0f)) +- **koa:** Use extended query parser for compatibility ([#2397](https://github.com/feathersjs/feathers/issues/2397)) ([b2944ba](https://github.com/feathersjs/feathers/commit/b2944bac3ec6d5ecc80dc518cd4e58093692db74)) ### Features -* **adapter-commons:** Add support for params.adapter option and move memory adapter to @feathersjs/memory ([#2367](https://github.com/feathersjs/feathers/issues/2367)) ([a43e7da](https://github.com/feathersjs/feathers/commit/a43e7da22b6b981a96d1321736ea9a0cb924fb4f)) - - - - +- **adapter-commons:** Add support for params.adapter option and move memory adapter to @feathersjs/memory ([#2367](https://github.com/feathersjs/feathers/issues/2367)) ([a43e7da](https://github.com/feathersjs/feathers/commit/a43e7da22b6b981a96d1321736ea9a0cb924fb4f)) # [5.0.0-pre.4](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.3...v5.0.0-pre.4) (2021-05-13) **Note:** Version bump only for package @feathersjs/authentication-oauth - - - - # [5.0.0-pre.3](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.2...v5.0.0-pre.3) (2021-04-21) - ### Bug Fixes -* **typescript:** Improve TypeScript backwards compatibility ([#2310](https://github.com/feathersjs/feathers/issues/2310)) ([f33be73](https://github.com/feathersjs/feathers/commit/f33be73fc46a533efb15df9aab0658e3240d3897)) - +- **typescript:** Improve TypeScript backwards compatibility ([#2310](https://github.com/feathersjs/feathers/issues/2310)) ([f33be73](https://github.com/feathersjs/feathers/commit/f33be73fc46a533efb15df9aab0658e3240d3897)) ### Features -* **dependencies:** Remove direct debug dependency ([#2296](https://github.com/feathersjs/feathers/issues/2296)) ([501d416](https://github.com/feathersjs/feathers/commit/501d4164d30c6a126906dc640cdfdc82207ba34a)) - - - - +- **dependencies:** Remove direct debug dependency ([#2296](https://github.com/feathersjs/feathers/issues/2296)) ([501d416](https://github.com/feathersjs/feathers/commit/501d4164d30c6a126906dc640cdfdc82207ba34a)) # [5.0.0-pre.2](https://github.com/feathersjs/feathers/compare/v5.0.0-beta.1...v5.0.0-pre.2) (2021-04-06) **Note:** Version bump only for package @feathersjs/authentication-oauth - - - - # [5.0.0-beta.1](https://github.com/feathersjs/feathers/compare/v5.0.0-beta.0...v5.0.0-beta.1) (2021-04-03) **Note:** Version bump only for package @feathersjs/authentication-oauth - - - - # [5.0.0-beta.0](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.1...v5.0.0-beta.0) (2021-03-28) - ### Bug Fixes -* Update Grant usage and other dependencies ([#2264](https://github.com/feathersjs/feathers/issues/2264)) ([7b0f8fa](https://github.com/feathersjs/feathers/commit/7b0f8fad252419ed0ad0bf259cdf3104d322ab60)) - +- Update Grant usage and other dependencies ([#2264](https://github.com/feathersjs/feathers/issues/2264)) ([7b0f8fa](https://github.com/feathersjs/feathers/commit/7b0f8fad252419ed0ad0bf259cdf3104d322ab60)) ### Features -* Feathers v5 core refactoring and features ([#2255](https://github.com/feathersjs/feathers/issues/2255)) ([2dafb7c](https://github.com/feathersjs/feathers/commit/2dafb7ce14ba57406aeec13d10ca45b1e709bee9)) - - - - +- Feathers v5 core refactoring and features ([#2255](https://github.com/feathersjs/feathers/issues/2255)) ([2dafb7c](https://github.com/feathersjs/feathers/commit/2dafb7ce14ba57406aeec13d10ca45b1e709bee9)) # [5.0.0-pre.1](https://github.com/feathersjs/feathers/compare/v4.5.11...v5.0.0-pre.1) (2020-12-17) - - # [5.0.0-pre.0](https://github.com/feathersjs/feathers/compare/v4.5.4...v5.0.0-pre.0) (2020-05-19) **Note:** Version bump only for package @feathersjs/authentication-oauth - - - - # [5.0.0-pre.0](https://github.com/feathersjs/feathers/compare/v4.5.4...v5.0.0-pre.0) (2020-05-19) **Note:** Version bump only for package @feathersjs/authentication-oauth - - ## [4.5.9](https://github.com/feathersjs/feathers/compare/v4.5.8...v4.5.9) (2020-10-09) - ### Bug Fixes -* **authentication-oauth:** Always end session after oAuth flows are finished ([#2087](https://github.com/feathersjs/feathers/issues/2087)) ([d219d0d](https://github.com/feathersjs/feathers/commit/d219d0d89c5e45aa289dd67cb0c8bdc05044c846)) - - - - +- **authentication-oauth:** Always end session after oAuth flows are finished ([#2087](https://github.com/feathersjs/feathers/issues/2087)) ([d219d0d](https://github.com/feathersjs/feathers/commit/d219d0d89c5e45aa289dd67cb0c8bdc05044c846)) ## [4.5.8](https://github.com/feathersjs/feathers/compare/v4.5.7...v4.5.8) (2020-08-12) **Note:** Version bump only for package @feathersjs/authentication-oauth - - - - ## [4.5.7](https://github.com/feathersjs/feathers/compare/v4.5.6...v4.5.7) (2020-07-24) - ### Bug Fixes -* **typescript:** Revert add overload types for `find` service methods ([#1972](https://github.com/feathersjs/feathers/issues/1972))" ([#2025](https://github.com/feathersjs/feathers/issues/2025)) ([a9501ac](https://github.com/feathersjs/feathers/commit/a9501acb4d3ef58dfb87d62c57a9bf76569da281)) - - - - +- **typescript:** Revert add overload types for `find` service methods ([#1972](https://github.com/feathersjs/feathers/issues/1972))" ([#2025](https://github.com/feathersjs/feathers/issues/2025)) ([a9501ac](https://github.com/feathersjs/feathers/commit/a9501acb4d3ef58dfb87d62c57a9bf76569da281)) ## [4.5.6](https://github.com/feathersjs/feathers/compare/v4.5.5...v4.5.6) (2020-07-12) **Note:** Version bump only for package @feathersjs/authentication-oauth - - - - ## [4.5.5](https://github.com/feathersjs/feathers/compare/v4.5.4...v4.5.5) (2020-07-11) - ### Bug Fixes -* **authentication-oauth:** Updated typings for projects with strictNullChecks ([#1941](https://github.com/feathersjs/feathers/issues/1941)) ([be91206](https://github.com/feathersjs/feathers/commit/be91206e3dba1e65a81412b7aa636bece3ab4aa2)) -* **typescript:** add overload types for `find` service methods ([#1972](https://github.com/feathersjs/feathers/issues/1972)) ([ef55af0](https://github.com/feathersjs/feathers/commit/ef55af088d05d9d36aba9d9f8d6c2c908a4f20dd)) - - - - +- **authentication-oauth:** Updated typings for projects with strictNullChecks ([#1941](https://github.com/feathersjs/feathers/issues/1941)) ([be91206](https://github.com/feathersjs/feathers/commit/be91206e3dba1e65a81412b7aa636bece3ab4aa2)) +- **typescript:** add overload types for `find` service methods ([#1972](https://github.com/feathersjs/feathers/issues/1972)) ([ef55af0](https://github.com/feathersjs/feathers/commit/ef55af088d05d9d36aba9d9f8d6c2c908a4f20dd)) ## [4.5.4](https://github.com/feathersjs/feathers/compare/v4.5.3...v4.5.4) (2020-04-29) - ### Bug Fixes -* **authentication-oauth:** Add getEntity method to oAuth authentication and remove provider field for other calls ([#1935](https://github.com/feathersjs/feathers/issues/1935)) ([d925c1b](https://github.com/feathersjs/feathers/commit/d925c1bd193b5c19cb23a246f04fc46d0429fc75)) - - - - +- **authentication-oauth:** Add getEntity method to oAuth authentication and remove provider field for other calls ([#1935](https://github.com/feathersjs/feathers/issues/1935)) ([d925c1b](https://github.com/feathersjs/feathers/commit/d925c1bd193b5c19cb23a246f04fc46d0429fc75)) ## [4.5.3](https://github.com/feathersjs/feathers/compare/v4.5.2...v4.5.3) (2020-04-17) - ### Bug Fixes -* **authentication-oauth:** Allow req.feathers to be used in oAuth authentication requests ([#1886](https://github.com/feathersjs/feathers/issues/1886)) ([854c9ca](https://github.com/feathersjs/feathers/commit/854c9cac9a9a5f8f89054a90feb24ab5c4766f5f)) - - - - +- **authentication-oauth:** Allow req.feathers to be used in oAuth authentication requests ([#1886](https://github.com/feathersjs/feathers/issues/1886)) ([854c9ca](https://github.com/feathersjs/feathers/commit/854c9cac9a9a5f8f89054a90feb24ab5c4766f5f)) ## [4.5.2](https://github.com/feathersjs/feathers/compare/v4.5.1...v4.5.2) (2020-03-04) - ### Bug Fixes -* **package:** update grant-profile to version 0.0.11 ([#1841](https://github.com/feathersjs/feathers/issues/1841)) ([5dcd2aa](https://github.com/feathersjs/feathers/commit/5dcd2aa3483059cc7a2546b145dd72b4705fe2fe)) - - - - +- **package:** update grant-profile to version 0.0.11 ([#1841](https://github.com/feathersjs/feathers/issues/1841)) ([5dcd2aa](https://github.com/feathersjs/feathers/commit/5dcd2aa3483059cc7a2546b145dd72b4705fe2fe)) ## [4.5.1](https://github.com/feathersjs/feathers/compare/v4.5.0...v4.5.1) (2020-01-24) **Note:** Version bump only for package @feathersjs/authentication-oauth - - - - # [4.5.0](https://github.com/feathersjs/feathers/compare/v4.4.3...v4.5.0) (2020-01-18) - ### Features -* **authentication-oauth:** Set oAuth redirect URL dynamically and pass query the service ([#1737](https://github.com/feathersjs/feathers/issues/1737)) ([0b05f0b](https://github.com/feathersjs/feathers/commit/0b05f0b58a257820fa61d695a36f36455209f6a1)) - - - - +- **authentication-oauth:** Set oAuth redirect URL dynamically and pass query the service ([#1737](https://github.com/feathersjs/feathers/issues/1737)) ([0b05f0b](https://github.com/feathersjs/feathers/commit/0b05f0b58a257820fa61d695a36f36455209f6a1)) ## [4.4.3](https://github.com/feathersjs/feathers/compare/v4.4.1...v4.4.3) (2019-12-06) **Note:** Version bump only for package @feathersjs/authentication-oauth - - - - ## [4.4.1](https://github.com/feathersjs/feathers/compare/v4.4.0...v4.4.1) (2019-11-27) **Note:** Version bump only for package @feathersjs/authentication-oauth - - - - # [4.4.0](https://github.com/feathersjs/feathers/compare/v4.3.11...v4.4.0) (2019-11-27) - ### Features -* **authentication-oauth:** Set oAuth redirect URL dynamically ([#1608](https://github.com/feathersjs/feathers/issues/1608)) ([1293e08](https://github.com/feathersjs/feathers/commit/1293e088abbb3d23f4a44680836645a8049ceaae)) - - - - +- **authentication-oauth:** Set oAuth redirect URL dynamically ([#1608](https://github.com/feathersjs/feathers/issues/1608)) ([1293e08](https://github.com/feathersjs/feathers/commit/1293e088abbb3d23f4a44680836645a8049ceaae)) ## [4.3.11](https://github.com/feathersjs/feathers/compare/v4.3.10...v4.3.11) (2019-11-11) - ### Bug Fixes -* **authentication-oauth:** Allow hash based redirects ([#1676](https://github.com/feathersjs/feathers/issues/1676)) ([ffe7cf3](https://github.com/feathersjs/feathers/commit/ffe7cf3fbb4e62d7689065cf7b61f25f602ce8cf)) - - - - +- **authentication-oauth:** Allow hash based redirects ([#1676](https://github.com/feathersjs/feathers/issues/1676)) ([ffe7cf3](https://github.com/feathersjs/feathers/commit/ffe7cf3fbb4e62d7689065cf7b61f25f602ce8cf)) ## [4.3.10](https://github.com/feathersjs/feathers/compare/v4.3.9...v4.3.10) (2019-10-26) **Note:** Version bump only for package @feathersjs/authentication-oauth - - - - ## [4.3.9](https://github.com/feathersjs/feathers/compare/v4.3.8...v4.3.9) (2019-10-26) - ### Bug Fixes -* Only initialize default Express session if oAuth is actually used ([#1648](https://github.com/feathersjs/feathers/issues/1648)) ([9b9b43f](https://github.com/feathersjs/feathers/commit/9b9b43ff09af1080e4aaa537064bac37b881c9a2)) - - - - +- Only initialize default Express session if oAuth is actually used ([#1648](https://github.com/feathersjs/feathers/issues/1648)) ([9b9b43f](https://github.com/feathersjs/feathers/commit/9b9b43ff09af1080e4aaa537064bac37b881c9a2)) ## [4.3.7](https://github.com/feathersjs/feathers/compare/v4.3.6...v4.3.7) (2019-10-14) **Note:** Version bump only for package @feathersjs/authentication-oauth - - - - ## [4.3.5](https://github.com/feathersjs/feathers/compare/v4.3.4...v4.3.5) (2019-10-07) **Note:** Version bump only for package @feathersjs/authentication-oauth - - - - ## [4.3.4](https://github.com/feathersjs/feathers/compare/v4.3.3...v4.3.4) (2019-10-03) **Note:** Version bump only for package @feathersjs/authentication-oauth - - - - ## [4.3.3](https://github.com/feathersjs/feathers/compare/v4.3.2...v4.3.3) (2019-09-21) - ### Bug Fixes -* Small improvements in dependencies and code sturcture ([#1562](https://github.com/feathersjs/feathers/issues/1562)) ([42c13e2](https://github.com/feathersjs/feathers/commit/42c13e2)) - - - - +- Small improvements in dependencies and code sturcture ([#1562](https://github.com/feathersjs/feathers/issues/1562)) ([42c13e2](https://github.com/feathersjs/feathers/commit/42c13e2)) ## [4.3.2](https://github.com/feathersjs/feathers/compare/v4.3.1...v4.3.2) (2019-09-16) **Note:** Version bump only for package @feathersjs/authentication-oauth - - - - ## [4.3.1](https://github.com/feathersjs/feathers/compare/v4.3.0...v4.3.1) (2019-09-09) - ### Bug Fixes -* Omit standard protocol ports from the default hostname ([#1543](https://github.com/feathersjs/feathers/issues/1543)) ([ef16d29](https://github.com/feathersjs/feathers/commit/ef16d29)) - - - - +- Omit standard protocol ports from the default hostname ([#1543](https://github.com/feathersjs/feathers/issues/1543)) ([ef16d29](https://github.com/feathersjs/feathers/commit/ef16d29)) # [4.3.0](https://github.com/feathersjs/feathers/compare/v4.3.0-pre.4...v4.3.0) (2019-08-27) **Note:** Version bump only for package @feathersjs/authentication-oauth - - - - # [4.3.0-pre.4](https://github.com/feathersjs/feathers/compare/v4.3.0-pre.3...v4.3.0-pre.4) (2019-08-22) **Note:** Version bump only for package @feathersjs/authentication-oauth - - - - # [4.3.0-pre.3](https://github.com/feathersjs/feathers/compare/v4.3.0-pre.2...v4.3.0-pre.3) (2019-08-19) - ### Bug Fixes -* Update all dependencies ([7d53a00](https://github.com/feathersjs/feathers/commit/7d53a00)) -* Use WeakMap to connect socket to connection ([#1509](https://github.com/feathersjs/feathers/issues/1509)) ([64807e3](https://github.com/feathersjs/feathers/commit/64807e3)) - - - - +- Update all dependencies ([7d53a00](https://github.com/feathersjs/feathers/commit/7d53a00)) +- Use WeakMap to connect socket to connection ([#1509](https://github.com/feathersjs/feathers/issues/1509)) ([64807e3](https://github.com/feathersjs/feathers/commit/64807e3)) # [4.3.0-pre.2](https://github.com/feathersjs/feathers/compare/v4.3.0-pre.1...v4.3.0-pre.2) (2019-08-02) - ### Bug Fixes -* Add method to reliably get default authentication service ([#1470](https://github.com/feathersjs/feathers/issues/1470)) ([e542cb3](https://github.com/feathersjs/feathers/commit/e542cb3)) - - - - +- Add method to reliably get default authentication service ([#1470](https://github.com/feathersjs/feathers/issues/1470)) ([e542cb3](https://github.com/feathersjs/feathers/commit/e542cb3)) # [4.3.0-pre.1](https://github.com/feathersjs/feathers/compare/v4.0.0-pre.5...v4.3.0-pre.1) (2019-07-11) **Note:** Version bump only for package @feathersjs/authentication-oauth - - - - # [4.0.0-pre.5](https://github.com/feathersjs/feathers/compare/v4.0.0-pre.4...v4.0.0-pre.5) (2019-07-10) **Note:** Version bump only for package @feathersjs/authentication-oauth - - - - # [4.0.0-pre.4](https://github.com/feathersjs/feathers/compare/v4.0.0-pre.3...v4.0.0-pre.4) (2019-07-05) **Note:** Version bump only for package @feathersjs/authentication-oauth - - - - # [4.0.0-pre.3](https://github.com/feathersjs/feathers/compare/v4.0.0-pre.2...v4.0.0-pre.3) (2019-06-01) - ### Bug Fixes -* Make oAuth paths more consistent and improve authentication client ([#1377](https://github.com/feathersjs/feathers/issues/1377)) ([adb2543](https://github.com/feathersjs/feathers/commit/adb2543)) -* Update dependencies and fix tests ([#1373](https://github.com/feathersjs/feathers/issues/1373)) ([d743a7f](https://github.com/feathersjs/feathers/commit/d743a7f)) - - - - +- Make oAuth paths more consistent and improve authentication client ([#1377](https://github.com/feathersjs/feathers/issues/1377)) ([adb2543](https://github.com/feathersjs/feathers/commit/adb2543)) +- Update dependencies and fix tests ([#1373](https://github.com/feathersjs/feathers/issues/1373)) ([d743a7f](https://github.com/feathersjs/feathers/commit/d743a7f)) # [4.0.0-pre.2](https://github.com/feathersjs/feathers/compare/v4.0.0-pre.1...v4.0.0-pre.2) (2019-05-15) - ### Bug Fixes -* Correctly read the oauth strategy config ([#1349](https://github.com/feathersjs/feathers/issues/1349)) ([9abf314](https://github.com/feathersjs/feathers/commit/9abf314)) - +- Correctly read the oauth strategy config ([#1349](https://github.com/feathersjs/feathers/issues/1349)) ([9abf314](https://github.com/feathersjs/feathers/commit/9abf314)) ### Features -* Add global disconnect event ([#1355](https://github.com/feathersjs/feathers/issues/1355)) ([85afcca](https://github.com/feathersjs/feathers/commit/85afcca)) - - - - +- Add global disconnect event ([#1355](https://github.com/feathersjs/feathers/issues/1355)) ([85afcca](https://github.com/feathersjs/feathers/commit/85afcca)) # [4.0.0-pre.1](https://github.com/feathersjs/feathers/compare/v4.0.0-pre.0...v4.0.0-pre.1) (2019-05-08) - ### Bug Fixes -* Always require strategy parameter in authentication ([#1327](https://github.com/feathersjs/feathers/issues/1327)) ([d4a8021](https://github.com/feathersjs/feathers/commit/d4a8021)) -* Improve authentication parameter handling ([#1333](https://github.com/feathersjs/feathers/issues/1333)) ([6e77204](https://github.com/feathersjs/feathers/commit/6e77204)) -* Improve oAuth option handling and usability ([#1335](https://github.com/feathersjs/feathers/issues/1335)) ([adb137d](https://github.com/feathersjs/feathers/commit/adb137d)) -* Merge httpStrategies and authStrategies option ([#1308](https://github.com/feathersjs/feathers/issues/1308)) ([afa4d55](https://github.com/feathersjs/feathers/commit/afa4d55)) -* Rename jwtStrategies option to authStrategies ([#1305](https://github.com/feathersjs/feathers/issues/1305)) ([4aee151](https://github.com/feathersjs/feathers/commit/4aee151)) - +- Always require strategy parameter in authentication ([#1327](https://github.com/feathersjs/feathers/issues/1327)) ([d4a8021](https://github.com/feathersjs/feathers/commit/d4a8021)) +- Improve authentication parameter handling ([#1333](https://github.com/feathersjs/feathers/issues/1333)) ([6e77204](https://github.com/feathersjs/feathers/commit/6e77204)) +- Improve oAuth option handling and usability ([#1335](https://github.com/feathersjs/feathers/issues/1335)) ([adb137d](https://github.com/feathersjs/feathers/commit/adb137d)) +- Merge httpStrategies and authStrategies option ([#1308](https://github.com/feathersjs/feathers/issues/1308)) ([afa4d55](https://github.com/feathersjs/feathers/commit/afa4d55)) +- Rename jwtStrategies option to authStrategies ([#1305](https://github.com/feathersjs/feathers/issues/1305)) ([4aee151](https://github.com/feathersjs/feathers/commit/4aee151)) ### Features -* Change and *JWT methods to *accessToken ([#1304](https://github.com/feathersjs/feathers/issues/1304)) ([5ac826b](https://github.com/feathersjs/feathers/commit/5ac826b)) - - - - +- Change and *JWT methods to *accessToken ([#1304](https://github.com/feathersjs/feathers/issues/1304)) ([5ac826b](https://github.com/feathersjs/feathers/commit/5ac826b)) # [4.0.0-pre.0](https://github.com/feathersjs/feathers/compare/v3.2.0-pre.1...v4.0.0-pre.0) (2019-04-21) - ### Features -* @feathersjs/authentication-oauth ([#1299](https://github.com/feathersjs/feathers/issues/1299)) ([656bae7](https://github.com/feathersjs/feathers/commit/656bae7)) +- @feathersjs/authentication-oauth ([#1299](https://github.com/feathersjs/feathers/issues/1299)) ([656bae7](https://github.com/feathersjs/feathers/commit/656bae7)) diff --git a/packages/authentication-oauth/LICENSE b/packages/authentication-oauth/LICENSE index 9f0c6ea9b0..b8be257c56 100644 --- a/packages/authentication-oauth/LICENSE +++ b/packages/authentication-oauth/LICENSE @@ -1,6 +1,6 @@ The MIT License (MIT) -Copyright (c) 2021 Feathers +Copyright (c) 2022 Feathers Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated documentation files (the "Software"), to deal diff --git a/packages/authentication-oauth/README.md b/packages/authentication-oauth/README.md index 98b41a4b72..a5b09c3b15 100644 --- a/packages/authentication-oauth/README.md +++ b/packages/authentication-oauth/README.md @@ -1,8 +1,8 @@ # @feathersjs/authentication-oauth [![CI](https://github.com/feathersjs/feathers/workflows/CI/badge.svg)](https://github.com/feathersjs/feathers/actions?query=workflow%3ACI) -[![Dependency Status](https://img.shields.io/david/feathersjs/feathers.svg?style=flat-square&path=packages/authentication-oauth)](https://david-dm.org/feathersjs/feathers?path=packages/authentication-oauth) [![Download Status](https://img.shields.io/npm/dm/@feathersjs/authentication-oauth.svg?style=flat-square)](https://www.npmjs.com/package/@feathersjs/authentication-oauth) +[![Discord](https://badgen.net/badge/icon/discord?icon=discord&label)](https://discord.gg/qa8kez8QBx) > OAuth 1 and 2 authentication for Feathers. Powered by Grant. @@ -18,6 +18,6 @@ Refer to the [Feathers oAuth authentication API documentation](https://docs.feat ## License -Copyright (c) 2021 [Feathers contributors](https://github.com/feathersjs/feathers/graphs/contributors) +Copyright (c) 2022 [Feathers contributors](https://github.com/feathersjs/feathers/graphs/contributors) Licensed under the [MIT license](LICENSE). diff --git a/packages/authentication-oauth/package.json b/packages/authentication-oauth/package.json index 775bfc67ae..7a2d4ebb38 100644 --- a/packages/authentication-oauth/package.json +++ b/packages/authentication-oauth/package.json @@ -1,7 +1,7 @@ { "name": "@feathersjs/authentication-oauth", "description": "oAuth 1 and 2 authentication for Feathers. Powered by Grant.", - "version": "5.0.0-pre.16", + "version": "5.0.0-pre.31", "homepage": "https://feathersjs.com", "main": "lib/", "types": "lib/", @@ -16,7 +16,8 @@ }, "repository": { "type": "git", - "url": "git://github.com/feathersjs/feathers.git" + "url": "git://github.com/feathersjs/feathers.git", + "directory": "packages/authentication-oauth" }, "author": { "name": "Feathers contributors", @@ -42,7 +43,8 @@ "scripts": { "start": "ts-node test/app", "prepublish": "npm run compile", - "compile": "shx rm -rf lib/ && tsc", + "pack": "npm pack --pack-destination ../cli/test/build", + "compile": "shx rm -rf lib/ && tsc && npm run pack", "test": "mocha --config ../../.mocharc.json --recursive test/**.test.ts test/**/*.test.ts" }, "directories": { @@ -52,27 +54,34 @@ "access": "public" }, "dependencies": { - "@feathersjs/authentication": "^5.0.0-pre.16", - "@feathersjs/commons": "^5.0.0-pre.16", - "@feathersjs/errors": "^5.0.0-pre.16", - "@feathersjs/express": "^5.0.0-pre.16", - "@feathersjs/feathers": "^5.0.0-pre.16", - "express-session": "^1.17.2", - "grant": "^5.4.18", - "lodash": "^4.17.21" + "@feathersjs/authentication": "^5.0.0-pre.31", + "@feathersjs/commons": "^5.0.0-pre.31", + "@feathersjs/errors": "^5.0.0-pre.31", + "@feathersjs/express": "^5.0.0-pre.31", + "@feathersjs/feathers": "^5.0.0-pre.31", + "@feathersjs/koa": "^5.0.0-pre.31", + "@feathersjs/schema": "^5.0.0-pre.31", + "cookie-session": "^2.0.0", + "grant": "^5.4.21", + "koa-session": "^6.2.0", + "lodash": "^4.17.21", + "qs": "^6.11.0" }, "devDependencies": { - "@feathersjs/memory": "^5.0.0-pre.16", - "@types/express": "^4.17.13", - "@types/express-session": "^1.17.4", - "@types/lodash": "^4.14.178", - "@types/mocha": "^9.0.0", - "@types/node": "^17.0.5", - "axios": "^0.24.0", - "mocha": "^9.1.3", - "shx": "^0.3.3", - "ts-node": "^10.4.0", - "typescript": "^4.5.4" + "@feathersjs/memory": "^5.0.0-pre.31", + "@types/cookie-session": "^2.0.44", + "@types/express": "^4.17.14", + "@types/koa-session": "^5.10.6", + "@types/lodash": "^4.14.186", + "@types/mocha": "^10.0.0", + "@types/node": "^18.8.2", + "@types/tough-cookie": "^4.0.2", + "axios": "^0.27.2", + "mocha": "^10.0.0", + "shx": "^0.3.4", + "tough-cookie": "^4.1.2", + "ts-node": "^10.9.1", + "typescript": "^4.8.4" }, - "gitHead": "f0cd227a82d159b528193bd33747c97684a48773" + "gitHead": "4500dbeb8cea566678cf88b3313a88efd93a2ed9" } diff --git a/packages/authentication-oauth/src/express.ts b/packages/authentication-oauth/src/express.ts deleted file mode 100644 index eb033e0708..0000000000 --- a/packages/authentication-oauth/src/express.ts +++ /dev/null @@ -1,136 +0,0 @@ -import grant from 'grant'; -import session from 'express-session'; -import { Request, Response, NextFunction } from 'express'; -import { createDebug } from '@feathersjs/commons'; -import { Application } from '@feathersjs/feathers'; -import { AuthenticationResult } from '@feathersjs/authentication'; -import { - Application as ExpressApplication, - original as originalExpress -} from '@feathersjs/express'; -import { OauthSetupSettings } from './utils'; -import { OAuthStrategy } from './strategy'; - -const grantInstance = grant.express(); -const debug = createDebug('@feathersjs/authentication-oauth/express'); - -declare module 'express-session' { - interface SessionData { - redirect: string; - accessToken: string; - query: { [key: string]: any }; - grant: { [key: string]: any }; - headers: { [key: string]: any }; - } -} - -export default (options: OauthSetupSettings) => { - return (feathersApp: Application) => { - const { authService, linkStrategy } = options; - const app = feathersApp as ExpressApplication; - const config = app.get('grant'); - - if (!config) { - debug('No grant configuration found, skipping Express oAuth setup'); - return; - } - - const { prefix } = config.defaults; - const expressSession = options.expressSession || session({ - secret: Math.random().toString(36).substring(7), - saveUninitialized: true, - resave: true - }); - const grantApp = grantInstance(config); - const authApp = originalExpress(); - - authApp.use(expressSession); - - authApp.get('/:name', (req: Request, _res: Response, next: NextFunction) => { - const { feathers_token, redirect, ...query } = req.query; - - if (feathers_token) { - debug('Got feathers_token query parameter to link accounts', feathers_token); - req.session.accessToken = feathers_token as string; - } - req.session.redirect = redirect as string; - req.session.query = query; - req.session.headers = req.headers; - req.session.save((err: any) => { - if (err) { - next(`Error storing session: ${err}`); - } else { - next(); - } - }); - }); - - authApp.get('/:name/authenticate', async (req: Request, res: Response, next: NextFunction) => { - const { name } = req.params ; - const { accessToken, grant, query = {}, redirect, headers } = req.session; - const service = app.defaultAuthentication(authService); - const [ strategy ] = service.getStrategies(name) as OAuthStrategy[]; - const params = { - ...req.feathers, - authStrategies: [ name ], - authentication: accessToken ? { - strategy: linkStrategy, - accessToken - } : null, - query, - redirect, - headers - }; - const sendResponse = async (data: AuthenticationResult|Error) => { - try { - const redirect = await strategy.getRedirect(data, params); - - if (redirect !== null) { - res.redirect(redirect); - } else if (data instanceof Error) { - throw data; - } else { - res.json(data); - } - } catch (error: any) { - debug('oAuth error', error); - next(error); - } - }; - - try { - const payload = config.defaults.transport === 'session' ? - grant.response : req.query; - const authentication = { - strategy: name, - ...payload - }; - - await new Promise((resolve, reject) => { - if (!req.session.destroy) { - req.session = null; - resolve(); - } - - req.session.destroy((err: any) => err ? reject(err) : resolve()); - }); - - debug(`Calling ${authService}.create authentication with strategy ${name}`); - - const authResult = await service.create(authentication, params); - - debug('Successful oAuth authentication, sending response'); - - await sendResponse(authResult); - } catch (error: any) { - debug('Received oAuth authentication error', error.stack); - await sendResponse(error); - } - }); - - authApp.use(grantApp); - - app.set('grant', grantApp.config); - app.use(prefix, authApp); - }; -}; diff --git a/packages/authentication-oauth/src/index.ts b/packages/authentication-oauth/src/index.ts index 6d9f36aa6a..9d2099e536 100644 --- a/packages/authentication-oauth/src/index.ts +++ b/packages/authentication-oauth/src/index.ts @@ -1,80 +1,49 @@ -import merge from 'lodash/merge'; -import each from 'lodash/each'; -import omit from 'lodash/omit'; -import { createDebug } from '@feathersjs/commons'; -import { Application } from '@feathersjs/feathers'; -import { OAuthStrategy, OAuthProfile } from './strategy'; -import { default as setupExpress } from './express'; -import { OauthSetupSettings, getDefaultSettings } from './utils'; +import { Application } from '@feathersjs/feathers' +import { createDebug } from '@feathersjs/commons' +import { resolveDispatch } from '@feathersjs/schema' -const debug = createDebug('@feathersjs/authentication-oauth'); +import { OAuthStrategy, OAuthProfile } from './strategy' +import { redirectHook, OAuthService } from './service' +import { getGrantConfig, getServiceOptions, OauthSetupSettings } from './utils' -export { OauthSetupSettings, OAuthStrategy, OAuthProfile }; +const debug = createDebug('@feathersjs/authentication-oauth') -export const setup = (options: OauthSetupSettings) => (app: Application) => { - const service = app.defaultAuthentication ? app.defaultAuthentication(options.authService) : null; +export { OauthSetupSettings, OAuthStrategy, OAuthProfile } - if (!service) { - throw new Error('An authentication service must exist before registering @feathersjs/authentication-oauth'); - } - - const { oauth } = service.configuration; - - if (!oauth) { - debug('No oauth configuration found in authentication configuration. Skipping oAuth setup.'); - return; - } - - const { strategyNames } = service; - - // Set up all the defaults - const { prefix = '/oauth' } = oauth.defaults || {}; - const port = app.get('port'); - let host = app.get('host'); - let protocol = 'https'; +export const oauth = + (settings: Partial = {}) => + (app: Application) => { + const authService = app.defaultAuthentication ? app.defaultAuthentication(settings.authService) : null - // Development environments commonly run on HTTP with an extended port - if (app.get('env') === 'development') { - protocol = 'http'; - if (String(port) !== '80') { - host += `:${port}`; + if (!authService) { + throw new Error( + 'An authentication service must exist before registering @feathersjs/authentication-oauth' + ) } - } - const grant = merge({ - defaults: { - prefix, - origin: `${protocol}://${host}`, - transport: 'session', - response: ['tokens', 'raw', 'profile'] + if (!authService.configuration.oauth) { + debug('No oauth configuration found in authentication configuration. Skipping oAuth setup.') + return } - }, omit(oauth, 'redirect')); - - const getUrl = (url: string) => { - const { defaults } = grant; - return `${defaults.origin}${prefix}/${url}`; - }; - - each(grant, (value, name) => { - if (name !== 'defaults') { - value.callback = value.callback || getUrl(`${name}/authenticate`); - value.redirect_uri = value.redirect_uri || getUrl(`${name}/callback`); - if (!strategyNames.includes(name)) { - debug(`Registering oAuth default strategy for '${name}'`); - service.register(name, new OAuthStrategy()); - } + const oauthOptions = { + linkStrategy: 'jwt', + ...settings } - }); - app.set('grant', grant); -}; + const grantConfig = getGrantConfig(authService) + const serviceOptions = getServiceOptions(authService, oauthOptions) + const servicePath = `${grantConfig.defaults.prefix || 'oauth'}/:provider` -export const express = (settings: Partial = {}) => (app: Application) => { - const options = getDefaultSettings(app, settings); + app.use(servicePath, new OAuthService(authService, oauthOptions), serviceOptions) - app.configure(setup(options)); - app.configure(setupExpress(options)); -}; + const oauthService = app.service(servicePath) -export const expressOauth = express; + oauthService.hooks({ + around: { all: [resolveDispatch(), redirectHook()] } + }) + + if (typeof oauthService.publish === 'function') { + app.service(servicePath).publish(() => null) + } + } diff --git a/packages/authentication-oauth/src/service.ts b/packages/authentication-oauth/src/service.ts new file mode 100644 index 0000000000..b84d21cc88 --- /dev/null +++ b/packages/authentication-oauth/src/service.ts @@ -0,0 +1,177 @@ +import { createDebug } from '@feathersjs/commons' +import { HookContext, NextFunction, Params } from '@feathersjs/feathers' +import { FeathersError } from '@feathersjs/errors' +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +//@ts-ignore +import Grant from 'grant/lib/grant' +import { AuthenticationService } from '@feathersjs/authentication' +import { OAuthStrategy } from './strategy' +import { getGrantConfig, OauthSetupSettings } from './utils' + +const debug = createDebug('@feathersjs/authentication-oauth/services') + +export type GrantResponse = { + location: string + session: any + state: any +} + +export type OAuthParams = Omit & { + session: any + state: Record + route: { + provider: string + } +} + +export class OAuthError extends FeathersError { + constructor(message: string, data: any, public location: string) { + super(message, 'NotAuthenticated', 401, 'not-authenticated', data) + } +} + +export const redirectHook = () => async (context: HookContext, next: NextFunction) => { + try { + await next() + + const { location } = context.result + + debug(`oAuth redirect to ${location}`) + + if (location) { + context.http = { + ...context.http, + location + } + } + } catch (error: any) { + if (error.location) { + context.http = { + ...context.http, + location: error.location + } + context.result = typeof error.toJSON === 'function' ? error.toJSON() : error + } else { + throw error + } + } +} + +export class OAuthService { + grant: any + + constructor(public service: AuthenticationService, public settings: OauthSetupSettings) { + const config = getGrantConfig(service) + + this.grant = Grant({ config }) + } + + async handler(method: string, params: OAuthParams, body?: any, override?: string): Promise { + const { + session, + state, + query, + route: { provider } + } = params + + const result: GrantResponse = await this.grant({ + params: { provider, override }, + state: state.grant, + session: session.grant, + query, + method, + body + }) + + session.grant = result.session + state.grant = result.state + + return result + } + + async authenticate(params: OAuthParams, result: GrantResponse) { + const name = params.route.provider + const { linkStrategy, authService } = this.settings + const { accessToken, grant, query = {}, redirect } = params.session + const strategy = this.service.getStrategy(name) as OAuthStrategy + const authParams = { + ...params, + authStrategies: [name], + authentication: accessToken + ? { + strategy: linkStrategy, + accessToken + } + : null, + query, + redirect + } + const payload = grant?.response || result?.session?.response || result?.state?.response || params.query + const authentication = { + strategy: name, + ...payload + } + + try { + debug(`Calling ${authService}.create authentication with strategy ${name}`) + + const authResult = await this.service.create(authentication, authParams) + + debug('Successful oAuth authentication, sending response') + + const location = await strategy.getRedirect(authResult, authParams) + + if (typeof params.session.destroy === 'function') { + await params.session.destroy() + } + + return { + ...authResult, + location + } + } catch (error: any) { + const location = await strategy.getRedirect(error, authParams) + const e = new OAuthError(error.message, error.data, location) + + if (typeof params.session.destroy === 'function') { + await params.session.destroy() + } + + e.stack = error.stack + throw e + } + } + + async find(params: OAuthParams) { + const { session, query } = params + const { feathers_token, redirect, ...restQuery } = query + const handlerParams = { + ...params, + query: restQuery + } + + if (feathers_token) { + debug('Got feathers_token query parameter to link accounts', feathers_token) + session.accessToken = feathers_token + } + + session.redirect = redirect + session.query = restQuery + + return this.handler('GET', handlerParams, {}) + } + + async get(override: string, params: OAuthParams) { + const result = await this.handler('GET', params, {}, override) + + if (override === 'callback') { + return this.authenticate(params, result) + } + + return result + } + + async create(data: any, params: OAuthParams) { + return this.handler('POST', params, data) + } +} diff --git a/packages/authentication-oauth/src/strategy.ts b/packages/authentication-oauth/src/strategy.ts index 108eab585f..e9f2bb77c0 100644 --- a/packages/authentication-oauth/src/strategy.ts +++ b/packages/authentication-oauth/src/strategy.ts @@ -1,176 +1,176 @@ -/* eslint-disable @typescript-eslint/no-unused-vars */ -// @ts-ignore -import querystring from 'querystring'; import { - AuthenticationRequest, AuthenticationBaseStrategy, AuthenticationResult -} from '@feathersjs/authentication'; -import { Params } from '@feathersjs/feathers'; -import { NotAuthenticated } from '@feathersjs/errors'; -import { createDebug, _ } from '@feathersjs/commons'; - -const debug = createDebug('@feathersjs/authentication-oauth/strategy'); + AuthenticationRequest, + AuthenticationBaseStrategy, + AuthenticationResult, + AuthenticationParams +} from '@feathersjs/authentication' +import { Params } from '@feathersjs/feathers' +import { NotAuthenticated } from '@feathersjs/errors' +import { createDebug, _ } from '@feathersjs/commons' +import qs from 'qs' + +const debug = createDebug('@feathersjs/authentication-oauth/strategy') export interface OAuthProfile { - id?: string|number; - [key: string]: any; + id?: string | number + [key: string]: any } export class OAuthStrategy extends AuthenticationBaseStrategy { - get configuration () { - const { entity, service, entityId, oauth } = this.authentication.configuration; - const config = oauth[this.name]; + get configuration() { + const { entity, service, entityId, oauth } = this.authentication.configuration + const config = oauth[this.name] as any return { entity, service, entityId, ...config - }; + } } - get entityId (): string { - const { entityService } = this; + get entityId(): string { + const { entityService } = this - return this.configuration.entityId || (entityService && (entityService as any).id); + return this.configuration.entityId || (entityService && (entityService as any).id) } - async getEntityQuery (profile: OAuthProfile, _params: Params) { + async getEntityQuery(profile: OAuthProfile, _params: Params) { return { [`${this.name}Id`]: profile.sub || profile.id - }; + } } - async getEntityData (profile: OAuthProfile, _existingEntity: any, _params: Params) { + async getEntityData(profile: OAuthProfile, _existingEntity: any, _params: Params) { return { [`${this.name}Id`]: profile.sub || profile.id - }; + } } - async getProfile (data: AuthenticationRequest, _params: Params) { + async getProfile(data: AuthenticationRequest, _params: Params) { return data.profile } - async getCurrentEntity (params: Params) { - const { authentication } = params; - const { entity } = this.configuration; + async getCurrentEntity(params: Params) { + const { authentication } = params + const { entity } = this.configuration if (authentication && authentication.strategy) { - debug('getCurrentEntity with authentication', authentication); + debug('getCurrentEntity with authentication', authentication) - const { strategy } = authentication; - const authResult = await this.authentication - .authenticate(authentication, params, strategy); + const { strategy } = authentication + const authResult = await this.authentication.authenticate(authentication, params, strategy) - return authResult[entity]; + return authResult[entity] } - return null; + return null } - async getAllowedOrigin (params?: Params) { - const { redirect, origins } = this.authentication.configuration.oauth; + async getAllowedOrigin(params?: Params) { + const { redirect, origins = this.app.get('origins') } = this.authentication.configuration.oauth if (Array.isArray(origins)) { - const referer = params?.headers?.referer || ''; - const allowedOrigin = origins.find(current => referer.toLowerCase().startsWith(current.toLowerCase())); + const referer = params?.headers?.referer || origins[0] + const allowedOrigin = origins.find((current) => referer.toLowerCase().startsWith(current.toLowerCase())) - if(!allowedOrigin) { - throw new NotAuthenticated(`Referer "${referer || '[header not available]'}" not allowed.`); + if (!allowedOrigin) { + throw new NotAuthenticated(`Referer "${referer}" is not allowed.`) } - return allowedOrigin; + return allowedOrigin } - return redirect; + return redirect } - async getRedirect (data: AuthenticationResult|Error, params?: Params): Promise { - const queryRedirect = (params && params.redirect) || ''; - const redirect = await this.getAllowedOrigin(params); + async getRedirect( + data: AuthenticationResult | Error, + params?: AuthenticationParams + ): Promise { + const queryRedirect = (params && params.redirect) || '' + const redirect = await this.getAllowedOrigin(params) if (!redirect) { - return null; + return null } - const redirectUrl = `${redirect}${queryRedirect}`; - const separator = redirect.endsWith('?') ? '' : - (redirect.indexOf('#') !== -1 ? '?' : '#'); - const authResult: AuthenticationResult = data; - const query = authResult.accessToken ? { - access_token: authResult.accessToken - } : { - error: data.message || 'OAuth Authentication not successful' - }; - - return `${redirectUrl}${separator}${querystring.stringify(query)}`; + const redirectUrl = `${redirect}${queryRedirect}` + const separator = redirect.endsWith('?') ? '' : redirect.indexOf('#') !== -1 ? '?' : '#' + const authResult: AuthenticationResult = data + const query = authResult.accessToken + ? { access_token: authResult.accessToken } + : { error: data.message || 'OAuth Authentication not successful' } + + return `${redirectUrl}${separator}${qs.stringify(query)}` } - async findEntity (profile: OAuthProfile, params: Params) { - const query = await this.getEntityQuery(profile, params); + async findEntity(profile: OAuthProfile, params: Params) { + const query = await this.getEntityQuery(profile, params) - debug('findEntity with query', query); + debug('findEntity with query', query) const result = await this.entityService.find({ ...params, query - }); - const [ entity = null ] = result.data ? result.data : result; + }) + const [entity = null] = result.data ? result.data : result - debug('findEntity returning', entity); + debug('findEntity returning', entity) - return entity; + return entity } - async createEntity (profile: OAuthProfile, params: Params) { - const data = await this.getEntityData(profile, null, params); + async createEntity(profile: OAuthProfile, params: Params) { + const data = await this.getEntityData(profile, null, params) - debug('createEntity with data', data); + debug('createEntity with data', data) - return this.entityService.create(data, _.omit(params, 'query')); + return this.entityService.create(data, _.omit(params, 'query')) } - async updateEntity (entity: any, profile: OAuthProfile, params: Params) { - const id = entity[this.entityId]; - const data = await this.getEntityData(profile, entity, params); + async updateEntity(entity: any, profile: OAuthProfile, params: Params) { + const id = entity[this.entityId] + const data = await this.getEntityData(profile, entity, params) - debug(`updateEntity with id ${id} and data`, data); + debug(`updateEntity with id ${id} and data`, data) - return this.entityService.patch(id, data, _.omit(params, 'query')); + return this.entityService.patch(id, data, _.omit(params, 'query')) } - async getEntity (result: any, params: Params) { - const { entityService } = this; - const { entityId = (entityService as any).id, entity } = this.configuration; + async getEntity(result: any, params: Params) { + const { entityService } = this + const { entityId = (entityService as any).id, entity } = this.configuration if (!entityId || result[entityId] === undefined) { - throw new NotAuthenticated('Could not get oAuth entity'); + throw new NotAuthenticated('Could not get oAuth entity') } if (!params.provider) { - return result; + return result } return entityService.get(result[entityId], { ..._.omit(params, 'query'), [entity]: result - }); + }) } - async authenticate (authentication: AuthenticationRequest, originalParams: Params) { - const entity: string = this.configuration.entity; - const { provider, ...params } = originalParams; - const profile = await this.getProfile(authentication, params); - const existingEntity = await this.findEntity(profile, params) - || await this.getCurrentEntity(params); + async authenticate(authentication: AuthenticationRequest, originalParams: AuthenticationParams) { + const entity: string = this.configuration.entity + const { provider, ...params } = originalParams + const profile = await this.getProfile(authentication, params) + const existingEntity = (await this.findEntity(profile, params)) || (await this.getCurrentEntity(params)) - debug('authenticate with (existing) entity', existingEntity); + debug('authenticate with (existing) entity', existingEntity) - const authEntity = !existingEntity ? await this.createEntity(profile, params) - : await this.updateEntity(existingEntity, profile, params); + const authEntity = !existingEntity + ? await this.createEntity(profile, params) + : await this.updateEntity(existingEntity, profile, params) return { authentication: { strategy: this.name }, [entity]: await this.getEntity(authEntity, originalParams) - }; + } } } diff --git a/packages/authentication-oauth/src/utils.ts b/packages/authentication-oauth/src/utils.ts index 847a040d54..cd6f5edfde 100644 --- a/packages/authentication-oauth/src/utils.ts +++ b/packages/authentication-oauth/src/utils.ts @@ -1,17 +1,123 @@ -import { RequestHandler } from 'express'; -import { Application } from '@feathersjs/feathers'; +import type { RequestHandler } from 'express' +import type { Middleware, Application as KoaApplication } from '@feathersjs/koa' + +import type { ServiceOptions } from '@feathersjs/feathers' + +import '@feathersjs/koa' +import '@feathersjs/express' +import expressCookieSession from 'cookie-session' +import koaCookieSession from 'koa-session' + +import { AuthenticationService } from '@feathersjs/authentication' +import { GrantConfig } from 'grant' + +import { defaultsDeep, each, omit } from 'lodash' export interface OauthSetupSettings { - authService?: string; - expressSession?: RequestHandler; - linkStrategy: string; + linkStrategy: string + authService?: string + expressSession?: RequestHandler + koaSession?: Middleware +} + +export const getGrantConfig = (service: AuthenticationService): GrantConfig => { + const { + app, + configuration: { oauth } + } = service + // Set up all the defaults + const port = app.get('port') + let host = app.get('host') + let protocol = 'https' + + // Development environments commonly run on HTTP with an extended port + if (process.env.NODE_ENV !== 'production') { + protocol = 'http' + if (String(port) !== '80') { + host += `:${port}` + } + } + + const grant: GrantConfig = defaultsDeep({}, omit(oauth, ['redirect', 'origins']), { + defaults: { + prefix: '/oauth', + origin: `${protocol}://${host}`, + transport: 'state', + response: ['tokens', 'raw', 'profile'] + } + }) + + const getUrl = (url: string) => { + const { defaults } = grant + return `${defaults.origin}${defaults.prefix}/${url}` + } + + each(grant, (value, name) => { + if (name !== 'defaults') { + value.redirect_uri = value.redirect_uri || getUrl(`${name}/callback`) + } + }) + + return grant +} + +export const setExpressParams: RequestHandler = (req, res, next) => { + req.session.destroy ||= () => { + req.session = null + } + + req.feathers = { + ...req.feathers, + session: req.session, + state: res.locals + } + + next() +} + +export const setKoaParams: Middleware = async (ctx, next) => { + ctx.session.destroy ||= () => { + ctx.session = null + } + + ctx.feathers = { + ...ctx.feathers, + session: ctx.session, + state: ctx.state + } as any + + await next() } -export const getDefaultSettings = (_app: Application, other?: Partial) => { - const defaults: OauthSetupSettings = { - linkStrategy: 'jwt', - ...other - }; +export const getServiceOptions = ( + service: AuthenticationService, + settings: OauthSetupSettings +): ServiceOptions => { + const { secret } = service.configuration + const koaApp = service.app as KoaApplication + + if (koaApp.context) { + koaApp.keys = [secret] + + const { koaSession = koaCookieSession({ key: 'feathers.oauth' }, koaApp as any) } = settings - return defaults; -}; + return { + koa: { + before: [koaSession, setKoaParams] + } + } + } + + const { + expressSession = expressCookieSession({ + name: 'feathers.oauth', + keys: [secret] + }) + } = settings + + return { + express: { + before: [expressSession, setExpressParams] + } + } +} diff --git a/packages/authentication-oauth/test/express.test.ts b/packages/authentication-oauth/test/express.test.ts deleted file mode 100644 index 3774f7fb7c..0000000000 --- a/packages/authentication-oauth/test/express.test.ts +++ /dev/null @@ -1,49 +0,0 @@ -import { strict as assert } from 'assert'; -import { Server } from 'http'; -import axios from 'axios'; -import { app } from './fixture'; - -describe('@feathersjs/authentication-oauth/express', () => { - let server: Server; - - before(async () => { - server = await app.listen(9876); - }); - - after(() => server.close()); - - it('oauth/test', async () => { - try { - await axios.get('http://localhost:9876/oauth/test?feathers_token=testing', { maxRedirects: 0 }); - } catch (error: any) { - assert.equal(error.response.status, 302) - } - }); - - it('oauth/test with query', async () => { - try { - await axios.get('http://localhost:9876/oauth/test?other=test', { maxRedirects: 0 }); - } catch (error: any) { - assert.equal(error.response.status, 302) - } - }); - - it('oauth/test/authenticate', async () => { - const { data } = await axios.get('http://localhost:9876/oauth/test/authenticate?profile[sub]=expressTest'); - - assert.ok(data.accessToken); - assert.equal(data.user.testId, 'expressTest'); - assert.equal(data.fromMiddleware, 'testing'); - }); - - it('oauth/test/authenticate with redirect', async () => { - app.get('authentication').oauth.redirect = '/'; - - try { - await axios.get('http://localhost:9876/oauth/test/authenticate'); - } catch (error: any) { - assert.ok(/Cannot GET/.test(error.response.data)); - delete app.get('authentication').oauth.redirect; - } - }); -}); diff --git a/packages/authentication-oauth/test/fixture.ts b/packages/authentication-oauth/test/fixture.ts deleted file mode 100644 index 1dc58da77a..0000000000 --- a/packages/authentication-oauth/test/fixture.ts +++ /dev/null @@ -1,59 +0,0 @@ -import { feathers, Params } from '@feathersjs/feathers'; -import express, { rest, errorHandler } from '@feathersjs/express'; -import { memory } from '@feathersjs/memory'; -import { AuthenticationService, JWTStrategy, AuthenticationRequest } from '@feathersjs/authentication'; -import { express as oauth, OAuthStrategy } from '../src'; - -export class TestOAuthStrategy extends OAuthStrategy { - async authenticate (data: AuthenticationRequest, params: Params) { - const { fromMiddleware } = params; - const authResult = await super.authenticate(data, params); - - if (fromMiddleware) { - authResult.fromMiddleware = fromMiddleware; - } - - return authResult; - } -} - -export const app = express(feathers()); - -const port = 9876; -const auth = new AuthenticationService(app); - -auth.register('jwt', new JWTStrategy()); -auth.register('test', new TestOAuthStrategy()); - -app.configure(rest()); -app.set('host', '127.0.0.1'); -app.set('port', port); -app.set('authentication', { - secret: 'supersecret', - entity: 'user', - service: 'users', - authStrategies: [ 'jwt' ], - oauth: { - defaults: { - transport: 'querystring' - }, - test: { - key: 'some-key', - secret: 'a secret secret' - }, - twitter: { - key: 'twitter key', - secret: 'some secret' - } - } -}); - -app.use((req, _res, next) => { - req.feathers = { fromMiddleware: 'testing' }; - next(); -}); -app.use('/authentication', auth); -app.use('/users', memory()); - -app.configure(oauth()); -app.use(errorHandler({ logger: null })); diff --git a/packages/authentication-oauth/test/index.test.ts b/packages/authentication-oauth/test/index.test.ts index 8542ccacf6..f4e192482e 100644 --- a/packages/authentication-oauth/test/index.test.ts +++ b/packages/authentication-oauth/test/index.test.ts @@ -1,29 +1,29 @@ -import { strict as assert } from 'assert'; -import { feathers } from '@feathersjs/feathers'; -import { setup, express, OauthSetupSettings } from '../src'; -import { AuthenticationService } from '@feathersjs/authentication'; +import { strict as assert } from 'assert' +import { feathers } from '@feathersjs/feathers' +import { oauth, OauthSetupSettings } from '../src' +import { AuthenticationService } from '@feathersjs/authentication' describe('@feathersjs/authentication-oauth', () => { describe('setup', () => { it('errors when service does not exist', () => { - const app = feathers(); + const app = feathers() - try { - app.configure(setup({ authService: 'something' } as OauthSetupSettings)); - assert.fail('Should never get here'); - } catch (error: any) { - assert.equal(error.message, - 'An authentication service must exist before registering @feathersjs/authentication-oauth' - ); - } - }); + assert.throws( + () => { + app.configure(oauth({ authService: 'something' } as OauthSetupSettings)) + }, + { + message: 'An authentication service must exist before registering @feathersjs/authentication-oauth' + } + ) + }) - it('errors when service does not exist', () => { - const app = feathers(); + it('does not error when service is configured', () => { + const app = feathers() - app.use('/authentication', new AuthenticationService(app)); + app.use('/authentication', new AuthenticationService(app)) - app.configure(express()); - }); - }); -}); + app.configure(oauth()) + }) + }) +}) diff --git a/packages/authentication-oauth/test/service.test.ts b/packages/authentication-oauth/test/service.test.ts new file mode 100644 index 0000000000..a39310763a --- /dev/null +++ b/packages/authentication-oauth/test/service.test.ts @@ -0,0 +1,57 @@ +import { strict as assert } from 'assert' +import axios, { AxiosResponse } from 'axios' +import { CookieJar } from 'tough-cookie' +import { expressFixture } from './utils/fixture' + +describe('@feathersjs/authentication-oauth service', () => { + const port = 9778 + const req = axios.create({ + withCredentials: true, + maxRedirects: 0 + }) + const cookie = new CookieJar() + let app: Awaited> + + const fetchErrorResponse = async (url: string): Promise => { + try { + await req.get(url) + } catch (error: any) { + return error.response + } + assert.fail('Should never get here') + } + + before(async () => { + app = await expressFixture(port, 5115) + }) + + after(async () => { + await app.teardown() + }) + + it('runs through the oAuth flow', async () => { + const host = `http://localhost:${port}` + let location = `${host}/oauth/github` + + const oauthResponse = await fetchErrorResponse(location) + assert.equal(oauthResponse.status, 303) + + oauthResponse.headers['set-cookie']?.forEach((value) => cookie.setCookie(value, host)) + + location = oauthResponse.data.location + + const providerResponse = await fetchErrorResponse(location) + assert.equal(providerResponse.status, 302) + + location = providerResponse.headers.location + + const { data } = await req.get(location, { + headers: { + cookie: await cookie.getCookieString(host) + } + }) + + assert.ok(data.accessToken) + assert.equal(data.authentication.strategy, 'github') + }) +}) diff --git a/packages/authentication-oauth/test/strategy.test.ts b/packages/authentication-oauth/test/strategy.test.ts index 64d5ede3d5..50e9b27671 100644 --- a/packages/authentication-oauth/test/strategy.test.ts +++ b/packages/authentication-oauth/test/strategy.test.ts @@ -1,150 +1,192 @@ -import { strict as assert } from 'assert'; -import { app, TestOAuthStrategy } from './fixture'; -import { AuthenticationService } from '@feathersjs/authentication'; +import { strict as assert } from 'assert' +import { expressFixture, TestOAuthStrategy } from './utils/fixture' +import { AuthenticationService } from '@feathersjs/authentication' describe('@feathersjs/authentication-oauth/strategy', () => { - const authService = app.service('authentication') as unknown as AuthenticationService; - const [ strategy ] = authService.getStrategies('test') as TestOAuthStrategy[]; + let app: Awaited> + let authService: AuthenticationService + let strategy: TestOAuthStrategy + + before(async () => { + app = await expressFixture(9778, 5115) + authService = app.service('authentication') + strategy = authService.getStrategy('github') as TestOAuthStrategy + }) + + after(async () => { + await app.teardown() + }) it('initializes, has .entityId and configuration', () => { - assert.ok(strategy); - assert.strictEqual(strategy.entityId, 'id'); - assert.ok(strategy.configuration.entity); - }); + assert.ok(strategy) + assert.strictEqual(strategy.entityId, 'id') + assert.ok(strategy.configuration.entity) + }) it('reads configuration from the oauth key', () => { - const testConfigValue = Math.random(); - app.get('authentication').oauth.test.hello = testConfigValue; - assert.strictEqual(strategy.configuration.hello, testConfigValue); - }); + const testConfigValue = Math.random() + app.get('authentication').oauth.github.hello = testConfigValue + assert.strictEqual(strategy.configuration.hello, testConfigValue) + }) it('getRedirect', async () => { - app.get('authentication').oauth.redirect = '/home'; + app.get('authentication').oauth.redirect = '/home' - let redirect = await strategy.getRedirect({ accessToken: 'testing' }); - assert.equal(redirect, '/home#access_token=testing'); + let redirect = await strategy.getRedirect({ accessToken: 'testing' }) + assert.equal(redirect, '/home#access_token=testing') - redirect = await strategy.getRedirect({ accessToken: 'testing' }, { - redirect: '/hi-there' - }); - assert.strictEqual('/home/hi-there#access_token=testing', redirect); + redirect = await strategy.getRedirect( + { accessToken: 'testing' }, + { + redirect: '/hi-there' + } + ) + assert.strictEqual('/home/hi-there#access_token=testing', redirect) - redirect = await strategy.getRedirect(new Error('something went wrong')); - assert.equal(redirect, '/home#error=something%20went%20wrong'); + redirect = await strategy.getRedirect(new Error('something went wrong')) + assert.equal(redirect, '/home#error=something%20went%20wrong') - redirect = await strategy.getRedirect(new Error()); - assert.equal(redirect, '/home#error=OAuth%20Authentication%20not%20successful'); + redirect = await strategy.getRedirect(new Error()) + assert.equal(redirect, '/home#error=OAuth%20Authentication%20not%20successful') - app.get('authentication').oauth.redirect = '/home?'; + app.get('authentication').oauth.redirect = '/home?' - redirect = await strategy.getRedirect({ accessToken: 'testing' }); - assert.equal(redirect, '/home?access_token=testing'); + redirect = await strategy.getRedirect({ accessToken: 'testing' }) + assert.equal(redirect, '/home?access_token=testing') - delete app.get('authentication').oauth.redirect; + delete app.get('authentication').oauth.redirect - redirect = await strategy.getRedirect({ accessToken: 'testing' }); - assert.equal(redirect, null); + redirect = await strategy.getRedirect({ accessToken: 'testing' }) + assert.equal(redirect, null) - app.get('authentication').oauth.redirect = '/#dashboard'; + app.get('authentication').oauth.redirect = '/#dashboard' - redirect = await strategy.getRedirect({ accessToken: 'testing' }); - assert.equal(redirect, '/#dashboard?access_token=testing'); - }); + redirect = await strategy.getRedirect({ accessToken: 'testing' }) + assert.equal(redirect, '/#dashboard?access_token=testing') + }) it('getRedirect with referrer and allowed origins (#2430)', async () => { - app.get('authentication').oauth.origins = [ - 'https://feathersjs.com', - 'https://feathers.cloud' - ]; - - let redirect = await strategy.getRedirect({ accessToken: 'testing' }, { - headers: { - referer: 'https://feathersjs.com/somewhere' - } - }); - assert.equal(redirect, 'https://feathersjs.com#access_token=testing'); + app.get('authentication').oauth.origins = ['https://feathersjs.com', 'https://feathers.cloud'] - redirect = await strategy.getRedirect({ accessToken: 'testing' }, { - headers: { - referer: 'HTTPS://feathers.CLOUD' + let redirect = await strategy.getRedirect( + { accessToken: 'testing' }, + { + headers: { + referer: 'https://feathersjs.com/somewhere' + } } - }); - assert.equal(redirect, 'https://feathers.cloud#access_token=testing'); + ) + assert.equal(redirect, 'https://feathersjs.com#access_token=testing') - redirect = await strategy.getRedirect({ accessToken: 'testing' }, { - redirect: '/home', - headers: { - referer: 'https://feathersjs.com/somewhere' - } - }); - assert.equal(redirect, 'https://feathersjs.com/home#access_token=testing'); + redirect = await strategy.getRedirect({ accessToken: 'testing' }, {}) + assert.equal(redirect, 'https://feathersjs.com#access_token=testing') - await assert.rejects(() => strategy.getRedirect({ accessToken: 'testing' }, { - headers: { - referer: 'https://example.com' + redirect = await strategy.getRedirect( + { accessToken: 'testing' }, + { + headers: { + referer: 'HTTPS://feathers.CLOUD' + } + } + ) + assert.equal(redirect, 'https://feathers.cloud#access_token=testing') + + redirect = await strategy.getRedirect( + { accessToken: 'testing' }, + { + redirect: '/home', + headers: { + referer: 'https://feathersjs.com/somewhere' + } } - }), { - message: 'Referer "https://example.com" not allowed.' - }); - }); + ) + assert.equal(redirect, 'https://feathersjs.com/home#access_token=testing') + + await assert.rejects( + () => + strategy.getRedirect( + { accessToken: 'testing' }, + { + headers: { + referer: 'https://example.com' + } + } + ), + { + message: 'Referer "https://example.com" is not allowed.' + } + ) + }) describe('authenticate', () => { it('with new user', async () => { - const authResult = await strategy.authenticate({ - strategy: 'test', - profile: { - id: 'newEntity' - } - }, {}); + const authResult = await strategy.authenticate( + { + strategy: 'test', + profile: { + id: 'newEntity' + } + }, + {} + ) assert.deepEqual(authResult, { - authentication: { strategy: 'test' }, - user: { testId: 'newEntity', id: authResult.user.id } - }); - }); + authentication: { strategy: 'github' }, + user: { githubId: 'newEntity', id: authResult.user.id } + }) + }) it('with existing user and already linked strategy', async () => { const existingUser = await app.service('users').create({ - testId: 'existingEntity', + githubId: 'existingEntity', name: 'David' - }); - const authResult = await strategy.authenticate({ - strategy: 'test', - profile: { - id: 'existingEntity' - } - }, {}); + }) + const authResult = await strategy.authenticate( + { + strategy: 'test', + profile: { + id: 'existingEntity' + } + }, + {} + ) assert.deepEqual(authResult, { - authentication: { strategy: 'test' }, + authentication: { strategy: 'github' }, user: existingUser - }); - }); + }) + }) it('links user with existing authentication', async () => { const user = await app.service('users').create({ name: 'David' - }); - const jwt = await authService.createAccessToken({}, { - subject: `${user.id}` - }); - - const authResult = await strategy.authenticate({ - strategy: 'test', - profile: { - id: 'linkedEntity' + }) + const jwt = await authService.createAccessToken( + {}, + { + subject: `${user.id}` } - }, { - authentication: { - strategy: 'jwt', - accessToken: jwt + ) + + const authResult = await strategy.authenticate( + { + strategy: 'test', + profile: { + id: 'linkedEntity' + } + }, + { + authentication: { + strategy: 'jwt', + accessToken: jwt + } } - }); + ) assert.deepEqual(authResult, { - authentication: { strategy: 'test' }, - user: { id: user.id, name: user.name, testId: 'linkedEntity' } - }); - }); - }); -}); + authentication: { strategy: 'github' }, + user: { id: user.id, name: user.name, githubId: 'linkedEntity' } + }) + }) + }) +}) diff --git a/packages/authentication-oauth/test/utils.test.ts b/packages/authentication-oauth/test/utils.test.ts index 04aee35b22..a84fd52997 100644 --- a/packages/authentication-oauth/test/utils.test.ts +++ b/packages/authentication-oauth/test/utils.test.ts @@ -1,12 +1,9 @@ -import { strict as assert } from 'assert'; -import { getDefaultSettings } from '../src/utils'; -import { app } from './fixture'; +import { strict as assert } from 'assert' +// import { getDefaultSettings } from '../src/utils' +// import { app } from './fixture' describe('@feathersjs/authentication-oauth/utils', () => { - it('getDefaultSettings', () => { - const settings = getDefaultSettings(app); - - assert.equal(settings.authService, undefined); - assert.equal(settings.linkStrategy, 'jwt'); - }); -}); + it('getGrantConfig', () => { + assert.ok(true) + }) +}) diff --git a/packages/authentication-oauth/test/utils/fixture.ts b/packages/authentication-oauth/test/utils/fixture.ts new file mode 100644 index 0000000000..0371f516ea --- /dev/null +++ b/packages/authentication-oauth/test/utils/fixture.ts @@ -0,0 +1,95 @@ +import { Application, feathers, NextFunction } from '@feathersjs/feathers' +import express, { rest, errorHandler } from '@feathersjs/express' +import { memory, MemoryService } from '@feathersjs/memory' +import { + AuthenticationService, + JWTStrategy, + AuthenticationRequest, + AuthenticationParams +} from '@feathersjs/authentication' +import { provider } from './provider' +import { oauth, OAuthStrategy } from '../../src' + +export interface ServiceTypes { + authentication: AuthenticationService + users: MemoryService +} + +export class TestOAuthStrategy extends OAuthStrategy { + async authenticate(data: AuthenticationRequest, params: AuthenticationParams) { + const { fromMiddleware } = params + const authResult = await super.authenticate(data, params) + + if (fromMiddleware) { + authResult.fromMiddleware = fromMiddleware + } + + return authResult + } +} + +export const fixtureConfig = + (port: number, providerInstance: Awaited>) => (app: Application) => { + app.set('host', '127.0.0.1') + app.set('port', port) + app.set('authentication', { + secret: 'supersecret', + entity: 'user', + service: 'users', + authStrategies: ['jwt'], + oauth: { + github: { + key: 'some-key', + secret: 'a secret secret', + authorize_url: providerInstance.url(`/github/authorize_url`), + access_url: providerInstance.url(`/github/access_url`), + dynamic: true + } + } + }) + + return app + } + +export const expressFixture = async (serverPort: number, providerPort: number) => { + const providerInstance = await provider({ flow: 'oauth2', port: providerPort }) + const app = express(feathers()) + const auth = new AuthenticationService(app) + + auth.register('jwt', new JWTStrategy()) + auth.register('github', new TestOAuthStrategy()) + + app.configure(rest()) + app.configure(fixtureConfig(serverPort, providerInstance)) + + app.use((req, _res, next) => { + req.feathers = { fromMiddleware: 'testing' } + next() + }) + app.use('authentication', auth) + app.use('users', memory()) + + app.configure(oauth()) + app.use(errorHandler({ logger: false })) + app.hooks({ + teardown: [ + async (_context: any, next: NextFunction) => { + await providerInstance.close() + await next() + } + ] + }) + app.hooks({ + error: { + all: [ + async (context) => { + console.error(context.error) + } + ] + } + }) + + await app.listen(serverPort) + + return app +} diff --git a/packages/authentication-oauth/test/utils/provider.ts b/packages/authentication-oauth/test/utils/provider.ts new file mode 100644 index 0000000000..77eafa7a84 --- /dev/null +++ b/packages/authentication-oauth/test/utils/provider.ts @@ -0,0 +1,282 @@ +/* eslint-disable @typescript-eslint/no-non-null-assertion */ +/* eslint-disable @typescript-eslint/no-empty-function */ +// Ported from https://github.com/simov/grant/blob/master/test/util/provider.js +import http from 'http' +import _url from 'url' +import qs from 'qs' + +const buffer = (req: http.IncomingMessage, done: any) => { + let data = '' + req.on('data', (chunk: any) => (data += chunk)) + req.on('end', () => done(/^{.*}$/.test(data) ? JSON.parse(data) : qs.parse(data))) +} +const _query = (req: http.IncomingMessage) => { + const parsed = _url.parse(req.url as string, false) + const query = qs.parse(parsed.query as any) + return query +} +const _oauth = (req: http.IncomingMessage) => + qs.parse((req.headers.authorization || '').replace('OAuth ', '').replace(/"/g, '').replace(/,/g, '&')) + +const sign = (...args: any[]) => + args + .map((arg, index) => + index < 2 + ? Buffer.from(JSON.stringify(arg)) + .toString('base64') + .replace(/=/g, '') + .replace(/\+/g, '-') + .replace(/\//g, '_') + : arg + ) + .join('.') + +export const provider = async ({ flow, port = 5000 }: { flow: 'oauth2' | 'oauth1'; port: number }) => { + const server = await (flow === 'oauth2' ? oauth2(port) : oauth1(port)) + return { + oauth1, + oauth2, + on, + server, + url: (path: string) => `http://localhost:${port}${path}`, + close: () => new Promise((resolve) => server.close(resolve)) + } +} + +const oauth1 = (port: number) => + new Promise((resolve) => { + let callback: any + const server = http.createServer() + server.on('request', (req, res) => { + const method = req.method + const url = req.url as string + const headers = req.headers + const oauth = _oauth(req) + const query = _query(req) + const provider = /^\/(.*)\/.*/.exec(url) && /^\/(.*)\/.*/.exec(url)![1] + + if (/request_url/.test(url)) { + callback = oauth.oauth_callback + buffer(req, (form: any) => { + if (provider === 'getpocket') { + callback = form.redirect_uri + } + on.request({ url, headers, query, form, oauth }) + provider === 'sellsy' + ? res.writeHead(200, { 'content-type': 'application/json' }) + : res.writeHead(200, { 'content-type': 'application/x-www-form-urlencoded' }) + provider === 'getpocket' + ? res.end(qs.stringify({ code: 'code' })) + : provider === 'sellsy' + ? res.end( + 'authentification_url=https://apifeed.sellsy.com/0/login.php&oauth_token=token&oauth_token_secret=secret&oauth_callback_confirmed=true' + ) + : res.end(qs.stringify({ oauth_token: 'token', oauth_token_secret: 'secret' })) + }) + } else if (/authorize_url/.test(url)) { + const location = callback + '?' + qs.stringify({ oauth_token: 'token', oauth_verifier: 'verifier' }) + on.authorize({ url, headers, query }) + res.writeHead(302, { location }) + res.end() + } else if (/access_url/.test(url)) { + buffer(req, (form: any) => { + on.access({ url, headers, query, form, oauth }) + res.writeHead(200, { 'content-type': 'application/json' }) + provider === 'getpocket' + ? res.end(JSON.stringify({ access_token: 'token' })) + : res.end( + JSON.stringify({ + oauth_token: 'token', + oauth_token_secret: 'secret', + user_id: provider === 'twitter' ? 'id' : undefined + }) + ) + }) + } else if (/request_error_message/.test(url)) { + callback = oauth.oauth_callback + buffer(req, (form: any) => { + on.request({ url, headers, query, form, oauth }) + res.writeHead(200, { 'content-type': 'application/x-www-form-urlencoded' }) + res.end(qs.stringify({ error: { message: 'invalid' } })) + }) + } else if (/request_error_token/.test(url)) { + callback = oauth.oauth_callback + buffer(req, (form: any) => { + on.request({ url, headers, query, form, oauth }) + res.writeHead(200, { 'content-type': 'application/x-www-form-urlencoded' }) + res.end() + }) + } else if (/request_error_status/.test(url)) { + callback = oauth.oauth_callback + buffer(req, (form: any) => { + on.request({ url, headers, query, form, oauth }) + res.writeHead(500, { 'content-type': 'application/x-www-form-urlencoded' }) + res.end(qs.stringify({ invalid: 'request_url' })) + }) + } else if (/authorize_error_message/.test(url)) { + const location = callback + '?' + qs.stringify({ error: { message: 'invalid' } }) + on.authorize({ url, headers, query }) + res.writeHead(302, { location }) + res.end() + } else if (/authorize_error_token/.test(url)) { + const location = callback as string + on.authorize({ url, headers, query }) + res.writeHead(302, { location }) + res.end() + } else if (/access_error_status/.test(url)) { + buffer(req, (form: any) => { + on.access({ url, headers, query, form, oauth }) + res.writeHead(500, { 'content-type': 'application/json' }) + res.end(JSON.stringify({ invalid: 'access_url' })) + }) + } else if (/profile_url/.test(url)) { + on.profile({ method, url, query, headers }) + res.writeHead(200, { 'content-type': 'application/json' }) + provider === 'flickr' + ? res.end('callback({"user": "simov"})') + : res.end(JSON.stringify({ user: 'simov' })) + } + }) + server.listen(port, () => resolve(server)) + }) + +const oauth2 = (port: number) => + new Promise((resolve) => { + const server = http.createServer() + let openid: any + server.on('request', (req, res) => { + const method = req.method + const url = req.url as string + const headers = req.headers + const query = _query(req) as any + const provider = /^\/(.*)\/.*/.exec(url) && /^\/(.*)\/.*/.exec(url)![1] + + if (/authorize_url/.test(url)) { + openid = (query.scope || []).includes('openid') + on.authorize({ provider, method, url, headers, query }) + if (query.response_mode === 'form_post') { + provider === 'apple' + ? res.end( + qs.stringify({ + code: 'code', + user: { name: { firstName: 'jon', lastName: 'doe' }, email: 'jon@doe.com' } + }) + ) + : res.end('code') + return + } + const location = + query.redirect_uri + + '?' + + (provider === 'intuit' + ? qs.stringify({ code: 'code', realmId: '123' }) + : qs.stringify({ code: 'code' })) + res.writeHead(302, { location }) + res.end() + } else if (/access_url/.test(url)) { + buffer(req, (form: any) => { + on.access({ provider, method, url, headers, query, form }) + res.writeHead(200, { 'content-type': 'application/json' }) + provider === 'concur' + ? res.end(' token refresh ') + : provider === 'withings' + ? res.end( + JSON.stringify({ + body: { + access_token: 'token', + refresh_token: 'refresh', + expires_in: 3600 + } + }) + ) + : res.end( + JSON.stringify({ + access_token: 'token', + refresh_token: 'refresh', + expires_in: 3600, + id_token: openid ? sign({ typ: 'JWT' }, { nonce: 'whatever' }, 'signature') : undefined, + open_id: provider === 'tiktok' ? 'id' : undefined, + uid: provider === 'weibo' ? 'id' : undefined, + openid: provider === 'wechat' ? 'openid' : undefined + }) + ) + }) + } else if (/authorize_error_message/.test(url)) { + on.authorize({ url, query, headers }) + const location = query.redirect_uri + '?' + qs.stringify({ error: { message: 'invalid' } }) + res.writeHead(302, { location }) + res.end() + } else if (/authorize_error_code/.test(url)) { + on.authorize({ url, query, headers }) + const location = query.redirect_uri as string + res.writeHead(302, { location }) + res.end() + } else if (/authorize_error_state_mismatch/.test(url)) { + on.authorize({ url, query, headers }) + const location = query.redirect_uri + '?' + qs.stringify({ code: 'code', state: 'whatever' }) + res.writeHead(302, { location }) + res.end() + } else if (/authorize_error_state_missing/.test(url)) { + on.authorize({ url, query, headers }) + const location = query.redirect_uri + '?' + qs.stringify({ code: 'code' }) + res.writeHead(302, { location }) + res.end() + } else if (/access_error_nonce_mismatch/.test(url)) { + buffer(req, (form: any) => { + on.access({ method, url, query, headers, form }) + res.writeHead(200, { 'content-type': 'application/json' }) + res.end( + JSON.stringify({ + id_token: sign({ typ: 'JWT' }, { nonce: 'whatever' }, 'signature') + }) + ) + }) + } else if (/access_error_nonce_missing/.test(url)) { + buffer(req, (form: any) => { + on.access({ method, url, query, headers, form }) + res.writeHead(200, { 'content-type': 'application/json' }) + res.end( + JSON.stringify({ + id_token: sign({ typ: 'JWT' }, {}, 'signature') + }) + ) + }) + } else if (/access_error_message/.test(url)) { + buffer(req, (form: any) => { + on.access({ method, url, query, headers, form }) + res.writeHead(200, { 'content-type': 'application/json' }) + res.end(JSON.stringify({ error: { message: 'invalid' } })) + }) + } else if (/access_error_status/.test(url)) { + buffer(req, (form: any) => { + on.access({ method, url, query, headers, form }) + res.writeHead(500, { 'content-type': 'application/json' }) + res.end(JSON.stringify({ invalid: 'access_url' })) + }) + } else if (/profile_url/.test(url)) { + if (method === 'POST') { + buffer(req, (form: any) => { + on.profile({ method, url, query, headers, form }) + res.writeHead(200, { 'content-type': 'application/json' }) + res.end(JSON.stringify({ id: 'test', user: 'simov' })) + }) + } else { + on.profile({ method, url, query, headers }) + res.writeHead(200, { 'content-type': 'application/json' }) + res.end(JSON.stringify({ id: 'test', user: 'simov' })) + } + } else if (/profile_error/.test(url)) { + on.profile({ method, url, query, headers }) + res.writeHead(400, { 'content-type': 'application/json' }) + res.end(JSON.stringify({ error: { message: 'Not Found' } })) + } + }) + server.listen(port, () => resolve(server)) + }) + +const on = { + request: (_opts: any) => {}, + authorize: (_opts: any) => {}, + access: (_opts: any) => {}, + profile: (_opts: any) => {} +} diff --git a/packages/authentication/CHANGELOG.md b/packages/authentication/CHANGELOG.md index 280cb4b8ad..0bf51e5aa8 100644 --- a/packages/authentication/CHANGELOG.md +++ b/packages/authentication/CHANGELOG.md @@ -3,664 +3,474 @@ All notable changes to this project will be documented in this file. See [Conventional Commits](https://conventionalcommits.org) for commit guidelines. -# [5.0.0-pre.16](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.15...v5.0.0-pre.16) (2022-01-12) - +# [5.0.0-pre.31](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.30...v5.0.0-pre.31) (2022-10-12) ### Features -* **express, koa:** make transports similar ([#2486](https://github.com/feathersjs/feathers/issues/2486)) ([26aa937](https://github.com/feathersjs/feathers/commit/26aa937c114fb8596dfefc599b1f53cead69c159)) +- **cli:** Generate full client test suite and improve typed client ([#2788](https://github.com/feathersjs/feathers/issues/2788)) ([57119b6](https://github.com/feathersjs/feathers/commit/57119b6bb2797f7297cf054268a248c093ecd538)) + +# [5.0.0-pre.30](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.29...v5.0.0-pre.30) (2022-10-07) +### Features +- **core:** Allow to unregister services at runtime ([#2756](https://github.com/feathersjs/feathers/issues/2756)) ([d16601f](https://github.com/feathersjs/feathers/commit/d16601f2277dca5357866ffdefba2a611f6dc7fa)) +- **schema:** Make schemas validation library independent and add TypeBox support ([#2772](https://github.com/feathersjs/feathers/issues/2772)) ([44172d9](https://github.com/feathersjs/feathers/commit/44172d99b566d11d9ceda04f1d0bf72b6d05ce76)) +# [5.0.0-pre.29](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.28...v5.0.0-pre.29) (2022-09-16) +### Features -# [5.0.0-pre.15](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.14...v5.0.0-pre.15) (2021-11-27) +- **authentication-oauth:** Koa and transport independent oAuth authentication ([#2737](https://github.com/feathersjs/feathers/issues/2737)) ([9231525](https://github.com/feathersjs/feathers/commit/9231525a24bb790ba9c5d940f2867a9c727691c9)) +# [5.0.0-pre.28](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.27...v5.0.0-pre.28) (2022-08-03) ### Bug Fixes -* **typescript:** Overall typing improvements ([#2478](https://github.com/feathersjs/feathers/issues/2478)) ([b8eb804](https://github.com/feathersjs/feathers/commit/b8eb804158556d9651a8607e3c3fda15e0bfd110)) +- **cli:** Improve generated application and client ([#2701](https://github.com/feathersjs/feathers/issues/2701)) ([bd55ffb](https://github.com/feathersjs/feathers/commit/bd55ffb812e89bf215f4515e7f137656ea888c3f)) +# [5.0.0-pre.27](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.26...v5.0.0-pre.27) (2022-07-13) -### Features +**Note:** Version bump only for package @feathersjs/authentication -* **authentication-oauth:** Allow dynamic oAuth redirect ([#2469](https://github.com/feathersjs/feathers/issues/2469)) ([b7143d4](https://github.com/feathersjs/feathers/commit/b7143d4c0fbe961e714f79512be04449b9bbd7d9)) +# [5.0.0-pre.26](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.25...v5.0.0-pre.26) (2022-06-22) +**Note:** Version bump only for package @feathersjs/authentication +# [5.0.0-pre.25](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.24...v5.0.0-pre.25) (2022-06-22) +**Note:** Version bump only for package @feathersjs/authentication +# [5.0.0-pre.24](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.23...v5.0.0-pre.24) (2022-06-21) -# [5.0.0-pre.14](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.13...v5.0.0-pre.14) (2021-10-13) +### Bug Fixes -**Note:** Version bump only for package @feathersjs/authentication +- **authentication:** Add safe dispatch data for authentication requests ([#2662](https://github.com/feathersjs/feathers/issues/2662)) ([d8104a1](https://github.com/feathersjs/feathers/commit/d8104a19ee9181e6a5ea81014af29ff9a3c28a8a)) +# [5.0.0-pre.23](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.22...v5.0.0-pre.23) (2022-06-06) +**Note:** Version bump only for package @feathersjs/authentication +# [5.0.0-pre.22](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.21...v5.0.0-pre.22) (2022-05-24) +**Note:** Version bump only for package @feathersjs/authentication -# [5.0.0-pre.13](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.12...v5.0.0-pre.13) (2021-10-13) +# [5.0.0-pre.21](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.20...v5.0.0-pre.21) (2022-05-23) **Note:** Version bump only for package @feathersjs/authentication +# [5.0.0-pre.20](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.19...v5.0.0-pre.20) (2022-05-04) +### Bug Fixes +- **dependencies:** Lock monorepo package version numbers ([#2623](https://github.com/feathersjs/feathers/issues/2623)) ([5640c10](https://github.com/feathersjs/feathers/commit/5640c1020cc139994e695d658c08bad3494db507)) +# [5.0.0-pre.19](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.18...v5.0.0-pre.19) (2022-05-01) -# [5.0.0-pre.12](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.11...v5.0.0-pre.12) (2021-10-12) - -**Note:** Version bump only for package @feathersjs/authentication +### Features +- **typescript:** Improve adapter typings ([#2605](https://github.com/feathersjs/feathers/issues/2605)) ([3b2ca0a](https://github.com/feathersjs/feathers/commit/3b2ca0a6a8e03e8390272c4d7e930b4bffdaacf5)) +- **typescript:** Improve params and query typeability ([#2600](https://github.com/feathersjs/feathers/issues/2600)) ([df28b76](https://github.com/feathersjs/feathers/commit/df28b7619161f1df5e700326f52cca1a92dc5d28)) +# [5.0.0-pre.18](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.17...v5.0.0-pre.18) (2022-04-11) +### Features +- **authentication:** Add setup method for auth strategies ([#1611](https://github.com/feathersjs/feathers/issues/1611)) ([a3c3581](https://github.com/feathersjs/feathers/commit/a3c35814dccdbbf6de96f04f60b226ce206c6dbe)) +- **configuration:** Allow app configuration to be validated against a schema ([#2590](https://github.com/feathersjs/feathers/issues/2590)) ([a268f86](https://github.com/feathersjs/feathers/commit/a268f86da92a8ada14ed11ab456aac0a4bba5bb0)) -# [5.0.0-pre.11](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.10...v5.0.0-pre.11) (2021-10-06) +# [5.0.0-pre.17](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.16...v5.0.0-pre.17) (2022-02-15) **Note:** Version bump only for package @feathersjs/authentication +# [5.0.0-pre.16](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.15...v5.0.0-pre.16) (2022-01-12) +### Features +- **express, koa:** make transports similar ([#2486](https://github.com/feathersjs/feathers/issues/2486)) ([26aa937](https://github.com/feathersjs/feathers/commit/26aa937c114fb8596dfefc599b1f53cead69c159)) +# [5.0.0-pre.15](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.14...v5.0.0-pre.15) (2021-11-27) -# [5.0.0-pre.10](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.9...v5.0.0-pre.10) (2021-09-19) +### Bug Fixes -**Note:** Version bump only for package @feathersjs/authentication +- **typescript:** Overall typing improvements ([#2478](https://github.com/feathersjs/feathers/issues/2478)) ([b8eb804](https://github.com/feathersjs/feathers/commit/b8eb804158556d9651a8607e3c3fda15e0bfd110)) +### Features +- **authentication-oauth:** Allow dynamic oAuth redirect ([#2469](https://github.com/feathersjs/feathers/issues/2469)) ([b7143d4](https://github.com/feathersjs/feathers/commit/b7143d4c0fbe961e714f79512be04449b9bbd7d9)) +# [5.0.0-pre.14](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.13...v5.0.0-pre.14) (2021-10-13) +**Note:** Version bump only for package @feathersjs/authentication -# [5.0.0-pre.9](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.8...v5.0.0-pre.9) (2021-08-09) +# [5.0.0-pre.13](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.12...v5.0.0-pre.13) (2021-10-13) **Note:** Version bump only for package @feathersjs/authentication +# [5.0.0-pre.12](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.11...v5.0.0-pre.12) (2021-10-12) +**Note:** Version bump only for package @feathersjs/authentication +# [5.0.0-pre.11](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.10...v5.0.0-pre.11) (2021-10-06) +**Note:** Version bump only for package @feathersjs/authentication -# [5.0.0-pre.8](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.7...v5.0.0-pre.8) (2021-08-09) +# [5.0.0-pre.10](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.9...v5.0.0-pre.10) (2021-09-19) **Note:** Version bump only for package @feathersjs/authentication +# [5.0.0-pre.9](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.8...v5.0.0-pre.9) (2021-08-09) +**Note:** Version bump only for package @feathersjs/authentication +# [5.0.0-pre.8](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.7...v5.0.0-pre.8) (2021-08-09) +**Note:** Version bump only for package @feathersjs/authentication # [5.0.0-pre.7](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.6...v5.0.0-pre.7) (2021-08-09) **Note:** Version bump only for package @feathersjs/authentication - - - - # [5.0.0-pre.6](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.5...v5.0.0-pre.6) (2021-08-08) **Note:** Version bump only for package @feathersjs/authentication - - - - # [5.0.0-pre.5](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.4...v5.0.0-pre.5) (2021-06-23) - ### Bug Fixes -* **hooks:** Migrate built-in hooks and allow backwards compatibility ([#2358](https://github.com/feathersjs/feathers/issues/2358)) ([759c5a1](https://github.com/feathersjs/feathers/commit/759c5a19327a731af965c3604119393b3d09a406)) -* **koa:** Use extended query parser for compatibility ([#2397](https://github.com/feathersjs/feathers/issues/2397)) ([b2944ba](https://github.com/feathersjs/feathers/commit/b2944bac3ec6d5ecc80dc518cd4e58093692db74)) - +- **hooks:** Migrate built-in hooks and allow backwards compatibility ([#2358](https://github.com/feathersjs/feathers/issues/2358)) ([759c5a1](https://github.com/feathersjs/feathers/commit/759c5a19327a731af965c3604119393b3d09a406)) +- **koa:** Use extended query parser for compatibility ([#2397](https://github.com/feathersjs/feathers/issues/2397)) ([b2944ba](https://github.com/feathersjs/feathers/commit/b2944bac3ec6d5ecc80dc518cd4e58093692db74)) ### Features -* **adapter-commons:** Add support for params.adapter option and move memory adapter to @feathersjs/memory ([#2367](https://github.com/feathersjs/feathers/issues/2367)) ([a43e7da](https://github.com/feathersjs/feathers/commit/a43e7da22b6b981a96d1321736ea9a0cb924fb4f)) - - - - +- **adapter-commons:** Add support for params.adapter option and move memory adapter to @feathersjs/memory ([#2367](https://github.com/feathersjs/feathers/issues/2367)) ([a43e7da](https://github.com/feathersjs/feathers/commit/a43e7da22b6b981a96d1321736ea9a0cb924fb4f)) # [5.0.0-pre.4](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.3...v5.0.0-pre.4) (2021-05-13) **Note:** Version bump only for package @feathersjs/authentication - - - - # [5.0.0-pre.3](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.2...v5.0.0-pre.3) (2021-04-21) - ### Bug Fixes -* **typescript:** Improve TypeScript backwards compatibility ([#2310](https://github.com/feathersjs/feathers/issues/2310)) ([f33be73](https://github.com/feathersjs/feathers/commit/f33be73fc46a533efb15df9aab0658e3240d3897)) - +- **typescript:** Improve TypeScript backwards compatibility ([#2310](https://github.com/feathersjs/feathers/issues/2310)) ([f33be73](https://github.com/feathersjs/feathers/commit/f33be73fc46a533efb15df9aab0658e3240d3897)) ### Features -* **dependencies:** Remove direct debug dependency ([#2296](https://github.com/feathersjs/feathers/issues/2296)) ([501d416](https://github.com/feathersjs/feathers/commit/501d4164d30c6a126906dc640cdfdc82207ba34a)) - - - - +- **dependencies:** Remove direct debug dependency ([#2296](https://github.com/feathersjs/feathers/issues/2296)) ([501d416](https://github.com/feathersjs/feathers/commit/501d4164d30c6a126906dc640cdfdc82207ba34a)) # [5.0.0-pre.2](https://github.com/feathersjs/feathers/compare/v5.0.0-beta.1...v5.0.0-pre.2) (2021-04-06) **Note:** Version bump only for package @feathersjs/authentication - - - - # [5.0.0-beta.1](https://github.com/feathersjs/feathers/compare/v5.0.0-beta.0...v5.0.0-beta.1) (2021-04-03) **Note:** Version bump only for package @feathersjs/authentication - - - - # [5.0.0-beta.0](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.1...v5.0.0-beta.0) (2021-03-28) - ### Bug Fixes -* Update Grant usage and other dependencies ([#2264](https://github.com/feathersjs/feathers/issues/2264)) ([7b0f8fa](https://github.com/feathersjs/feathers/commit/7b0f8fad252419ed0ad0bf259cdf3104d322ab60)) - +- Update Grant usage and other dependencies ([#2264](https://github.com/feathersjs/feathers/issues/2264)) ([7b0f8fa](https://github.com/feathersjs/feathers/commit/7b0f8fad252419ed0ad0bf259cdf3104d322ab60)) ### Features -* Application service types default to any ([#1566](https://github.com/feathersjs/feathers/issues/1566)) ([d93ba9a](https://github.com/feathersjs/feathers/commit/d93ba9a17edd20d3397bb00f4f6e82e804e42ed6)) -* Feathers v5 core refactoring and features ([#2255](https://github.com/feathersjs/feathers/issues/2255)) ([2dafb7c](https://github.com/feathersjs/feathers/commit/2dafb7ce14ba57406aeec13d10ca45b1e709bee9)) - - - - +- Application service types default to any ([#1566](https://github.com/feathersjs/feathers/issues/1566)) ([d93ba9a](https://github.com/feathersjs/feathers/commit/d93ba9a17edd20d3397bb00f4f6e82e804e42ed6)) +- Feathers v5 core refactoring and features ([#2255](https://github.com/feathersjs/feathers/issues/2255)) ([2dafb7c](https://github.com/feathersjs/feathers/commit/2dafb7ce14ba57406aeec13d10ca45b1e709bee9)) # [5.0.0-pre.1](https://github.com/feathersjs/feathers/compare/v4.5.11...v5.0.0-pre.1) (2020-12-17) - - # [5.0.0-pre.0](https://github.com/feathersjs/feathers/compare/v4.5.4...v5.0.0-pre.0) (2020-05-19) **Note:** Version bump only for package @feathersjs/authentication - - - - # [5.0.0-pre.0](https://github.com/feathersjs/feathers/compare/v4.5.4...v5.0.0-pre.0) (2020-05-19) - - ## [4.5.11](https://github.com/feathersjs/feathers/compare/v4.5.10...v4.5.11) (2020-12-05) **Note:** Version bump only for package @feathersjs/authentication - - - - ## [4.5.10](https://github.com/feathersjs/feathers/compare/v4.5.9...v4.5.10) (2020-11-08) - ### Bug Fixes -* **authentication:** consistent response return between local and jwt strategy ([#2042](https://github.com/feathersjs/feathers/issues/2042)) ([8d25be1](https://github.com/feathersjs/feathers/commit/8d25be101a2593a9e789375c928a07780b9e28cf)) - - - - +- **authentication:** consistent response return between local and jwt strategy ([#2042](https://github.com/feathersjs/feathers/issues/2042)) ([8d25be1](https://github.com/feathersjs/feathers/commit/8d25be101a2593a9e789375c928a07780b9e28cf)) ## [4.5.9](https://github.com/feathersjs/feathers/compare/v4.5.8...v4.5.9) (2020-10-09) **Note:** Version bump only for package @feathersjs/authentication - - - - ## [4.5.8](https://github.com/feathersjs/feathers/compare/v4.5.7...v4.5.8) (2020-08-12) **Note:** Version bump only for package @feathersjs/authentication - - - - ## [4.5.7](https://github.com/feathersjs/feathers/compare/v4.5.6...v4.5.7) (2020-07-24) - ### Bug Fixes -* **authentication:** Add JWT getEntityQuery ([#2013](https://github.com/feathersjs/feathers/issues/2013)) ([e0e7fb5](https://github.com/feathersjs/feathers/commit/e0e7fb5162940fe776731283b40026c61d9c8a33)) - - - - +- **authentication:** Add JWT getEntityQuery ([#2013](https://github.com/feathersjs/feathers/issues/2013)) ([e0e7fb5](https://github.com/feathersjs/feathers/commit/e0e7fb5162940fe776731283b40026c61d9c8a33)) ## [4.5.6](https://github.com/feathersjs/feathers/compare/v4.5.5...v4.5.6) (2020-07-12) - ### Bug Fixes -* **authentication:** Omit query in JWT strategy ([#2011](https://github.com/feathersjs/feathers/issues/2011)) ([04ce7e9](https://github.com/feathersjs/feathers/commit/04ce7e98515fe9d495cd0e83e0da097e9bcd7382)) - - - - +- **authentication:** Omit query in JWT strategy ([#2011](https://github.com/feathersjs/feathers/issues/2011)) ([04ce7e9](https://github.com/feathersjs/feathers/commit/04ce7e98515fe9d495cd0e83e0da097e9bcd7382)) ## [4.5.5](https://github.com/feathersjs/feathers/compare/v4.5.4...v4.5.5) (2020-07-11) - ### Bug Fixes -* **authentication:** Include query params when authenticating via authenticate hook [#2009](https://github.com/feathersjs/feathers/issues/2009) ([4cdb7bf](https://github.com/feathersjs/feathers/commit/4cdb7bf2898385ddac7a1692bc9ac2f6cf5ad446)) - - - - +- **authentication:** Include query params when authenticating via authenticate hook [#2009](https://github.com/feathersjs/feathers/issues/2009) ([4cdb7bf](https://github.com/feathersjs/feathers/commit/4cdb7bf2898385ddac7a1692bc9ac2f6cf5ad446)) ## [4.5.3](https://github.com/feathersjs/feathers/compare/v4.5.2...v4.5.3) (2020-04-17) - ### Bug Fixes -* **authentication:** Remove entity from connection information on logout ([#1889](https://github.com/feathersjs/feathers/issues/1889)) ([b062753](https://github.com/feathersjs/feathers/commit/b0627530d61babe15dd84369d3093ccae4b780ca)) - - - - +- **authentication:** Remove entity from connection information on logout ([#1889](https://github.com/feathersjs/feathers/issues/1889)) ([b062753](https://github.com/feathersjs/feathers/commit/b0627530d61babe15dd84369d3093ccae4b780ca)) ## [4.5.2](https://github.com/feathersjs/feathers/compare/v4.5.1...v4.5.2) (2020-03-04) - ### Bug Fixes -* **authentication:** Improve JWT strategy configuration error message ([#1844](https://github.com/feathersjs/feathers/issues/1844)) ([2c771db](https://github.com/feathersjs/feathers/commit/2c771dbb22d53d4f7de3c3f514e57afa1a186322)) - - - - +- **authentication:** Improve JWT strategy configuration error message ([#1844](https://github.com/feathersjs/feathers/issues/1844)) ([2c771db](https://github.com/feathersjs/feathers/commit/2c771dbb22d53d4f7de3c3f514e57afa1a186322)) ## [4.5.1](https://github.com/feathersjs/feathers/compare/v4.5.0...v4.5.1) (2020-01-24) **Note:** Version bump only for package @feathersjs/authentication - - - - # [4.5.0](https://github.com/feathersjs/feathers/compare/v4.4.3...v4.5.0) (2020-01-18) - ### Bug Fixes -* Add `params.authentication` type, remove `hook.connection` type ([#1732](https://github.com/feathersjs/feathers/issues/1732)) ([d46b7b2](https://github.com/feathersjs/feathers/commit/d46b7b2abac8862c0e4dbfce20d71b8b8a96692f)) - - - - +- Add `params.authentication` type, remove `hook.connection` type ([#1732](https://github.com/feathersjs/feathers/issues/1732)) ([d46b7b2](https://github.com/feathersjs/feathers/commit/d46b7b2abac8862c0e4dbfce20d71b8b8a96692f)) ## [4.4.3](https://github.com/feathersjs/feathers/compare/v4.4.1...v4.4.3) (2019-12-06) **Note:** Version bump only for package @feathersjs/authentication - - - - ## [4.4.1](https://github.com/feathersjs/feathers/compare/v4.4.0...v4.4.1) (2019-11-27) **Note:** Version bump only for package @feathersjs/authentication - - - - # [4.4.0](https://github.com/feathersjs/feathers/compare/v4.3.11...v4.4.0) (2019-11-27) **Note:** Version bump only for package @feathersjs/authentication - - - - ## [4.3.11](https://github.com/feathersjs/feathers/compare/v4.3.10...v4.3.11) (2019-11-11) - ### Bug Fixes -* **authentication:** Retain object references in authenticate hook ([#1675](https://github.com/feathersjs/feathers/issues/1675)) ([e1939be](https://github.com/feathersjs/feathers/commit/e1939be19d4e79d3f5e2fe69ba894a11c627ae99)) - - - - +- **authentication:** Retain object references in authenticate hook ([#1675](https://github.com/feathersjs/feathers/issues/1675)) ([e1939be](https://github.com/feathersjs/feathers/commit/e1939be19d4e79d3f5e2fe69ba894a11c627ae99)) ## [4.3.10](https://github.com/feathersjs/feathers/compare/v4.3.9...v4.3.10) (2019-10-26) **Note:** Version bump only for package @feathersjs/authentication - - - - ## [4.3.9](https://github.com/feathersjs/feathers/compare/v4.3.8...v4.3.9) (2019-10-26) - ### Bug Fixes -* Add jsonwebtoken TypeScript type dependency ([317c80a](https://github.com/feathersjs/feathers/commit/317c80a9205e8853bb830a12c3aa1a19e95f9abc)) -* Small type improvements ([#1624](https://github.com/feathersjs/feathers/issues/1624)) ([50162c6](https://github.com/feathersjs/feathers/commit/50162c6e562f0a47c6a280c4f01fff7c3afee293)) - - - - +- Add jsonwebtoken TypeScript type dependency ([317c80a](https://github.com/feathersjs/feathers/commit/317c80a9205e8853bb830a12c3aa1a19e95f9abc)) +- Small type improvements ([#1624](https://github.com/feathersjs/feathers/issues/1624)) ([50162c6](https://github.com/feathersjs/feathers/commit/50162c6e562f0a47c6a280c4f01fff7c3afee293)) ## [4.3.7](https://github.com/feathersjs/feathers/compare/v4.3.6...v4.3.7) (2019-10-14) **Note:** Version bump only for package @feathersjs/authentication - - - - ## [4.3.5](https://github.com/feathersjs/feathers/compare/v4.3.4...v4.3.5) (2019-10-07) - ### Bug Fixes -* Authentication type improvements and timeout fix ([#1605](https://github.com/feathersjs/feathers/issues/1605)) ([19854d3](https://github.com/feathersjs/feathers/commit/19854d3)) -* Improve error message when authentication strategy is not allowed ([#1600](https://github.com/feathersjs/feathers/issues/1600)) ([317a312](https://github.com/feathersjs/feathers/commit/317a312)) - - - - +- Authentication type improvements and timeout fix ([#1605](https://github.com/feathersjs/feathers/issues/1605)) ([19854d3](https://github.com/feathersjs/feathers/commit/19854d3)) +- Improve error message when authentication strategy is not allowed ([#1600](https://github.com/feathersjs/feathers/issues/1600)) ([317a312](https://github.com/feathersjs/feathers/commit/317a312)) ## [4.3.4](https://github.com/feathersjs/feathers/compare/v4.3.3...v4.3.4) (2019-10-03) **Note:** Version bump only for package @feathersjs/authentication - - - - ## [4.3.3](https://github.com/feathersjs/feathers/compare/v4.3.2...v4.3.3) (2019-09-21) - ### Bug Fixes -* check for undefined access token ([#1571](https://github.com/feathersjs/feathers/issues/1571)) ([976369d](https://github.com/feathersjs/feathers/commit/976369d)) -* Small improvements in dependencies and code sturcture ([#1562](https://github.com/feathersjs/feathers/issues/1562)) ([42c13e2](https://github.com/feathersjs/feathers/commit/42c13e2)) - - - - +- check for undefined access token ([#1571](https://github.com/feathersjs/feathers/issues/1571)) ([976369d](https://github.com/feathersjs/feathers/commit/976369d)) +- Small improvements in dependencies and code sturcture ([#1562](https://github.com/feathersjs/feathers/issues/1562)) ([42c13e2](https://github.com/feathersjs/feathers/commit/42c13e2)) ## [4.3.2](https://github.com/feathersjs/feathers/compare/v4.3.1...v4.3.2) (2019-09-16) **Note:** Version bump only for package @feathersjs/authentication - - - - ## [4.3.1](https://github.com/feathersjs/feathers/compare/v4.3.0...v4.3.1) (2019-09-09) - ### Bug Fixes -* Use long-timeout for JWT expiration timers ([#1552](https://github.com/feathersjs/feathers/issues/1552)) ([65637ec](https://github.com/feathersjs/feathers/commit/65637ec)) - - - - +- Use long-timeout for JWT expiration timers ([#1552](https://github.com/feathersjs/feathers/issues/1552)) ([65637ec](https://github.com/feathersjs/feathers/commit/65637ec)) # [4.3.0](https://github.com/feathersjs/feathers/compare/v4.3.0-pre.4...v4.3.0) (2019-08-27) **Note:** Version bump only for package @feathersjs/authentication - - - - # [4.3.0-pre.4](https://github.com/feathersjs/feathers/compare/v4.3.0-pre.3...v4.3.0-pre.4) (2019-08-22) - ### Bug Fixes -* Fix auth publisher mistake ([08bad61](https://github.com/feathersjs/feathers/commit/08bad61)) - - - - +- Fix auth publisher mistake ([08bad61](https://github.com/feathersjs/feathers/commit/08bad61)) # [4.3.0-pre.3](https://github.com/feathersjs/feathers/compare/v4.3.0-pre.2...v4.3.0-pre.3) (2019-08-19) - ### Bug Fixes -* Expire and remove authenticated real-time connections ([#1512](https://github.com/feathersjs/feathers/issues/1512)) ([2707c33](https://github.com/feathersjs/feathers/commit/2707c33)) -* Update all dependencies ([7d53a00](https://github.com/feathersjs/feathers/commit/7d53a00)) - +- Expire and remove authenticated real-time connections ([#1512](https://github.com/feathersjs/feathers/issues/1512)) ([2707c33](https://github.com/feathersjs/feathers/commit/2707c33)) +- Update all dependencies ([7d53a00](https://github.com/feathersjs/feathers/commit/7d53a00)) ### Features -* Let strategies handle the connection ([#1510](https://github.com/feathersjs/feathers/issues/1510)) ([4329feb](https://github.com/feathersjs/feathers/commit/4329feb)) - - - - +- Let strategies handle the connection ([#1510](https://github.com/feathersjs/feathers/issues/1510)) ([4329feb](https://github.com/feathersjs/feathers/commit/4329feb)) # [4.3.0-pre.2](https://github.com/feathersjs/feathers/compare/v4.3.0-pre.1...v4.3.0-pre.2) (2019-08-02) - ### Bug Fixes -* Add getEntityId to JWT strategy and fix legacy Socket authentication ([#1488](https://github.com/feathersjs/feathers/issues/1488)) ([9a3b324](https://github.com/feathersjs/feathers/commit/9a3b324)) -* Add method to reliably get default authentication service ([#1470](https://github.com/feathersjs/feathers/issues/1470)) ([e542cb3](https://github.com/feathersjs/feathers/commit/e542cb3)) - - - - +- Add getEntityId to JWT strategy and fix legacy Socket authentication ([#1488](https://github.com/feathersjs/feathers/issues/1488)) ([9a3b324](https://github.com/feathersjs/feathers/commit/9a3b324)) +- Add method to reliably get default authentication service ([#1470](https://github.com/feathersjs/feathers/issues/1470)) ([e542cb3](https://github.com/feathersjs/feathers/commit/e542cb3)) # [4.3.0-pre.1](https://github.com/feathersjs/feathers/compare/v4.0.0-pre.5...v4.3.0-pre.1) (2019-07-11) **Note:** Version bump only for package @feathersjs/authentication - - - - # [4.0.0-pre.5](https://github.com/feathersjs/feathers/compare/v4.0.0-pre.4...v4.0.0-pre.5) (2019-07-10) **Note:** Version bump only for package @feathersjs/authentication - - - - # [4.0.0-pre.4](https://github.com/feathersjs/feathers/compare/v4.0.0-pre.3...v4.0.0-pre.4) (2019-07-05) - ### Bug Fixes -* Updated typings for ServiceMethods ([#1409](https://github.com/feathersjs/feathers/issues/1409)) ([b5ee7e2](https://github.com/feathersjs/feathers/commit/b5ee7e2)) - - - - +- Updated typings for ServiceMethods ([#1409](https://github.com/feathersjs/feathers/issues/1409)) ([b5ee7e2](https://github.com/feathersjs/feathers/commit/b5ee7e2)) # [4.0.0-pre.3](https://github.com/feathersjs/feathers/compare/v4.0.0-pre.2...v4.0.0-pre.3) (2019-06-01) - ### Bug Fixes -* Make oAuth paths more consistent and improve authentication client ([#1377](https://github.com/feathersjs/feathers/issues/1377)) ([adb2543](https://github.com/feathersjs/feathers/commit/adb2543)) -* Set authenticated: true after successful authentication ([#1367](https://github.com/feathersjs/feathers/issues/1367)) ([9918cff](https://github.com/feathersjs/feathers/commit/9918cff)) -* Typings fix and improvements. ([#1364](https://github.com/feathersjs/feathers/issues/1364)) ([515b916](https://github.com/feathersjs/feathers/commit/515b916)) -* Update dependencies and fix tests ([#1373](https://github.com/feathersjs/feathers/issues/1373)) ([d743a7f](https://github.com/feathersjs/feathers/commit/d743a7f)) - - - - +- Make oAuth paths more consistent and improve authentication client ([#1377](https://github.com/feathersjs/feathers/issues/1377)) ([adb2543](https://github.com/feathersjs/feathers/commit/adb2543)) +- Set authenticated: true after successful authentication ([#1367](https://github.com/feathersjs/feathers/issues/1367)) ([9918cff](https://github.com/feathersjs/feathers/commit/9918cff)) +- Typings fix and improvements. ([#1364](https://github.com/feathersjs/feathers/issues/1364)) ([515b916](https://github.com/feathersjs/feathers/commit/515b916)) +- Update dependencies and fix tests ([#1373](https://github.com/feathersjs/feathers/issues/1373)) ([d743a7f](https://github.com/feathersjs/feathers/commit/d743a7f)) # [4.0.0-pre.2](https://github.com/feathersjs/feathers/compare/v4.0.0-pre.1...v4.0.0-pre.2) (2019-05-15) - ### Bug Fixes -* Throw NotAuthenticated on token verification errors ([#1357](https://github.com/feathersjs/feathers/issues/1357)) ([e0120df](https://github.com/feathersjs/feathers/commit/e0120df)) - - - - +- Throw NotAuthenticated on token verification errors ([#1357](https://github.com/feathersjs/feathers/issues/1357)) ([e0120df](https://github.com/feathersjs/feathers/commit/e0120df)) # [4.0.0-pre.1](https://github.com/feathersjs/feathers/compare/v4.0.0-pre.0...v4.0.0-pre.1) (2019-05-08) - ### Bug Fixes -* Always require strategy parameter in authentication ([#1327](https://github.com/feathersjs/feathers/issues/1327)) ([d4a8021](https://github.com/feathersjs/feathers/commit/d4a8021)) -* Bring back params.authenticated ([#1317](https://github.com/feathersjs/feathers/issues/1317)) ([a0ffd5e](https://github.com/feathersjs/feathers/commit/a0ffd5e)) -* Improve authentication parameter handling ([#1333](https://github.com/feathersjs/feathers/issues/1333)) ([6e77204](https://github.com/feathersjs/feathers/commit/6e77204)) -* Merge httpStrategies and authStrategies option ([#1308](https://github.com/feathersjs/feathers/issues/1308)) ([afa4d55](https://github.com/feathersjs/feathers/commit/afa4d55)) -* Rename jwtStrategies option to authStrategies ([#1305](https://github.com/feathersjs/feathers/issues/1305)) ([4aee151](https://github.com/feathersjs/feathers/commit/4aee151)) - +- Always require strategy parameter in authentication ([#1327](https://github.com/feathersjs/feathers/issues/1327)) ([d4a8021](https://github.com/feathersjs/feathers/commit/d4a8021)) +- Bring back params.authenticated ([#1317](https://github.com/feathersjs/feathers/issues/1317)) ([a0ffd5e](https://github.com/feathersjs/feathers/commit/a0ffd5e)) +- Improve authentication parameter handling ([#1333](https://github.com/feathersjs/feathers/issues/1333)) ([6e77204](https://github.com/feathersjs/feathers/commit/6e77204)) +- Merge httpStrategies and authStrategies option ([#1308](https://github.com/feathersjs/feathers/issues/1308)) ([afa4d55](https://github.com/feathersjs/feathers/commit/afa4d55)) +- Rename jwtStrategies option to authStrategies ([#1305](https://github.com/feathersjs/feathers/issues/1305)) ([4aee151](https://github.com/feathersjs/feathers/commit/4aee151)) ### Features -* Change and *JWT methods to *accessToken ([#1304](https://github.com/feathersjs/feathers/issues/1304)) ([5ac826b](https://github.com/feathersjs/feathers/commit/5ac826b)) - - - - +- Change and *JWT methods to *accessToken ([#1304](https://github.com/feathersjs/feathers/issues/1304)) ([5ac826b](https://github.com/feathersjs/feathers/commit/5ac826b)) # [4.0.0-pre.0](https://github.com/feathersjs/feathers/compare/v3.2.0-pre.1...v4.0.0-pre.0) (2019-04-21) - ### Bug Fixes -* Added path and method in to express request for passport ([#1112](https://github.com/feathersjs/feathers/issues/1112)) ([afa1cb4](https://github.com/feathersjs/feathers/commit/afa1cb4)) -* Authentication core improvements ([#1260](https://github.com/feathersjs/feathers/issues/1260)) ([c5dc7a2](https://github.com/feathersjs/feathers/commit/c5dc7a2)) -* Improve JWT authentication option handling ([#1261](https://github.com/feathersjs/feathers/issues/1261)) ([31b956b](https://github.com/feathersjs/feathers/commit/31b956b)) -* Make Mocha a proper devDependency for every repository ([#1053](https://github.com/feathersjs/feathers/issues/1053)) ([9974803](https://github.com/feathersjs/feathers/commit/9974803)) -* Only merge authenticated property on update ([8a564f7](https://github.com/feathersjs/feathers/commit/8a564f7)) -* reduce authentication connection hook complexity and remove unnecessary checks ([fa94b2f](https://github.com/feathersjs/feathers/commit/fa94b2f)) -* Update all dependencies to latest ([#1206](https://github.com/feathersjs/feathers/issues/1206)) ([e51e0f6](https://github.com/feathersjs/feathers/commit/e51e0f6)) -* **authentication:** Fall back when req.app is not the application when emitting events ([#1185](https://github.com/feathersjs/feathers/issues/1185)) ([6a534f0](https://github.com/feathersjs/feathers/commit/6a534f0)) -* Update adapter common tests ([#1135](https://github.com/feathersjs/feathers/issues/1135)) ([8166dda](https://github.com/feathersjs/feathers/commit/8166dda)) -* **docs/new-features:** syntax highlighting ([#347](https://github.com/feathersjs/feathers/issues/347)) ([4ab7c95](https://github.com/feathersjs/feathers/commit/4ab7c95)) -* **package:** update @feathersjs/commons to version 2.0.0 ([#692](https://github.com/feathersjs/feathers/issues/692)) ([ca665ab](https://github.com/feathersjs/feathers/commit/ca665ab)) -* **package:** update debug to version 3.0.0 ([#555](https://github.com/feathersjs/feathers/issues/555)) ([f788804](https://github.com/feathersjs/feathers/commit/f788804)) -* **package:** update jsonwebtoken to version 8.0.0 ([#567](https://github.com/feathersjs/feathers/issues/567)) ([6811626](https://github.com/feathersjs/feathers/commit/6811626)) -* **package:** update ms to version 2.0.0 ([#509](https://github.com/feathersjs/feathers/issues/509)) ([7e4b0b6](https://github.com/feathersjs/feathers/commit/7e4b0b6)) -* **package:** update passport to version 0.4.0 ([#558](https://github.com/feathersjs/feathers/issues/558)) ([dcb14a5](https://github.com/feathersjs/feathers/commit/dcb14a5)) - +- Added path and method in to express request for passport ([#1112](https://github.com/feathersjs/feathers/issues/1112)) ([afa1cb4](https://github.com/feathersjs/feathers/commit/afa1cb4)) +- Authentication core improvements ([#1260](https://github.com/feathersjs/feathers/issues/1260)) ([c5dc7a2](https://github.com/feathersjs/feathers/commit/c5dc7a2)) +- Improve JWT authentication option handling ([#1261](https://github.com/feathersjs/feathers/issues/1261)) ([31b956b](https://github.com/feathersjs/feathers/commit/31b956b)) +- Make Mocha a proper devDependency for every repository ([#1053](https://github.com/feathersjs/feathers/issues/1053)) ([9974803](https://github.com/feathersjs/feathers/commit/9974803)) +- Only merge authenticated property on update ([8a564f7](https://github.com/feathersjs/feathers/commit/8a564f7)) +- reduce authentication connection hook complexity and remove unnecessary checks ([fa94b2f](https://github.com/feathersjs/feathers/commit/fa94b2f)) +- Update all dependencies to latest ([#1206](https://github.com/feathersjs/feathers/issues/1206)) ([e51e0f6](https://github.com/feathersjs/feathers/commit/e51e0f6)) +- **authentication:** Fall back when req.app is not the application when emitting events ([#1185](https://github.com/feathersjs/feathers/issues/1185)) ([6a534f0](https://github.com/feathersjs/feathers/commit/6a534f0)) +- Update adapter common tests ([#1135](https://github.com/feathersjs/feathers/issues/1135)) ([8166dda](https://github.com/feathersjs/feathers/commit/8166dda)) +- **docs/new-features:** syntax highlighting ([#347](https://github.com/feathersjs/feathers/issues/347)) ([4ab7c95](https://github.com/feathersjs/feathers/commit/4ab7c95)) +- **package:** update @feathersjs/commons to version 2.0.0 ([#692](https://github.com/feathersjs/feathers/issues/692)) ([ca665ab](https://github.com/feathersjs/feathers/commit/ca665ab)) +- **package:** update debug to version 3.0.0 ([#555](https://github.com/feathersjs/feathers/issues/555)) ([f788804](https://github.com/feathersjs/feathers/commit/f788804)) +- **package:** update jsonwebtoken to version 8.0.0 ([#567](https://github.com/feathersjs/feathers/issues/567)) ([6811626](https://github.com/feathersjs/feathers/commit/6811626)) +- **package:** update ms to version 2.0.0 ([#509](https://github.com/feathersjs/feathers/issues/509)) ([7e4b0b6](https://github.com/feathersjs/feathers/commit/7e4b0b6)) +- **package:** update passport to version 0.4.0 ([#558](https://github.com/feathersjs/feathers/issues/558)) ([dcb14a5](https://github.com/feathersjs/feathers/commit/dcb14a5)) ### Features -* @feathersjs/authentication-oauth ([#1299](https://github.com/feathersjs/feathers/issues/1299)) ([656bae7](https://github.com/feathersjs/feathers/commit/656bae7)) -* Add AuthenticationBaseStrategy and make authentication option handling more explicit ([#1284](https://github.com/feathersjs/feathers/issues/1284)) ([2667d92](https://github.com/feathersjs/feathers/commit/2667d92)) -* Add TypeScript definitions ([#1275](https://github.com/feathersjs/feathers/issues/1275)) ([9dd6713](https://github.com/feathersjs/feathers/commit/9dd6713)) -* Authentication v3 core server implementation ([#1205](https://github.com/feathersjs/feathers/issues/1205)) ([1bd7591](https://github.com/feathersjs/feathers/commit/1bd7591)) -* Authentication v3 local authentication ([#1211](https://github.com/feathersjs/feathers/issues/1211)) ([0fa5f7c](https://github.com/feathersjs/feathers/commit/0fa5f7c)) -* Remove (hook, next) signature and SKIP support ([#1269](https://github.com/feathersjs/feathers/issues/1269)) ([211c0f8](https://github.com/feathersjs/feathers/commit/211c0f8)) -* Support params symbol to skip authenticate hook ([#1296](https://github.com/feathersjs/feathers/issues/1296)) ([d16cf4d](https://github.com/feathersjs/feathers/commit/d16cf4d)) - +- @feathersjs/authentication-oauth ([#1299](https://github.com/feathersjs/feathers/issues/1299)) ([656bae7](https://github.com/feathersjs/feathers/commit/656bae7)) +- Add AuthenticationBaseStrategy and make authentication option handling more explicit ([#1284](https://github.com/feathersjs/feathers/issues/1284)) ([2667d92](https://github.com/feathersjs/feathers/commit/2667d92)) +- Add TypeScript definitions ([#1275](https://github.com/feathersjs/feathers/issues/1275)) ([9dd6713](https://github.com/feathersjs/feathers/commit/9dd6713)) +- Authentication v3 core server implementation ([#1205](https://github.com/feathersjs/feathers/issues/1205)) ([1bd7591](https://github.com/feathersjs/feathers/commit/1bd7591)) +- Authentication v3 local authentication ([#1211](https://github.com/feathersjs/feathers/issues/1211)) ([0fa5f7c](https://github.com/feathersjs/feathers/commit/0fa5f7c)) +- Remove (hook, next) signature and SKIP support ([#1269](https://github.com/feathersjs/feathers/issues/1269)) ([211c0f8](https://github.com/feathersjs/feathers/commit/211c0f8)) +- Support params symbol to skip authenticate hook ([#1296](https://github.com/feathersjs/feathers/issues/1296)) ([d16cf4d](https://github.com/feathersjs/feathers/commit/d16cf4d)) ### BREAKING CHANGES -* Update authentication strategies for @feathersjs/authentication v3 - - - - +- Update authentication strategies for @feathersjs/authentication v3 ## [2.1.16](https://github.com/feathersjs/feathers/compare/@feathersjs/authentication@2.1.15...@feathersjs/authentication@2.1.16) (2019-01-26) - ### Bug Fixes -* **authentication:** Fall back when req.app is not the application when emitting events ([#1185](https://github.com/feathersjs/feathers/issues/1185)) ([6a534f0](https://github.com/feathersjs/feathers/commit/6a534f0)) - - - - +- **authentication:** Fall back when req.app is not the application when emitting events ([#1185](https://github.com/feathersjs/feathers/issues/1185)) ([6a534f0](https://github.com/feathersjs/feathers/commit/6a534f0)) ## [2.1.15](https://github.com/feathersjs/feathers/compare/@feathersjs/authentication@2.1.14...@feathersjs/authentication@2.1.15) (2019-01-02) - ### Bug Fixes -* Update adapter common tests ([#1135](https://github.com/feathersjs/feathers/issues/1135)) ([8166dda](https://github.com/feathersjs/feathers/commit/8166dda)) - - - - +- Update adapter common tests ([#1135](https://github.com/feathersjs/feathers/issues/1135)) ([8166dda](https://github.com/feathersjs/feathers/commit/8166dda)) -## [2.1.14](https://github.com/feathersjs/feathers/compare/@feathersjs/authentication@2.1.13...@feathersjs/authentication@2.1.14) (2018-12-16) +## [2.1.14](https://github.com/feathersjs/feathers/compare/@feathersjs/authentication@2.1.13...@feathersjs/authentication@2.1.14) (2018-12-16) ### Bug Fixes -* Added path and method in to express request for passport ([#1112](https://github.com/feathersjs/feathers/issues/1112)) ([afa1cb4](https://github.com/feathersjs/feathers/commit/afa1cb4)) - - - - +- Added path and method in to express request for passport ([#1112](https://github.com/feathersjs/feathers/issues/1112)) ([afa1cb4](https://github.com/feathersjs/feathers/commit/afa1cb4)) + ## [2.1.13](https://github.com/feathersjs/feathers/compare/@feathersjs/authentication@2.1.12...@feathersjs/authentication@2.1.13) (2018-10-26) **Note:** Version bump only for package @feathersjs/authentication - - - - -## [2.1.12](https://github.com/feathersjs/feathers/compare/@feathersjs/authentication@2.1.11...@feathersjs/authentication@2.1.12) (2018-10-25) +## [2.1.12](https://github.com/feathersjs/feathers/compare/@feathersjs/authentication@2.1.11...@feathersjs/authentication@2.1.12) (2018-10-25) ### Bug Fixes -* Make Mocha a proper devDependency for every repository ([#1053](https://github.com/feathersjs/feathers/issues/1053)) ([9974803](https://github.com/feathersjs/feathers/commit/9974803)) -* Only merge authenticated property on update ([8a564f7](https://github.com/feathersjs/feathers/commit/8a564f7)) - - - - +- Make Mocha a proper devDependency for every repository ([#1053](https://github.com/feathersjs/feathers/issues/1053)) ([9974803](https://github.com/feathersjs/feathers/commit/9974803)) +- Only merge authenticated property on update ([8a564f7](https://github.com/feathersjs/feathers/commit/8a564f7)) + ## [2.1.11](https://github.com/feathersjs/feathers/compare/@feathersjs/authentication@2.1.10...@feathersjs/authentication@2.1.11) (2018-09-21) **Note:** Version bump only for package @feathersjs/authentication - - - - + ## [2.1.10](https://github.com/feathersjs/feathers/compare/@feathersjs/authentication@2.1.9...@feathersjs/authentication@2.1.10) (2018-09-17) **Note:** Version bump only for package @feathersjs/authentication - - - - + ## [2.1.9](https://github.com/feathersjs/feathers/compare/@feathersjs/authentication@2.1.8...@feathersjs/authentication@2.1.9) (2018-09-02) **Note:** Version bump only for package @feathersjs/authentication + ## 2.1.8 - Migrate to Monorepo ([feathers#462](https://github.com/feathersjs/feathers/issues/462)) ## [v2.1.7](https://github.com/feathersjs/authentication/tree/v2.1.7) (2018-06-29) + [Full Changelog](https://github.com/feathersjs/authentication/compare/v2.1.6...v2.1.7) **Fixed bugs:** @@ -682,6 +492,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Update sinon to the latest version 🚀 [\#681](https://github.com/feathersjs/authentication/pull/681) ([greenkeeper[bot]](https://github.com/apps/greenkeeper)) ## [v2.1.6](https://github.com/feathersjs/authentication/tree/v2.1.6) (2018-06-01) + [Full Changelog](https://github.com/feathersjs/authentication/compare/v2.1.5...v2.1.6) **Closed issues:** @@ -703,6 +514,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - add option to allowUnauthenticated [\#599](https://github.com/feathersjs/authentication/pull/599) ([MichaelErmer](https://github.com/MichaelErmer)) ## [v2.1.5](https://github.com/feathersjs/authentication/tree/v2.1.5) (2018-04-16) + [Full Changelog](https://github.com/feathersjs/authentication/compare/v2.1.4...v2.1.5) **Closed issues:** @@ -715,6 +527,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Remove payload and user entity on logout. [\#665](https://github.com/feathersjs/authentication/pull/665) ([bertho-zero](https://github.com/bertho-zero)) ## [v2.1.4](https://github.com/feathersjs/authentication/tree/v2.1.4) (2018-04-12) + [Full Changelog](https://github.com/feathersjs/authentication/compare/v2.1.3...v2.1.4) **Closed issues:** @@ -731,6 +544,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Update sinon to the latest version 🚀 [\#656](https://github.com/feathersjs/authentication/pull/656) ([greenkeeper[bot]](https://github.com/apps/greenkeeper)) ## [v2.1.3](https://github.com/feathersjs/authentication/tree/v2.1.3) (2018-03-16) + [Full Changelog](https://github.com/feathersjs/authentication/compare/v2.1.2...v2.1.3) **Closed issues:** @@ -750,6 +564,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Update sinon-chai to the latest version 🚀 [\#644](https://github.com/feathersjs/authentication/pull/644) ([greenkeeper[bot]](https://github.com/apps/greenkeeper)) ## [v2.1.2](https://github.com/feathersjs/authentication/tree/v2.1.2) (2018-02-14) + [Full Changelog](https://github.com/feathersjs/authentication/compare/v2.1.1...v2.1.2) **Fixed bugs:** @@ -766,7 +581,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - cookie reused from server in SSR app [\#619](https://github.com/feathersjs/authentication/issues/619) - Express middleware not setCookie [\#617](https://github.com/feathersjs/authentication/issues/617) - Server to Server Authentication Question [\#612](https://github.com/feathersjs/authentication/issues/612) -- No way to share token between socket-rest-express [\#607](https://github.com/feathersjs/authentication/issues/607) +- No way to share token between socket-rest-express [\#607](https://github.com/feathersjs/authentication/issues/607) - 404 when accessing route using customer authentication [\#579](https://github.com/feathersjs/authentication/issues/579) - \[question\] is it possible to protect by role a create method? [\#564](https://github.com/feathersjs/authentication/issues/564) - Authentication with server-side rendering [\#560](https://github.com/feathersjs/authentication/issues/560) @@ -783,6 +598,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Options merged [\#611](https://github.com/feathersjs/authentication/pull/611) ([Makingweb](https://github.com/Makingweb)) ## [v2.1.1](https://github.com/feathersjs/authentication/tree/v2.1.1) (2018-01-03) + [Full Changelog](https://github.com/feathersjs/authentication/compare/v2.1.0...v2.1.1) **Closed issues:** @@ -798,6 +614,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Update mongodb to the latest version 🚀 [\#618](https://github.com/feathersjs/authentication/pull/618) ([greenkeeper[bot]](https://github.com/apps/greenkeeper)) ## [v2.1.0](https://github.com/feathersjs/authentication/tree/v2.1.0) (2017-12-06) + [Full Changelog](https://github.com/feathersjs/authentication/compare/v2.0.1...v2.1.0) **Closed issues:** @@ -811,6 +628,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Update feathers-memory to the latest version 🚀 [\#613](https://github.com/feathersjs/authentication/pull/613) ([greenkeeper[bot]](https://github.com/apps/greenkeeper)) ## [v2.0.1](https://github.com/feathersjs/authentication/tree/v2.0.1) (2017-11-16) + [Full Changelog](https://github.com/feathersjs/authentication/compare/v2.0.0...v2.0.1) **Merged pull requests:** @@ -818,6 +636,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Add default export for better ES module \(TypeScript\) compatibility [\#605](https://github.com/feathersjs/authentication/pull/605) ([daffl](https://github.com/daffl)) ## [v2.0.0](https://github.com/feathersjs/authentication/tree/v2.0.0) (2017-11-09) + [Full Changelog](https://github.com/feathersjs/authentication/compare/v1.3.1...v2.0.0) **Closed issues:** @@ -830,6 +649,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Update nsp to the latest version 🚀 [\#603](https://github.com/feathersjs/authentication/pull/603) ([greenkeeper[bot]](https://github.com/apps/greenkeeper)) ## [v1.3.1](https://github.com/feathersjs/authentication/tree/v1.3.1) (2017-11-03) + [Full Changelog](https://github.com/feathersjs/authentication/compare/v1.4.1...v1.3.1) **Merged pull requests:** @@ -837,6 +657,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Only set the JWT UUID if it is not already set [\#600](https://github.com/feathersjs/authentication/pull/600) ([daffl](https://github.com/daffl)) ## [v1.4.1](https://github.com/feathersjs/authentication/tree/v1.4.1) (2017-11-01) + [Full Changelog](https://github.com/feathersjs/authentication/compare/v1.4.0...v1.4.1) **Merged pull requests:** @@ -846,6 +667,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Update Codeclimate coverage token [\#595](https://github.com/feathersjs/authentication/pull/595) ([daffl](https://github.com/daffl)) ## [v1.4.0](https://github.com/feathersjs/authentication/tree/v1.4.0) (2017-10-25) + [Full Changelog](https://github.com/feathersjs/authentication/compare/v1.3.0...v1.4.0) **Closed issues:** @@ -860,6 +682,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Update to new plugin infrastructure [\#591](https://github.com/feathersjs/authentication/pull/591) ([daffl](https://github.com/daffl)) ## [v1.3.0](https://github.com/feathersjs/authentication/tree/v1.3.0) (2017-10-24) + [Full Changelog](https://github.com/feathersjs/authentication/compare/v0.7.13...v1.3.0) **Merged pull requests:** @@ -867,12 +690,13 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - updating the codeclimate setup [\#589](https://github.com/feathersjs/authentication/pull/589) ([ekryski](https://github.com/ekryski)) ## [v0.7.13](https://github.com/feathersjs/authentication/tree/v0.7.13) (2017-10-23) + [Full Changelog](https://github.com/feathersjs/authentication/compare/v1.2.7...v0.7.13) **Closed issues:** - Error authenticating! Error: Token provided to verifyJWT is missing or not a string ? [\#584](https://github.com/feathersjs/authentication/issues/584) -- Visual Studio Code Debug no authentication [\#583](https://github.com/feathersjs/authentication/issues/583) +- Visual Studio Code Debug no authentication [\#583](https://github.com/feathersjs/authentication/issues/583) - \[Feature Request\] Cloud DB's [\#581](https://github.com/feathersjs/authentication/issues/581) - Request doesn't contain any headers when user service requested [\#578](https://github.com/feathersjs/authentication/issues/578) - No way to pass Options to auth.express.authenticate. Needed for Google API refreshToken [\#576](https://github.com/feathersjs/authentication/issues/576) @@ -913,13 +737,14 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Refresh token must have a user ID [\#419](https://github.com/feathersjs/authentication/pull/419) ([francisco-sanchez-molina](https://github.com/francisco-sanchez-molina)) ## [v1.2.7](https://github.com/feathersjs/authentication/tree/v1.2.7) (2017-07-11) + [Full Changelog](https://github.com/feathersjs/authentication/compare/v1.2.6...v1.2.7) **Closed issues:** - Connection without password [\#541](https://github.com/feathersjs/authentication/issues/541) - email in lower case ? [\#538](https://github.com/feathersjs/authentication/issues/538) -- Im unable to ping feathers server from react native. [\#537](https://github.com/feathersjs/authentication/issues/537) +- Im unable to ping feathers server from react native. [\#537](https://github.com/feathersjs/authentication/issues/537) - whats the official way to open cors in feather ? [\#536](https://github.com/feathersjs/authentication/issues/536) - Error options.service does not exist after initial auth setup [\#535](https://github.com/feathersjs/authentication/issues/535) - LogoutTimer not being cleared correctly [\#532](https://github.com/feathersjs/authentication/issues/532) @@ -930,6 +755,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - fixed meta undefined error [\#542](https://github.com/feathersjs/authentication/pull/542) ([markacola](https://github.com/markacola)) ## [v1.2.6](https://github.com/feathersjs/authentication/tree/v1.2.6) (2017-06-22) + [Full Changelog](https://github.com/feathersjs/authentication/compare/v1.2.5...v1.2.6) **Closed issues:** @@ -942,6 +768,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Update feathers-authentication-local to the latest version 🚀 [\#533](https://github.com/feathersjs/authentication/pull/533) ([greenkeeper[bot]](https://github.com/apps/greenkeeper)) ## [v1.2.5](https://github.com/feathersjs/authentication/tree/v1.2.5) (2017-06-21) + [Full Changelog](https://github.com/feathersjs/authentication/compare/v1.2.4...v1.2.5) **Closed issues:** @@ -955,6 +782,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - fixes several issues with update-entity w/ test cases [\#531](https://github.com/feathersjs/authentication/pull/531) ([jerfowler](https://github.com/jerfowler)) ## [v1.2.4](https://github.com/feathersjs/authentication/tree/v1.2.4) (2017-06-08) + [Full Changelog](https://github.com/feathersjs/authentication/compare/v1.2.3...v1.2.4) **Fixed bugs:** @@ -982,6 +810,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Fix default authentication config keys [\#506](https://github.com/feathersjs/authentication/pull/506) ([ekryski](https://github.com/ekryski)) ## [v1.2.3](https://github.com/feathersjs/authentication/tree/v1.2.3) (2017-05-10) + [Full Changelog](https://github.com/feathersjs/authentication/compare/v1.2.2...v1.2.3) **Closed issues:** @@ -1007,6 +836,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Update dependencies to enable Greenkeeper 🌴 [\#482](https://github.com/feathersjs/authentication/pull/482) ([greenkeeper[bot]](https://github.com/apps/greenkeeper)) ## [v1.2.2](https://github.com/feathersjs/authentication/tree/v1.2.2) (2017-04-12) + [Full Changelog](https://github.com/feathersjs/authentication/compare/v1.2.1...v1.2.2) **Fixed bugs:** @@ -1028,6 +858,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Resolves \#475 - Socket params are made available to authentication hooks [\#477](https://github.com/feathersjs/authentication/pull/477) ([thomas-p-wilson](https://github.com/thomas-p-wilson)) ## [v1.2.1](https://github.com/feathersjs/authentication/tree/v1.2.1) (2017-04-07) + [Full Changelog](https://github.com/feathersjs/authentication/compare/v1.2.0...v1.2.1) **Fixed bugs:** @@ -1051,6 +882,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Allow the cookie to be set if action is not `remove` [\#474](https://github.com/feathersjs/authentication/pull/474) ([marshallswain](https://github.com/marshallswain)) ## [v1.2.0](https://github.com/feathersjs/authentication/tree/v1.2.0) (2017-03-23) + [Full Changelog](https://github.com/feathersjs/authentication/compare/v1.1.1...v1.2.0) **Fixed bugs:** @@ -1063,7 +895,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Token creation has side effect [\#454](https://github.com/feathersjs/authentication/issues/454) - Question: When is userId set? [\#453](https://github.com/feathersjs/authentication/issues/453) -- How to authenticate SPA? More precisely how does the redirect works? [\#451](https://github.com/feathersjs/authentication/issues/451) +- How to authenticate SPA? More precisely how does the redirect works? [\#451](https://github.com/feathersjs/authentication/issues/451) - POST to auth/facebook for FacebookTokenStrategy 404? [\#447](https://github.com/feathersjs/authentication/issues/447) - feathers-authentication 1.1.1 `No auth token` [\#445](https://github.com/feathersjs/authentication/issues/445) - Another readme incorrect and maybe docs to [\#441](https://github.com/feathersjs/authentication/issues/441) @@ -1086,6 +918,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Add support for Bearer scheme in remove method [\#403](https://github.com/feathersjs/authentication/pull/403) ([boybundit](https://github.com/boybundit)) ## [v1.1.1](https://github.com/feathersjs/authentication/tree/v1.1.1) (2017-03-02) + [Full Changelog](https://github.com/feathersjs/authentication/compare/v1.1.0...v1.1.1) **Closed issues:** @@ -1097,6 +930,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Remove lots of hardcoded values for config, and adds the `authenticate` hook [\#427](https://github.com/feathersjs/authentication/pull/427) ([myknbani](https://github.com/myknbani)) ## [v1.1.0](https://github.com/feathersjs/authentication/tree/v1.1.0) (2017-03-01) + [Full Changelog](https://github.com/feathersjs/authentication/compare/v1.0.2...v1.1.0) **Fixed bugs:** @@ -1125,10 +959,10 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - feathers-authentication errors with any view error, and redirects to /auth/failure [\#381](https://github.com/feathersjs/authentication/issues/381) - what does app.service\('authentication'\).remove\(...\) mean? [\#379](https://github.com/feathersjs/authentication/issues/379) - Rest Endpoints. [\#375](https://github.com/feathersjs/authentication/issues/375) -- cordova google-plus signUp with id\_token [\#373](https://github.com/feathersjs/authentication/issues/373) +- cordova google-plus signUp with id_token [\#373](https://github.com/feathersjs/authentication/issues/373) - How to reconnect socket with cookie after page refresh ? [\#372](https://github.com/feathersjs/authentication/issues/372) - Error: Could not find stored JWT and no authentication strategy was given [\#367](https://github.com/feathersjs/authentication/issues/367) -- "No auth token" using authenticate strategy: 'jwt' \(v.1.0.0-beta-2\) [\#366](https://github.com/feathersjs/authentication/issues/366) +- "No auth token" using authenticate strategy: 'jwt' \(v.1.0.0-beta-2\) [\#366](https://github.com/feathersjs/authentication/issues/366) - Navigating to /auth/\ twice redirects to /auth/failed [\#344](https://github.com/feathersjs/authentication/issues/344) - Meteor auth migration guide [\#334](https://github.com/feathersjs/authentication/issues/334) - Auth 1.0 [\#330](https://github.com/feathersjs/authentication/issues/330) @@ -1156,6 +990,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Docs: Equalize usage of feathers-authenticate [\#378](https://github.com/feathersjs/authentication/pull/378) ([eikaramba](https://github.com/eikaramba)) ## [v1.0.2](https://github.com/feathersjs/authentication/tree/v1.0.2) (2016-12-14) + [Full Changelog](https://github.com/feathersjs/authentication/compare/v1.0.1...v1.0.2) **Closed issues:** @@ -1163,9 +998,11 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - successRedirect not redirecting [\#364](https://github.com/feathersjs/authentication/issues/364) ## [v1.0.1](https://github.com/feathersjs/authentication/tree/v1.0.1) (2016-12-14) + [Full Changelog](https://github.com/feathersjs/authentication/compare/v1.0.0...v1.0.1) ## [v1.0.0](https://github.com/feathersjs/authentication/tree/v1.0.0) (2016-12-14) + [Full Changelog](https://github.com/feathersjs/authentication/compare/v0.7.12...v1.0.0) **Fixed bugs:** @@ -1176,19 +1013,19 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - auth.express.authenticate got undefined [\#363](https://github.com/feathersjs/authentication/issues/363) - Non-standard header structure [\#361](https://github.com/feathersjs/authentication/issues/361) -- localEndpoint without local strategy [\#359](https://github.com/feathersjs/authentication/issues/359) +- localEndpoint without local strategy [\#359](https://github.com/feathersjs/authentication/issues/359) - Using custom passport strategies [\#356](https://github.com/feathersjs/authentication/issues/356) - Client-side app.on\('login'\) [\#355](https://github.com/feathersjs/authentication/issues/355) - Payload limiting on `app.get\('user'\)`? [\#354](https://github.com/feathersjs/authentication/issues/354) -- Authentication token is missing [\#352](https://github.com/feathersjs/authentication/issues/352) +- Authentication token is missing [\#352](https://github.com/feathersjs/authentication/issues/352) - \[1.0\] The entity on the socket should pull from the strategy options. [\#348](https://github.com/feathersjs/authentication/issues/348) - \[1.0\] Only the first failure is returned on auth failure when chaining multiple strategies [\#346](https://github.com/feathersjs/authentication/issues/346) - Build 0.7.11 does not contain current code on NPMJS [\#342](https://github.com/feathersjs/authentication/issues/342) -- feathers-authentication branch 0.8 did not work with payload \(tested on socket\) [\#264](https://github.com/feathersjs/authentication/issues/264) +- feathers-authentication branch 0.8 did not work with payload \(tested on socket\) [\#264](https://github.com/feathersjs/authentication/issues/264) - Add method for updating JWT [\#260](https://github.com/feathersjs/authentication/issues/260) - 1.0 architecture considerations [\#226](https://github.com/feathersjs/authentication/issues/226) - Features/RFC [\#213](https://github.com/feathersjs/authentication/issues/213) -- Support access\_token based OAuth2 providers [\#169](https://github.com/feathersjs/authentication/issues/169) +- Support access_token based OAuth2 providers [\#169](https://github.com/feathersjs/authentication/issues/169) - Support openID [\#154](https://github.com/feathersjs/authentication/issues/154) - Disable cookie by default if not using OAuth [\#152](https://github.com/feathersjs/authentication/issues/152) - Add token service tests [\#144](https://github.com/feathersjs/authentication/issues/144) @@ -1219,6 +1056,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - 1.0 Pre-release [\#336](https://github.com/feathersjs/authentication/pull/336) ([ekryski](https://github.com/ekryski)) ## [v0.7.12](https://github.com/feathersjs/authentication/tree/v0.7.12) (2016-11-11) + [Full Changelog](https://github.com/feathersjs/authentication/compare/v0.7.11...v0.7.12) **Closed issues:** @@ -1266,6 +1104,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - 0.8 - OAuth fixes [\#304](https://github.com/feathersjs/authentication/pull/304) ([marshallswain](https://github.com/marshallswain)) ## [v0.7.11](https://github.com/feathersjs/authentication/tree/v0.7.11) (2016-09-28) + [Full Changelog](https://github.com/feathersjs/authentication/compare/v0.7.10...v0.7.11) **Closed issues:** @@ -1284,6 +1123,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Allow multiple username fields for local auth [\#283](https://github.com/feathersjs/authentication/pull/283) ([sdbondi](https://github.com/sdbondi)) ## [v0.7.10](https://github.com/feathersjs/authentication/tree/v0.7.10) (2016-08-31) + [Full Changelog](https://github.com/feathersjs/authentication/compare/v0.7.9...v0.7.10) **Fixed bugs:** @@ -1296,7 +1136,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Auth0 & featherjs authorization only [\#277](https://github.com/feathersjs/authentication/issues/277) - Cannot read property 'scope' of undefined [\#273](https://github.com/feathersjs/authentication/issues/273) - Socker.js | Custom successHandler [\#271](https://github.com/feathersjs/authentication/issues/271) -- Use feathers-socketio? and rest&socket share session maybe? [\#269](https://github.com/feathersjs/authentication/issues/269) +- Use feathers-socketio? and rest&socket share session maybe? [\#269](https://github.com/feathersjs/authentication/issues/269) - Ability to invalidate old token/session when user login with another machine. [\#267](https://github.com/feathersjs/authentication/issues/267) - 0.8 authentication before hooks - only ever getting a 401 Unauthorised [\#263](https://github.com/feathersjs/authentication/issues/263) - REST Middleware breaks local auth [\#262](https://github.com/feathersjs/authentication/issues/262) @@ -1326,6 +1166,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Adds ability to limit queries unless authenticated and authorized [\#229](https://github.com/feathersjs/authentication/pull/229) ([codingfriend1](https://github.com/codingfriend1)) ## [v0.7.9](https://github.com/feathersjs/authentication/tree/v0.7.9) (2016-06-20) + [Full Changelog](https://github.com/feathersjs/authentication/compare/v0.7.8...v0.7.9) **Fixed bugs:** @@ -1343,6 +1184,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - jwt ssl warning [\#214](https://github.com/feathersjs/authentication/pull/214) ([aboutlo](https://github.com/aboutlo)) ## [v0.7.8](https://github.com/feathersjs/authentication/tree/v0.7.8) (2016-06-09) + [Full Changelog](https://github.com/feathersjs/authentication/compare/v0.7.7...v0.7.8) **Closed issues:** @@ -1367,6 +1209,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Update babel-plugin-add-module-exports to version 0.2.0 🚀 [\#199](https://github.com/feathersjs/authentication/pull/199) ([greenkeeperio-bot](https://github.com/greenkeeperio-bot)) ## [v0.7.7](https://github.com/feathersjs/authentication/tree/v0.7.7) (2016-05-05) + [Full Changelog](https://github.com/feathersjs/authentication/compare/v0.7.6...v0.7.7) **Fixed bugs:** @@ -1378,6 +1221,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - properly handle optional `\_json` property [\#197](https://github.com/feathersjs/authentication/pull/197) ([nyaaao](https://github.com/nyaaao)) ## [v0.7.6](https://github.com/feathersjs/authentication/tree/v0.7.6) (2016-05-03) + [Full Changelog](https://github.com/feathersjs/authentication/compare/v0.7.5...v0.7.6) **Fixed bugs:** @@ -1386,7 +1230,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline **Closed issues:** -- Authenticated user [\#192](https://github.com/feathersjs/authentication/issues/192) +- Authenticated user [\#192](https://github.com/feathersjs/authentication/issues/192) - REST token revoke [\#185](https://github.com/feathersjs/authentication/issues/185) - TypeError: Cannot read property 'service' of undefined [\#173](https://github.com/feathersjs/authentication/issues/173) - Optionally Include password in the params.query object passed to User.find\(\) [\#171](https://github.com/feathersjs/authentication/issues/171) @@ -1400,6 +1244,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - fix\(oauth2\): Use patch to update user in oauthCallback [\#183](https://github.com/feathersjs/authentication/pull/183) ([beevelop](https://github.com/beevelop)) ## [v0.7.5](https://github.com/feathersjs/authentication/tree/v0.7.5) (2016-04-23) + [Full Changelog](https://github.com/feathersjs/authentication/compare/v0.7.4...v0.7.5) **Fixed bugs:** @@ -1412,6 +1257,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Unable to authenticate requests when using vanilla Socket.IO [\#166](https://github.com/feathersjs/authentication/issues/166) ## [v0.7.4](https://github.com/feathersjs/authentication/tree/v0.7.4) (2016-04-18) + [Full Changelog](https://github.com/feathersjs/authentication/compare/v0.7.3...v0.7.4) **Fixed bugs:** @@ -1429,9 +1275,11 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Hook fixes [\#164](https://github.com/feathersjs/authentication/pull/164) ([ekryski](https://github.com/ekryski)) ## [v0.7.3](https://github.com/feathersjs/authentication/tree/v0.7.3) (2016-04-16) + [Full Changelog](https://github.com/feathersjs/authentication/compare/v0.7.2...v0.7.3) ## [v0.7.2](https://github.com/feathersjs/authentication/tree/v0.7.2) (2016-04-16) + [Full Changelog](https://github.com/feathersjs/authentication/compare/v0.7.1...v0.7.2) **Closed issues:** @@ -1447,6 +1295,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Steal Compatibility [\#156](https://github.com/feathersjs/authentication/pull/156) ([marshallswain](https://github.com/marshallswain)) ## [v0.7.1](https://github.com/feathersjs/authentication/tree/v0.7.1) (2016-04-08) + [Full Changelog](https://github.com/feathersjs/authentication/compare/v0.7.0...v0.7.1) **Closed issues:** @@ -1463,6 +1312,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Fix copy paste typo in queryWithCurrentUser hook. [\#140](https://github.com/feathersjs/authentication/pull/140) ([juodumas](https://github.com/juodumas)) ## [v0.7.0](https://github.com/feathersjs/authentication/tree/v0.7.0) (2016-03-30) + [Full Changelog](https://github.com/feathersjs/authentication/compare/v0.6.0...v0.7.0) **Fixed bugs:** @@ -1493,6 +1343,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - 0.7 Release [\#139](https://github.com/feathersjs/authentication/pull/139) ([ekryski](https://github.com/ekryski)) ## [v0.6.0](https://github.com/feathersjs/authentication/tree/v0.6.0) (2016-03-24) + [Full Changelog](https://github.com/feathersjs/authentication/compare/v0.5.1...v0.6.0) **Fixed bugs:** @@ -1513,15 +1364,17 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline **Merged pull requests:** - Bcryptjs [\#137](https://github.com/feathersjs/authentication/pull/137) ([ekryski](https://github.com/ekryski)) -- Allow user.id to be 0. Fixes \#116 [\#117](https://github.com/feathersjs/authentication/pull/117) ([marshallswain](https://github.com/marshallswain)) +- Allow user.id to be 0. Fixes \#116 [\#117](https://github.com/feathersjs/authentication/pull/117) ([marshallswain](https://github.com/marshallswain)) - client should return a 401 error code when no token is provided [\#115](https://github.com/feathersjs/authentication/pull/115) ([ccummings](https://github.com/ccummings)) - v0.6 - Bugs fixes, new hooks, and hook tests [\#109](https://github.com/feathersjs/authentication/pull/109) ([ekryski](https://github.com/ekryski)) - primus client connect event is 'open' [\#106](https://github.com/feathersjs/authentication/pull/106) ([ahdinosaur](https://github.com/ahdinosaur)) ## [v0.5.1](https://github.com/feathersjs/authentication/tree/v0.5.1) (2016-03-15) + [Full Changelog](https://github.com/feathersjs/authentication/compare/v0.5.0...v0.5.1) ## [v0.5.0](https://github.com/feathersjs/authentication/tree/v0.5.0) (2016-03-14) + [Full Changelog](https://github.com/feathersjs/authentication/compare/v0.4.1...v0.5.0) **Fixed bugs:** @@ -1547,6 +1400,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Customize the JWT payload [\#80](https://github.com/feathersjs/authentication/pull/80) ([enten](https://github.com/enten)) ## [v0.4.1](https://github.com/feathersjs/authentication/tree/v0.4.1) (2016-02-28) + [Full Changelog](https://github.com/feathersjs/authentication/compare/v0.4.0...v0.4.1) **Fixed bugs:** @@ -1556,13 +1410,14 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline **Closed issues:** - Username response ? [\#84](https://github.com/feathersjs/authentication/issues/84) -- User doesn't get populated after authentication with databases that don't use \_id [\#71](https://github.com/feathersjs/authentication/issues/71) +- User doesn't get populated after authentication with databases that don't use \_id [\#71](https://github.com/feathersjs/authentication/issues/71) - Support client usage in NodeJS [\#52](https://github.com/feathersjs/authentication/issues/52) - Support async storage for React Native [\#51](https://github.com/feathersjs/authentication/issues/51) - RequireAdmin on userService [\#36](https://github.com/feathersjs/authentication/issues/36) - Create test for changing the `usernameField` [\#1](https://github.com/feathersjs/authentication/issues/1) ## [v0.4.0](https://github.com/feathersjs/authentication/tree/v0.4.0) (2016-02-27) + [Full Changelog](https://github.com/feathersjs/authentication/compare/v0.3.5...v0.4.0) **Closed issues:** @@ -1574,6 +1429,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Refactoring for storage service [\#76](https://github.com/feathersjs/authentication/pull/76) ([ekryski](https://github.com/ekryski)) ## [v0.3.5](https://github.com/feathersjs/authentication/tree/v0.3.5) (2016-02-25) + [Full Changelog](https://github.com/feathersjs/authentication/compare/v0.3.4...v0.3.5) **Merged pull requests:** @@ -1581,12 +1437,15 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Adding support for OAuth2 token based auth strategies. Closes \#46. [\#77](https://github.com/feathersjs/authentication/pull/77) ([ekryski](https://github.com/ekryski)) ## [v0.3.4](https://github.com/feathersjs/authentication/tree/v0.3.4) (2016-02-25) + [Full Changelog](https://github.com/feathersjs/authentication/compare/v0.3.3...v0.3.4) ## [v0.3.3](https://github.com/feathersjs/authentication/tree/v0.3.3) (2016-02-25) + [Full Changelog](https://github.com/feathersjs/authentication/compare/v0.3.2...v0.3.3) ## [v0.3.2](https://github.com/feathersjs/authentication/tree/v0.3.2) (2016-02-24) + [Full Changelog](https://github.com/feathersjs/authentication/compare/v0.3.1...v0.3.2) **Merged pull requests:** @@ -1594,6 +1453,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - bumping feathers-errors version [\#79](https://github.com/feathersjs/authentication/pull/79) ([ekryski](https://github.com/ekryski)) ## [v0.3.1](https://github.com/feathersjs/authentication/tree/v0.3.1) (2016-02-23) + [Full Changelog](https://github.com/feathersjs/authentication/compare/v0.3.0...v0.3.1) **Closed issues:** @@ -1607,6 +1467,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Fix toLowerCase hook [\#75](https://github.com/feathersjs/authentication/pull/75) ([enten](https://github.com/enten)) ## [v0.3.0](https://github.com/feathersjs/authentication/tree/v0.3.0) (2016-02-19) + [Full Changelog](https://github.com/feathersjs/authentication/compare/v0.2.4...v0.3.0) **Fixed bugs:** @@ -1624,6 +1485,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Config options [\#70](https://github.com/feathersjs/authentication/pull/70) ([ekryski](https://github.com/ekryski)) ## [v0.2.4](https://github.com/feathersjs/authentication/tree/v0.2.4) (2016-02-17) + [Full Changelog](https://github.com/feathersjs/authentication/compare/v0.2.3...v0.2.4) **Closed issues:** @@ -1635,11 +1497,12 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Add module exports Babel module and test CommonJS compatibility [\#68](https://github.com/feathersjs/authentication/pull/68) ([daffl](https://github.com/daffl)) ## [v0.2.3](https://github.com/feathersjs/authentication/tree/v0.2.3) (2016-02-15) + [Full Changelog](https://github.com/feathersjs/authentication/compare/v0.2.2...v0.2.3) **Closed issues:** -- How to forbid get and find on the userEndpoint? [\#66](https://github.com/feathersjs/authentication/issues/66) +- How to forbid get and find on the userEndpoint? [\#66](https://github.com/feathersjs/authentication/issues/66) - userEndpoint problem in sub-app [\#63](https://github.com/feathersjs/authentication/issues/63) - How to modify successRedirect in local authentication? [\#60](https://github.com/feathersjs/authentication/issues/60) @@ -1649,6 +1512,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Fixing client query [\#65](https://github.com/feathersjs/authentication/pull/65) ([fastlorenzo](https://github.com/fastlorenzo)) ## [v0.2.2](https://github.com/feathersjs/authentication/tree/v0.2.2) (2016-02-13) + [Full Changelog](https://github.com/feathersjs/authentication/compare/v0.2.1...v0.2.2) **Closed issues:** @@ -1662,6 +1526,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Fixing token endpoint [\#58](https://github.com/feathersjs/authentication/pull/58) ([marshallswain](https://github.com/marshallswain)) ## [v0.2.1](https://github.com/feathersjs/authentication/tree/v0.2.1) (2016-02-12) + [Full Changelog](https://github.com/feathersjs/authentication/compare/v0.2.0...v0.2.1) **Closed issues:** @@ -1670,6 +1535,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - node can not require\("feathers-authentication"\).default [\#53](https://github.com/feathersjs/authentication/issues/53) ## [v0.2.0](https://github.com/feathersjs/authentication/tree/v0.2.0) (2016-02-12) + [Full Changelog](https://github.com/feathersjs/authentication/compare/v0.1.2...v0.2.0) **Closed issues:** @@ -1691,6 +1557,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Validate if provider [\#39](https://github.com/feathersjs/authentication/pull/39) ([mastertinner](https://github.com/mastertinner)) ## [v0.1.2](https://github.com/feathersjs/authentication/tree/v0.1.2) (2016-02-04) + [Full Changelog](https://github.com/feathersjs/authentication/compare/v0.1.1...v0.1.2) **Closed issues:** @@ -1704,9 +1571,11 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - safety check for data [\#35](https://github.com/feathersjs/authentication/pull/35) ([deanmcpherson](https://github.com/deanmcpherson)) ## [v0.1.1](https://github.com/feathersjs/authentication/tree/v0.1.1) (2016-01-30) + [Full Changelog](https://github.com/feathersjs/authentication/compare/v0.1.0...v0.1.1) ## [v0.1.0](https://github.com/feathersjs/authentication/tree/v0.1.0) (2016-01-25) + [Full Changelog](https://github.com/feathersjs/authentication/compare/v0.0.8...v0.1.0) **Closed issues:** @@ -1725,6 +1594,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Adding nsp check [\#26](https://github.com/feathersjs/authentication/pull/26) ([marshallswain](https://github.com/marshallswain)) ## [v0.0.8](https://github.com/feathersjs/authentication/tree/v0.0.8) (2016-01-16) + [Full Changelog](https://github.com/feathersjs/authentication/compare/v0.0.7...v0.0.8) **Merged pull requests:** @@ -1732,11 +1602,12 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Support services that use pagination. [\#23](https://github.com/feathersjs/authentication/pull/23) ([marshallswain](https://github.com/marshallswain)) ## [v0.0.7](https://github.com/feathersjs/authentication/tree/v0.0.7) (2016-01-07) + [Full Changelog](https://github.com/feathersjs/authentication/compare/v0.0.6...v0.0.7) **Closed issues:** -- Password isn't removed from responses when using a mongoose service for users endpoint [\#19](https://github.com/feathersjs/authentication/issues/19) +- Password isn't removed from responses when using a mongoose service for users endpoint [\#19](https://github.com/feathersjs/authentication/issues/19) - next called twice using socket.io and using an unauthenticated service [\#17](https://github.com/feathersjs/authentication/issues/17) - Switch to a callback-based field configuration? [\#15](https://github.com/feathersjs/authentication/issues/15) - Cannot authenticate [\#14](https://github.com/feathersjs/authentication/issues/14) @@ -1745,12 +1616,13 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline **Merged pull requests:** -- Adding separate route for refreshing a login token. [\#21](https://github.com/feathersjs/authentication/pull/21) ([corymsmith](https://github.com/corymsmith)) +- Adding separate route for refreshing a login token. [\#21](https://github.com/feathersjs/authentication/pull/21) ([corymsmith](https://github.com/corymsmith)) - Converting user model to object when using mongoose service [\#20](https://github.com/feathersjs/authentication/pull/20) ([corymsmith](https://github.com/corymsmith)) - Fixing issue where next is called twice when hitting an unauthenticated service via socket.io [\#18](https://github.com/feathersjs/authentication/pull/18) ([corymsmith](https://github.com/corymsmith)) - Fixing usage of mongoose service [\#16](https://github.com/feathersjs/authentication/pull/16) ([corymsmith](https://github.com/corymsmith)) ## [v0.0.6](https://github.com/feathersjs/authentication/tree/v0.0.6) (2015-11-22) + [Full Changelog](https://github.com/feathersjs/authentication/compare/v0.0.5...v0.0.6) **Closed issues:** @@ -1759,12 +1631,15 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Make sure we're returning proper error responses. [\#8](https://github.com/feathersjs/authentication/issues/8) ## [v0.0.5](https://github.com/feathersjs/authentication/tree/v0.0.5) (2015-11-19) + [Full Changelog](https://github.com/feathersjs/authentication/compare/v0.0.4...v0.0.5) ## [v0.0.4](https://github.com/feathersjs/authentication/tree/v0.0.4) (2015-11-19) + [Full Changelog](https://github.com/feathersjs/authentication/compare/v0.0.3...v0.0.4) ## [v0.0.3](https://github.com/feathersjs/authentication/tree/v0.0.3) (2015-11-18) + [Full Changelog](https://github.com/feathersjs/authentication/compare/v1.0.6...v0.0.3) **Merged pull requests:** @@ -1772,15 +1647,17 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - allow runtime auth via socket.io [\#4](https://github.com/feathersjs/authentication/pull/4) ([randomnerd](https://github.com/randomnerd)) ## [v1.0.6](https://github.com/feathersjs/authentication/tree/v1.0.6) (2015-11-02) + [Full Changelog](https://github.com/feathersjs/authentication/compare/v1.0.5...v1.0.6) ## [v1.0.5](https://github.com/feathersjs/authentication/tree/v1.0.5) (2015-11-02) + [Full Changelog](https://github.com/feathersjs/authentication/compare/v1.0.4...v1.0.5) ## [v1.0.4](https://github.com/feathersjs/authentication/tree/v1.0.4) (2015-11-02) + [Full Changelog](https://github.com/feathersjs/authentication/compare/v1.0.3...v1.0.4) ## [v1.0.3](https://github.com/feathersjs/authentication/tree/v1.0.3) (2015-10-12) - -\* *This Change Log was automatically generated by [github_changelog_generator](https://github.com/skywinder/Github-Changelog-Generator)* +\* _This Change Log was automatically generated by [github_changelog_generator](https://github.com/skywinder/Github-Changelog-Generator)_ diff --git a/packages/authentication/LICENSE b/packages/authentication/LICENSE index 3f395cc665..59604f46f3 100644 --- a/packages/authentication/LICENSE +++ b/packages/authentication/LICENSE @@ -1,6 +1,6 @@ The MIT License (MIT) -Copyright (c) 2021 Feathers +Copyright (c) 2022 Feathers Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated documentation files (the "Software"), to deal diff --git a/packages/authentication/README.md b/packages/authentication/README.md index e35f55d15a..cba2195a1d 100644 --- a/packages/authentication/README.md +++ b/packages/authentication/README.md @@ -1,8 +1,8 @@ # @feathersjs/authentication [![CI](https://github.com/feathersjs/feathers/workflows/CI/badge.svg)](https://github.com/feathersjs/feathers/actions?query=workflow%3ACI) -[![Dependency Status](https://img.shields.io/david/feathersjs/feathers.svg?style=flat-square&path=packages/authentication)](https://david-dm.org/feathersjs/feathers?path=packages/authentication) [![Download Status](https://img.shields.io/npm/dm/@feathersjs/authentication.svg?style=flat-square)](https://www.npmjs.com/package/@feathersjs/authentication) +[![Discord](https://badgen.net/badge/icon/discord?icon=discord&label)](https://discord.gg/qa8kez8QBx) > Add Authentication to your FeathersJS app. @@ -18,6 +18,6 @@ Refer to the [Feathers authentication API documentation](https://docs.feathersjs ## License -Copyright (c) 2021 [Feathers contributors](https://github.com/feathersjs/feathers/graphs/contributors) +Copyright (c) 2022 [Feathers contributors](https://github.com/feathersjs/feathers/graphs/contributors) Licensed under the [MIT license](LICENSE). diff --git a/packages/authentication/package.json b/packages/authentication/package.json index d6dea86db7..08d670764c 100644 --- a/packages/authentication/package.json +++ b/packages/authentication/package.json @@ -1,7 +1,7 @@ { "name": "@feathersjs/authentication", "description": "Add Authentication to your FeathersJS app.", - "version": "5.0.0-pre.16", + "version": "5.0.0-pre.31", "homepage": "https://feathersjs.com", "main": "lib/", "types": "lib/", @@ -16,7 +16,8 @@ }, "repository": { "type": "git", - "url": "git://github.com/feathersjs/feathers.git" + "url": "git://github.com/feathersjs/feathers.git", + "directory": "packages/authentication" }, "author": { "name": "Feathers contributors", @@ -41,9 +42,9 @@ }, "scripts": { "prepublish": "npm run compile", - "compile": "shx rm -rf lib/ && tsc", - "test": "npm run compile && npm run mocha", - "mocha": "mocha --config ../../.mocharc.json --recursive test/**.test.ts test/**/*.test.ts" + "pack": "npm pack --pack-destination ../cli/test/build", + "compile": "shx rm -rf lib/ && tsc && npm run pack", + "test": "mocha --config ../../.mocharc.json --recursive test/**.test.ts test/**/*.test.ts" }, "directories": { "lib": "lib" @@ -52,26 +53,28 @@ "access": "public" }, "dependencies": { - "@feathersjs/commons": "^5.0.0-pre.16", - "@feathersjs/errors": "^5.0.0-pre.16", - "@feathersjs/feathers": "^5.0.0-pre.16", - "@feathersjs/transport-commons": "^5.0.0-pre.16", - "@types/jsonwebtoken": "^8.5.6", + "@feathersjs/commons": "^5.0.0-pre.31", + "@feathersjs/errors": "^5.0.0-pre.31", + "@feathersjs/feathers": "^5.0.0-pre.31", + "@feathersjs/hooks": "^0.7.5", + "@feathersjs/schema": "^5.0.0-pre.31", + "@feathersjs/transport-commons": "^5.0.0-pre.31", + "@types/jsonwebtoken": "^8.5.9", "jsonwebtoken": "^8.5.1", "lodash": "^4.17.21", "long-timeout": "^0.1.1", - "uuid": "^8.3.2" + "uuid": "^9.0.0" }, "devDependencies": { - "@feathersjs/memory": "^5.0.0-pre.16", - "@types/lodash": "^4.14.178", - "@types/mocha": "^9.0.0", - "@types/node": "^17.0.5", - "@types/uuid": "^8.3.3", - "mocha": "^9.1.3", - "shx": "^0.3.3", - "ts-node": "^10.4.0", - "typescript": "^4.5.4" + "@feathersjs/memory": "^5.0.0-pre.31", + "@types/lodash": "^4.14.186", + "@types/mocha": "^10.0.0", + "@types/node": "^18.8.2", + "@types/uuid": "^8.3.4", + "mocha": "^10.0.0", + "shx": "^0.3.4", + "ts-node": "^10.9.1", + "typescript": "^4.8.4" }, - "gitHead": "f0cd227a82d159b528193bd33747c97684a48773" + "gitHead": "4500dbeb8cea566678cf88b3313a88efd93a2ed9" } diff --git a/packages/authentication/src/core.ts b/packages/authentication/src/core.ts index 0a6e7da740..623bc56d40 100644 --- a/packages/authentication/src/core.ts +++ b/packages/authentication/src/core.ts @@ -1,24 +1,32 @@ -import merge from 'lodash/merge'; -import jsonwebtoken, { SignOptions, Secret, VerifyOptions } from 'jsonwebtoken'; -import { v4 as uuidv4 } from 'uuid'; -import { NotAuthenticated } from '@feathersjs/errors'; -import { createDebug } from '@feathersjs/commons'; -import { Application, Params } from '@feathersjs/feathers'; -import { IncomingMessage, ServerResponse } from 'http'; -import defaultOptions from './options'; +import merge from 'lodash/merge' +import jsonwebtoken, { SignOptions, Secret, VerifyOptions, Algorithm } from 'jsonwebtoken' +import { v4 as uuidv4 } from 'uuid' +import { NotAuthenticated } from '@feathersjs/errors' +import { createDebug } from '@feathersjs/commons' +import { Application, Params } from '@feathersjs/feathers' +import { IncomingMessage, ServerResponse } from 'http' +import { AuthenticationConfiguration, defaultOptions } from './options' -const debug = createDebug('@feathersjs/authentication/base'); +const debug = createDebug('@feathersjs/authentication/base') export interface AuthenticationResult { - [key: string]: any; + [key: string]: any } export interface AuthenticationRequest { - strategy?: string; - [key: string]: any; + strategy?: string + [key: string]: any } -export type ConnectionEvent = 'login' | 'logout' | 'disconnect'; +export interface AuthenticationParams extends Params { + payload?: { [key: string]: any } + jwtOptions?: SignOptions + authStrategies?: string[] + secret?: string + [key: string]: any +} + +export type ConnectionEvent = 'login' | 'logout' | 'disconnect' export interface AuthenticationStrategy { /** @@ -26,24 +34,30 @@ export interface AuthenticationStrategy { * * @param auth The AuthenticationService */ - setAuthentication? (auth: AuthenticationBase): void; + setAuthentication?(auth: AuthenticationBase): void /** * Implement this method to get access to the Feathers application * * @param app The Feathers application instance */ - setApplication? (app: Application): void; + setApplication?(app: Application): void /** * Implement this method to get access to the strategy name * * @param name The name of the strategy */ - setName? (name: string): void; + setName?(name: string): void /** * Implement this method to verify the current configuration * and throw an error if it is invalid. */ - verifyConfiguration? (): void; + verifyConfiguration?(): void + /** + * Implement this method to setup this strategy + * @param auth The AuthenticationService + * @param name The name of the strategy + */ + setup?(auth: AuthenticationBase, name: string): Promise /** * Authenticate an authentication request with this strategy. * Should throw an error if the strategy did not succeed. @@ -51,36 +65,38 @@ export interface AuthenticationStrategy { * @param authentication The authentication request * @param params The service call parameters */ - authenticate? (authentication: AuthenticationRequest, params: Params): Promise; + authenticate?( + authentication: AuthenticationRequest, + params: AuthenticationParams + ): Promise /** * Update a real-time connection according to this strategy. * * @param connection The real-time connection * @param context The hook context */ - handleConnection? (event: ConnectionEvent, connection: any, authResult?: AuthenticationResult): Promise; + handleConnection?(event: ConnectionEvent, connection: any, authResult?: AuthenticationResult): Promise /** * Parse a basic HTTP request and response for authentication request information. * * @param req The HTTP request * @param res The HTTP response */ - parse? (req: IncomingMessage, res: ServerResponse): Promise; + parse?(req: IncomingMessage, res: ServerResponse): Promise } export interface JwtVerifyOptions extends VerifyOptions { - algorithm?: string | string[]; + algorithm?: string | string[] } /** * A base class for managing authentication strategies and creating and verifying JWTs */ export class AuthenticationBase { - app: Application; - configKey: string; - strategies: { - [key: string]: AuthenticationStrategy; - }; + app: Application + strategies: { [key: string]: AuthenticationStrategy } + configKey: string + isReady: boolean /** * Create a new authentication service. @@ -89,32 +105,33 @@ export class AuthenticationBase { * @param configKey The configuration key name in `app.get` (default: `authentication`) * @param options Optional initial options */ - constructor (app: Application, configKey = 'authentication', options = {}) { + constructor(app: Application, configKey = 'authentication', options = {}) { if (!app || typeof app.use !== 'function') { - throw new Error('An application instance has to be passed to the authentication service'); + throw new Error('An application instance has to be passed to the authentication service') } - this.app = app; - this.strategies = {}; - this.configKey = configKey; + this.app = app + this.strategies = {} + this.configKey = configKey + this.isReady = false - app.set('defaultAuthentication', app.get('defaultAuthentication') || configKey); - app.set(configKey, merge({}, app.get(configKey), options)); + app.set('defaultAuthentication', app.get('defaultAuthentication') || configKey) + app.set(configKey, merge({}, app.get(configKey), options)) } /** * Return the current configuration from the application */ - get configuration () { + get configuration(): AuthenticationConfiguration { // Always returns a copy of the authentication configuration - return Object.assign({}, defaultOptions, this.app.get(this.configKey)); + return Object.assign({}, defaultOptions, this.app.get(this.configKey)) } /** * A list of all registered strategy names */ - get strategyNames () { - return Object.keys(this.strategies); + get strategyNames() { + return Object.keys(this.strategies) } /** @@ -123,26 +140,30 @@ export class AuthenticationBase { * @param name The name to register the strategy under * @param strategy The authentication strategy instance */ - register (name: string, strategy: AuthenticationStrategy) { + register(name: string, strategy: AuthenticationStrategy) { // Call the functions a strategy can implement if (typeof strategy.setName === 'function') { - strategy.setName(name); + strategy.setName(name) } if (typeof strategy.setApplication === 'function') { - strategy.setApplication(this.app); + strategy.setApplication(this.app) } if (typeof strategy.setAuthentication === 'function') { - strategy.setAuthentication(this); + strategy.setAuthentication(this) } if (typeof strategy.verifyConfiguration === 'function') { - strategy.verifyConfiguration(); + strategy.verifyConfiguration() } // Register strategy as name - this.strategies[name] = strategy; + this.strategies[name] = strategy + + if (this.isReady) { + strategy.setup?.(this, name) + } } /** @@ -150,19 +171,18 @@ export class AuthenticationBase { * * @param names The list or strategy names */ - getStrategies (...names: string[]) { - return names.map(name => this.strategies[name]) - .filter(current => !!current); + getStrategies(...names: string[]) { + return names.map((name) => this.strategies[name]).filter((current) => !!current) } /** * Returns a single strategy by name - * + * * @param name The strategy name * @returns The authentication strategy or undefined */ - getStrategy (name: string) { - return this.strategies[name]; + getStrategy(name: string) { + return this.strategies[name] } /** @@ -172,19 +192,23 @@ export class AuthenticationBase { * @param optsOverride The options to extend the defaults (`configuration.jwtOptions`) with * @param secretOverride Use a different secret instead */ - async createAccessToken (payload: string | Buffer | object, optsOverride?: SignOptions, secretOverride?: Secret) { - const { secret, jwtOptions } = this.configuration; + async createAccessToken( + payload: string | Buffer | object, + optsOverride?: SignOptions, + secretOverride?: Secret + ) { + const { secret, jwtOptions } = this.configuration // Use configuration by default but allow overriding the secret - const jwtSecret = secretOverride || secret; + const jwtSecret = secretOverride || secret // Default jwt options merged with additional options - const options = merge({}, jwtOptions, optsOverride); + const options = merge({}, jwtOptions, optsOverride) if (!options.jwtid) { // Generate a UUID as JWT ID by default - options.jwtid = uuidv4(); + options.jwtid = uuidv4() } - return jsonwebtoken.sign(payload, jwtSecret, options); + return jsonwebtoken.sign(payload, jwtSecret, options) } /** @@ -194,24 +218,24 @@ export class AuthenticationBase { * @param optsOverride The options to extend the defaults (`configuration.jwtOptions`) with * @param secretOverride Use a different secret instead */ - async verifyAccessToken (accessToken: string, optsOverride?: JwtVerifyOptions, secretOverride?: Secret) { - const { secret, jwtOptions } = this.configuration; - const jwtSecret = secretOverride || secret; - const options = merge({}, jwtOptions, optsOverride); - const { algorithm } = options; + async verifyAccessToken(accessToken: string, optsOverride?: JwtVerifyOptions, secretOverride?: Secret) { + const { secret, jwtOptions } = this.configuration + const jwtSecret = secretOverride || secret + const options = merge({}, jwtOptions, optsOverride) + const { algorithm } = options // Normalize the `algorithm` setting into the algorithms array if (algorithm && !options.algorithms) { - options.algorithms = Array.isArray(algorithm) ? algorithm : [ algorithm ]; - delete options.algorithm; + options.algorithms = (Array.isArray(algorithm) ? algorithm : [algorithm]) as Algorithm[] + delete options.algorithm } try { - const verified = jsonwebtoken.verify(accessToken, jwtSecret, options); + const verified = jsonwebtoken.verify(accessToken, jwtSecret, options) - return verified as any; + return verified as any } catch (error: any) { - throw new NotAuthenticated(error.message, error); + throw new NotAuthenticated(error.message, error) } } @@ -222,33 +246,40 @@ export class AuthenticationBase { * @param params Service call parameters * @param allowed A list of allowed strategy names */ - async authenticate (authentication: AuthenticationRequest, params: Params, ...allowed: string[]) { - const { strategy } = authentication || {}; - const [ authStrategy ] = this.getStrategies(strategy); - const strategyAllowed = allowed.includes(strategy); + async authenticate( + authentication: AuthenticationRequest, + params: AuthenticationParams, + ...allowed: string[] + ) { + const { strategy } = authentication || {} + const [authStrategy] = this.getStrategies(strategy) + const strategyAllowed = allowed.includes(strategy) - debug('Running authenticate for strategy', strategy, allowed); + debug('Running authenticate for strategy', strategy, allowed) if (!authentication || !authStrategy || !strategyAllowed) { - const additionalInfo = (!strategy && ' (no `strategy` set)') || - (!strategyAllowed && ' (strategy not allowed in authStrategies)') || ''; + const additionalInfo = + (!strategy && ' (no `strategy` set)') || + (!strategyAllowed && ' (strategy not allowed in authStrategies)') || + '' // If there are no valid strategies or `authentication` is not an object - throw new NotAuthenticated('Invalid authentication information' + additionalInfo); + throw new NotAuthenticated('Invalid authentication information' + additionalInfo) } return authStrategy.authenticate(authentication, { ...params, authenticated: true - }); + }) } - async handleConnection (event: ConnectionEvent, connection: any, authResult?: AuthenticationResult) { - const strategies = this.getStrategies(...Object.keys(this.strategies)) - .filter(current => typeof current.handleConnection === 'function'); + async handleConnection(event: ConnectionEvent, connection: any, authResult?: AuthenticationResult) { + const strategies = this.getStrategies(...Object.keys(this.strategies)).filter( + (current) => typeof current.handleConnection === 'function' + ) for (const strategy of strategies) { - await strategy.handleConnection(event, connection, authResult); + await strategy.handleConnection(event, connection, authResult) } } @@ -259,20 +290,29 @@ export class AuthenticationBase { * @param res The HTTP response * @param names A list of strategies to use */ - async parse (req: IncomingMessage, res: ServerResponse, ...names: string[]) { - const strategies = this.getStrategies(...names) - .filter(current => typeof current.parse === 'function'); + async parse(req: IncomingMessage, res: ServerResponse, ...names: string[]) { + const strategies = this.getStrategies(...names).filter((current) => typeof current.parse === 'function') - debug('Strategies parsing HTTP header for authentication information', names); + debug('Strategies parsing HTTP header for authentication information', names) for (const authStrategy of strategies) { - const value = await authStrategy.parse(req, res); + const value = await authStrategy.parse(req, res) if (value !== null) { - return value; + return value } } - return null; + return null + } + + async setup() { + this.isReady = true + + for (const name of Object.keys(this.strategies)) { + const strategy = this.strategies[name] + + await strategy.setup?.(this, name) + } } } diff --git a/packages/authentication/src/hooks/authenticate.ts b/packages/authentication/src/hooks/authenticate.ts index 5c1103a056..fc1d2e3e67 100644 --- a/packages/authentication/src/hooks/authenticate.ts +++ b/packages/authentication/src/hooks/authenticate.ts @@ -1,63 +1,67 @@ -import flatten from 'lodash/flatten'; -import omit from 'lodash/omit'; -import { HookContext, NextFunction } from '@feathersjs/feathers'; -import { NotAuthenticated } from '@feathersjs/errors'; -import { createDebug } from '@feathersjs/commons'; +import flatten from 'lodash/flatten' +import omit from 'lodash/omit' +import { HookContext, NextFunction } from '@feathersjs/feathers' +import { NotAuthenticated } from '@feathersjs/errors' +import { createDebug } from '@feathersjs/commons' -const debug = createDebug('@feathersjs/authentication/hooks/authenticate'); +const debug = createDebug('@feathersjs/authentication/hooks/authenticate') export interface AuthenticateHookSettings { - service?: string; - strategies?: string[]; + service?: string + strategies?: string[] } export default (originalSettings: string | AuthenticateHookSettings, ...originalStrategies: string[]) => { - const settings = typeof originalSettings === 'string' - ? { strategies: flatten([ originalSettings, ...originalStrategies ]) } - : originalSettings; + const settings = + typeof originalSettings === 'string' + ? { strategies: flatten([originalSettings, ...originalStrategies]) } + : originalSettings if (!originalSettings || settings.strategies.length === 0) { - throw new Error('The authenticate hook needs at least one allowed strategy'); + throw new Error('The authenticate hook needs at least one allowed strategy') } return async (context: HookContext, _next?: NextFunction) => { - const next = typeof _next === 'function' ? _next : async () => context; - const { app, params, type, path, service } = context; - const { strategies } = settings; - const { provider, authentication } = params; - const authService = app.defaultAuthentication(settings.service); + const next = typeof _next === 'function' ? _next : async () => context + const { app, params, type, path, service } = context + const { strategies } = settings + const { provider, authentication } = params + const authService = app.defaultAuthentication(settings.service) - debug(`Running authenticate hook on '${path}'`); + debug(`Running authenticate hook on '${path}'`) if (type && type !== 'before') { - throw new NotAuthenticated('The authenticate hook must be used as a before hook'); + throw new NotAuthenticated('The authenticate hook must be used as a before hook') } if (!authService || typeof authService.authenticate !== 'function') { - throw new NotAuthenticated('Could not find a valid authentication service'); + throw new NotAuthenticated('Could not find a valid authentication service') } - // @ts-ignore if (service === authService) { - throw new NotAuthenticated('The authenticate hook does not need to be used on the authentication service'); + throw new NotAuthenticated( + 'The authenticate hook does not need to be used on the authentication service' + ) } if (params.authenticated === true) { - return next(); + return next() } if (authentication) { - const authParams = omit(params, 'provider', 'authentication'); + const authParams = omit(params, 'provider', 'authentication') - debug('Authenticating with', authentication, strategies); + debug('Authenticating with', authentication, strategies) - const authResult = await authService.authenticate(authentication, authParams, ...strategies); + const authResult = await authService.authenticate(authentication, authParams, ...strategies) - context.params = Object.assign({}, params, omit(authResult, 'accessToken'), { authenticated: true }); + context.params = Object.assign({}, params, omit(authResult, 'accessToken'), { + authenticated: true + }) } else if (provider) { - throw new NotAuthenticated('Not authenticated'); + throw new NotAuthenticated('Not authenticated') } - return next(); - }; -}; + return next() + } +} diff --git a/packages/authentication/src/hooks/connection.ts b/packages/authentication/src/hooks/connection.ts index c8c01f0e6c..8403490fa0 100644 --- a/packages/authentication/src/hooks/connection.ts +++ b/packages/authentication/src/hooks/connection.ts @@ -1,17 +1,20 @@ -import { HookContext, NextFunction } from '@feathersjs/feathers'; -import omit from 'lodash/omit'; -import { AuthenticationBase, ConnectionEvent } from '../core'; +import { HookContext, NextFunction } from '@feathersjs/feathers' +import omit from 'lodash/omit' +import { AuthenticationBase, ConnectionEvent } from '../core' export default (event: ConnectionEvent) => async (context: HookContext, next: NextFunction) => { - await next(); + await next() - const { result, params: { connection } } = context; + const { + result, + params: { connection } + } = context if (connection) { - const service = context.service as unknown as AuthenticationBase; + const service = context.service as unknown as AuthenticationBase - Object.assign(connection, omit(result, 'accessToken', 'authentication')); + Object.assign(connection, omit(result, 'accessToken', 'authentication')) - await service.handleConnection(event, connection, result); + await service.handleConnection(event, connection, result) } -}; +} diff --git a/packages/authentication/src/hooks/event.ts b/packages/authentication/src/hooks/event.ts index 4525db1aaf..44b6953b91 100644 --- a/packages/authentication/src/hooks/event.ts +++ b/packages/authentication/src/hooks/event.ts @@ -1,16 +1,16 @@ -import { HookContext, NextFunction } from '@feathersjs/feathers'; -import { createDebug } from '@feathersjs/commons'; -import { ConnectionEvent } from '../core'; +import { HookContext, NextFunction } from '@feathersjs/feathers' +import { createDebug } from '@feathersjs/commons' +import { ConnectionEvent } from '../core' -const debug = createDebug('@feathersjs/authentication/hooks/connection'); +const debug = createDebug('@feathersjs/authentication/hooks/connection') export default (event: ConnectionEvent) => async (context: HookContext, next: NextFunction) => { - await next(); + await next() - const { app, result, params } = context; + const { app, result, params } = context if (params.provider && result) { - debug(`Sending authentication event '${event}'`); - app.emit(event, result, params, context); + debug(`Sending authentication event '${event}'`) + app.emit(event, result, params, context) } -}; +} diff --git a/packages/authentication/src/hooks/index.ts b/packages/authentication/src/hooks/index.ts index 775f3e0943..4c9a354cfa 100644 --- a/packages/authentication/src/hooks/index.ts +++ b/packages/authentication/src/hooks/index.ts @@ -1,3 +1,3 @@ -export { default as authenticate } from './authenticate'; -export { default as connection } from './connection'; -export { default as event } from './event'; +export { default as authenticate } from './authenticate' +export { default as connection } from './connection' +export { default as event } from './event' diff --git a/packages/authentication/src/index.ts b/packages/authentication/src/index.ts index c634a3f7a5..47962f995b 100644 --- a/packages/authentication/src/index.ts +++ b/packages/authentication/src/index.ts @@ -1,12 +1,14 @@ -export * as hooks from './hooks'; -export { authenticate } from './hooks'; +export * as hooks from './hooks' +export { authenticate } from './hooks' export { AuthenticationBase, AuthenticationRequest, AuthenticationResult, AuthenticationStrategy, + AuthenticationParams, ConnectionEvent -} from './core'; -export { AuthenticationBaseStrategy } from './strategy'; -export { AuthenticationService } from './service'; -export { JWTStrategy } from './jwt'; +} from './core' +export { AuthenticationBaseStrategy } from './strategy' +export { AuthenticationService } from './service' +export { JWTStrategy } from './jwt' +export { authenticationSettingsSchema, AuthenticationConfiguration } from './options' diff --git a/packages/authentication/src/jwt.ts b/packages/authentication/src/jwt.ts index 910e41190b..4262e7bf0f 100644 --- a/packages/authentication/src/jwt.ts +++ b/packages/authentication/src/jwt.ts @@ -1,88 +1,97 @@ -/* eslint-disable @typescript-eslint/no-unused-vars */ -import omit from 'lodash/omit'; -import { IncomingMessage } from 'http'; -import { NotAuthenticated } from '@feathersjs/errors'; -import { Params } from '@feathersjs/feathers'; -import { createDebug } from '@feathersjs/commons'; +/* eslint-disable @typescript-eslint/no-unused-vars, @typescript-eslint/ban-ts-comment */ +import omit from 'lodash/omit' +import { IncomingMessage } from 'http' +import { NotAuthenticated } from '@feathersjs/errors' +import { Params } from '@feathersjs/feathers' +import { createDebug } from '@feathersjs/commons' // @ts-ignore -import lt from 'long-timeout'; +import lt from 'long-timeout' -import { AuthenticationBaseStrategy } from './strategy'; -import { AuthenticationRequest, AuthenticationResult, ConnectionEvent } from './core'; +import { AuthenticationBaseStrategy } from './strategy' +import { AuthenticationParams, AuthenticationRequest, AuthenticationResult, ConnectionEvent } from './core' -const debug = createDebug('@feathersjs/authentication/jwt'); -const SPLIT_HEADER = /(\S+)\s+(\S+)/; +const debug = createDebug('@feathersjs/authentication/jwt') +const SPLIT_HEADER = /(\S+)\s+(\S+)/ export class JWTStrategy extends AuthenticationBaseStrategy { - expirationTimers = new WeakMap(); + expirationTimers = new WeakMap() - get configuration () { - const authConfig = this.authentication.configuration; - const config = super.configuration; + get configuration() { + const authConfig = this.authentication.configuration + const config = super.configuration return { service: authConfig.service, entity: authConfig.entity, entityId: authConfig.entityId, header: 'Authorization', - schemes: [ 'Bearer', 'JWT' ], + schemes: ['Bearer', 'JWT'], ...config - }; + } } - async handleConnection (event: ConnectionEvent, connection: any, authResult?: AuthenticationResult): Promise { - const isValidLogout = event === 'logout' && connection.authentication && authResult && - connection.authentication.accessToken === authResult.accessToken; + async handleConnection( + event: ConnectionEvent, + connection: any, + authResult?: AuthenticationResult + ): Promise { + const isValidLogout = + event === 'logout' && + connection.authentication && + authResult && + connection.authentication.accessToken === authResult.accessToken - const { accessToken } = authResult || {}; + const { accessToken } = authResult || {} if (accessToken && event === 'login') { - debug('Adding authentication information to connection'); - const { exp } = await this.authentication.verifyAccessToken(accessToken); + debug('Adding authentication information to connection') + const { exp } = await this.authentication.verifyAccessToken(accessToken) // The time (in ms) until the token expires - const duration = (exp * 1000) - Date.now(); + const duration = exp * 1000 - Date.now() // This may have to be a `logout` event but right now we don't want // the whole context object lingering around until the timer is gone - const timer = lt.setTimeout(() => this.app.emit('disconnect', connection), duration); + const timer = lt.setTimeout(() => this.app.emit('disconnect', connection), duration) - debug(`Registering connection expiration timer for ${duration}ms`); - lt.clearTimeout(this.expirationTimers.get(connection)); - this.expirationTimers.set(connection, timer); + debug(`Registering connection expiration timer for ${duration}ms`) + lt.clearTimeout(this.expirationTimers.get(connection)) + this.expirationTimers.set(connection, timer) - debug('Adding authentication information to connection'); + debug('Adding authentication information to connection') connection.authentication = { strategy: this.name, accessToken - }; + } } else if (event === 'disconnect' || isValidLogout) { - debug('Removing authentication information and expiration timer from connection'); + debug('Removing authentication information and expiration timer from connection') - const { entity } = this.configuration; + const { entity } = this.configuration - delete connection[entity]; - delete connection.authentication; + delete connection[entity] + delete connection.authentication - lt.clearTimeout(this.expirationTimers.get(connection)); - this.expirationTimers.delete(connection); + lt.clearTimeout(this.expirationTimers.get(connection)) + this.expirationTimers.delete(connection) } } - verifyConfiguration () { - const allowedKeys = [ 'entity', 'entityId', 'service', 'header', 'schemes' ]; + verifyConfiguration() { + const allowedKeys = ['entity', 'entityId', 'service', 'header', 'schemes'] for (const key of Object.keys(this.configuration)) { if (!allowedKeys.includes(key)) { - throw new Error(`Invalid JwtStrategy option 'authentication.${this.name}.${key}'. Did you mean to set it in 'authentication.jwtOptions'?`); + throw new Error( + `Invalid JwtStrategy option 'authentication.${this.name}.${key}'. Did you mean to set it in 'authentication.jwtOptions'?` + ) } } if (typeof this.configuration.header !== 'string') { - throw new Error(`The 'header' option for the ${this.name} strategy must be a string`); + throw new Error(`The 'header' option for the ${this.name} strategy must be a string`) } } - async getEntityQuery (_params: Params) { - return {}; + async getEntityQuery(_params: Params) { + return {} } /** @@ -91,40 +100,40 @@ export class JWTStrategy extends AuthenticationBaseStrategy { * @param id The id to use * @param params Service call parameters */ - async getEntity (id: string, params: Params) { - const entityService = this.entityService; - const { entity } = this.configuration; + async getEntity(id: string, params: Params) { + const entityService = this.entityService + const { entity } = this.configuration - debug('Getting entity', id); + debug('Getting entity', id) if (entityService === null) { - throw new NotAuthenticated('Could not find entity service'); + throw new NotAuthenticated('Could not find entity service') } - const query = await this.getEntityQuery(params); - const getParams = Object.assign({}, omit(params, 'provider'), { query }); - const result = await entityService.get(id, getParams); + const query = await this.getEntityQuery(params) + const getParams = Object.assign({}, omit(params, 'provider'), { query }) + const result = await entityService.get(id, getParams) if (!params.provider) { - return result; + return result } - return entityService.get(id, { ...params, [entity]: result }); + return entityService.get(id, { ...params, [entity]: result }) } - async getEntityId (authResult: AuthenticationResult, _params: Params) { - return authResult.authentication.payload.sub; + async getEntityId(authResult: AuthenticationResult, _params: Params) { + return authResult.authentication.payload.sub } - async authenticate (authentication: AuthenticationRequest, params: Params) { - const { accessToken } = authentication; - const { entity } = this.configuration; + async authenticate(authentication: AuthenticationRequest, params: AuthenticationParams) { + const { accessToken } = authentication + const { entity } = this.configuration if (!accessToken) { - throw new NotAuthenticated('No access token'); + throw new NotAuthenticated('No access token') } - const payload = await this.authentication.verifyAccessToken(accessToken, params.jwt); + const payload = await this.authentication.verifyAccessToken(accessToken, params.jwt) const result = { accessToken, authentication: { @@ -132,46 +141,44 @@ export class JWTStrategy extends AuthenticationBaseStrategy { accessToken, payload } - }; + } if (entity === null) { - return result; + return result } - const entityId = await this.getEntityId(result, params); - const value = await this.getEntity(entityId, params); + const entityId = await this.getEntityId(result, params) + const value = await this.getEntity(entityId, params) return { ...result, [entity]: value - }; + } } - async parse (req: IncomingMessage): Promise<{ - strategy: string; - accessToken: string; + async parse(req: IncomingMessage): Promise<{ + strategy: string + accessToken: string } | null> { - const { header, schemes }: { header: string, schemes: string[] } = this.configuration; - const headerValue = req.headers && req.headers[header.toLowerCase()]; + const { header, schemes }: { header: string; schemes: string[] } = this.configuration + const headerValue = req.headers && req.headers[header.toLowerCase()] if (!headerValue || typeof headerValue !== 'string') { - return null; + return null } - debug('Found parsed header value'); + debug('Found parsed header value') - const [ , scheme, schemeValue ] = headerValue.match(SPLIT_HEADER) || []; - const hasScheme = scheme && schemes.some( - current => new RegExp(current, 'i').test(scheme) - ); + const [, scheme, schemeValue] = headerValue.match(SPLIT_HEADER) || [] + const hasScheme = scheme && schemes.some((current) => new RegExp(current, 'i').test(scheme)) if (scheme && !hasScheme) { - return null; + return null } return { strategy: this.name, accessToken: hasScheme ? schemeValue : headerValue - }; + } } } diff --git a/packages/authentication/src/options.ts b/packages/authentication/src/options.ts index ee869f2b05..2176889087 100644 --- a/packages/authentication/src/options.ts +++ b/packages/authentication/src/options.ts @@ -1,5 +1,7 @@ -export default { - authStrategies: [], +import { FromSchema, authenticationSettingsSchema } from '@feathersjs/schema' + +export const defaultOptions = { + authStrategies: [] as string[], jwtOptions: { header: { typ: 'access' }, // by default is an access token but can be any type audience: 'https://yourdomain.com', // The resource server where the token is processed @@ -7,4 +9,8 @@ export default { algorithm: 'HS256', expiresIn: '1d' } -}; +} + +export { authenticationSettingsSchema } + +export type AuthenticationConfiguration = FromSchema diff --git a/packages/authentication/src/service.ts b/packages/authentication/src/service.ts index 6d3e575866..f3b7107c0e 100644 --- a/packages/authentication/src/service.ts +++ b/packages/authentication/src/service.ts @@ -1,47 +1,64 @@ -import merge from 'lodash/merge'; -import { NotAuthenticated } from '@feathersjs/errors'; -import { AuthenticationBase, AuthenticationResult, AuthenticationRequest } from './core'; -import { connection, event } from './hooks'; -import '@feathersjs/transport-commons'; -import { createDebug } from '@feathersjs/commons'; -import { Params, ServiceMethods, ServiceAddons } from '@feathersjs/feathers'; -import jsonwebtoken from 'jsonwebtoken'; +import merge from 'lodash/merge' +import { NotAuthenticated } from '@feathersjs/errors' +import '@feathersjs/transport-commons' +import { createDebug } from '@feathersjs/commons' +import { ServiceMethods, ServiceAddons } from '@feathersjs/feathers' +import { resolveDispatch } from '@feathersjs/schema' +import jsonwebtoken from 'jsonwebtoken' +import { hooks } from '@feathersjs/hooks' -const debug = createDebug('@feathersjs/authentication/service'); +import { AuthenticationBase, AuthenticationResult, AuthenticationRequest, AuthenticationParams } from './core' +import { connection, event } from './hooks' + +const debug = createDebug('@feathersjs/authentication/service') declare module '@feathersjs/feathers/lib/declarations' { - interface FeathersApplication { // eslint-disable-line + // eslint-disable-next-line @typescript-eslint/no-unused-vars + interface FeathersApplication { + // eslint-disable-line /** * Returns the default authentication service or the * authentication service for a given path. * * @param location The service path to use (optional) */ - defaultAuthentication? (location?: string): AuthenticationService; + defaultAuthentication?(location?: string): AuthenticationService } interface Params { - authenticated?: boolean; - authentication?: AuthenticationRequest; + authenticated?: boolean + authentication?: AuthenticationRequest } } -// eslint-disable-next-line +// eslint-disable-next-line @typescript-eslint/no-empty-interface export interface AuthenticationService extends ServiceAddons {} -export class AuthenticationService extends AuthenticationBase implements Partial> { - constructor (app: any, configKey = 'authentication', options = {}) { - super(app, configKey, options); +export class AuthenticationService + extends AuthenticationBase + implements Partial> +{ + constructor(app: any, configKey = 'authentication', options = {}) { + super(app, configKey, options) + + hooks(this, { + create: [resolveDispatch(), connection('login'), event('login')], + remove: [resolveDispatch(), connection('logout'), event('logout')] + }) + + this.app.on('disconnect', async (connection) => { + await this.handleConnection('disconnect', connection) + }) if (typeof app.defaultAuthentication !== 'function') { app.defaultAuthentication = function (location?: string) { - const configKey = app.get('defaultAuthentication'); - const path = location || Object.keys(this.services).find(current => - this.service(current).configKey === configKey - ); + const configKey = app.get('defaultAuthentication') + const path = + location || + Object.keys(this.services).find((current) => this.service(current).configKey === configKey) - return path ? this.service(path) : null; - }; + return path ? this.service(path) : null + } } } /** @@ -51,11 +68,11 @@ export class AuthenticationService extends AuthenticationBase implements Partial * @param _authResult The current authentication result * @param params The service call parameters */ - async getPayload (_authResult: AuthenticationResult, params: Params) { + async getPayload(_authResult: AuthenticationResult, params: AuthenticationParams) { // Uses `params.payload` or returns an empty payload - const { payload = {} } = params; + const { payload = {} } = params - return payload; + return payload } /** @@ -65,24 +82,24 @@ export class AuthenticationService extends AuthenticationBase implements Partial * @param authResult The authentication result * @param params Service call parameters */ - async getTokenOptions (authResult: AuthenticationResult, params: Params) { - const { service, entity, entityId } = this.configuration; - const jwtOptions = merge({}, params.jwtOptions, params.jwt); - const value = service && entity && authResult[entity]; + async getTokenOptions(authResult: AuthenticationResult, params: AuthenticationParams) { + const { service, entity, entityId } = this.configuration + const jwtOptions = merge({}, params.jwtOptions, params.jwt) + const value = service && entity && authResult[entity] // Set the subject to the entity id if it is available if (value && !jwtOptions.subject) { - const idProperty = entityId || this.app.service(service).id; - const subject = value[idProperty]; + const idProperty = entityId || this.app.service(service).id + const subject = value[idProperty] if (subject === undefined) { - throw new NotAuthenticated(`Can not set subject from ${entity}.${idProperty}`); + throw new NotAuthenticated(`Can not set subject from ${entity}.${idProperty}`) } - jwtOptions.subject = `${subject}`; + jwtOptions.subject = `${subject}` } - return jwtOptions; + return jwtOptions } /** @@ -92,36 +109,38 @@ export class AuthenticationService extends AuthenticationBase implements Partial * @param data The authentication request (should include `strategy` key) * @param params Service call parameters */ - async create (data: AuthenticationRequest, params?: Params) { - const authStrategies = params.authStrategies || this.configuration.authStrategies; + async create(data: AuthenticationRequest, params?: AuthenticationParams) { + const authStrategies = params.authStrategies || this.configuration.authStrategies if (!authStrategies.length) { - throw new NotAuthenticated('No authentication strategies allowed for creating a JWT (`authStrategies`)'); + throw new NotAuthenticated('No authentication strategies allowed for creating a JWT (`authStrategies`)') } - const authResult = await this.authenticate(data, params, ...authStrategies); + const authResult = await this.authenticate(data, params, ...authStrategies) - debug('Got authentication result', authResult); + debug('Got authentication result', authResult) if (authResult.accessToken) { - return authResult; + return authResult } - const [ payload, jwtOptions ] = await Promise.all([ + const [payload, jwtOptions] = await Promise.all([ this.getPayload(authResult, params), this.getTokenOptions(authResult, params) - ]); + ]) - debug('Creating JWT with', payload, jwtOptions); + debug('Creating JWT with', payload, jwtOptions) - const accessToken = await this.createAccessToken(payload, jwtOptions, params.secret); + const accessToken = await this.createAccessToken(payload, jwtOptions, params.secret) - return merge({ accessToken }, authResult, { + return { + accessToken, + ...authResult, authentication: { - accessToken, - payload: jsonwebtoken.decode(accessToken) + ...authResult.authentication, + payload: jsonwebtoken.decode(accessToken) } - }); + } } /** @@ -131,57 +150,54 @@ export class AuthenticationService extends AuthenticationBase implements Partial * @param id The JWT to remove or null * @param params Service call parameters */ - async remove (id: string | null, params?: Params) { - const { authentication } = params; - const { authStrategies } = this.configuration; + async remove(id: string | null, params?: AuthenticationParams) { + const { authentication } = params + const { authStrategies } = this.configuration // When an id is passed it is expected to be the authentication `accessToken` if (id !== null && id !== authentication.accessToken) { - throw new NotAuthenticated('Invalid access token'); + throw new NotAuthenticated('Invalid access token') } - debug('Verifying authentication strategy in remove'); + debug('Verifying authentication strategy in remove') - return this.authenticate(authentication, params, ...authStrategies); + return this.authenticate(authentication, params, ...authStrategies) } /** * Validates the service configuration. */ - async setup () { + async setup() { + await super.setup() + // The setup method checks for valid settings and registers the // connection and event (login, logout) hooks - const { secret, service, entity, entityId } = this.configuration; + const { secret, service, entity, entityId } = this.configuration if (typeof secret !== 'string') { - throw new Error('A \'secret\' must be provided in your authentication configuration'); + throw new Error("A 'secret' must be provided in your authentication configuration") } if (entity !== null) { if (service === undefined) { - throw new Error('The \'service\' option is not set in the authentication configuration'); + throw new Error("The 'service' option is not set in the authentication configuration") } if (this.app.service(service) === undefined) { - throw new Error(`The '${service}' entity service does not exist (set to 'null' if it is not required)`); + throw new Error( + `The '${service}' entity service does not exist (set to 'null' if it is not required)` + ) } if (this.app.service(service).id === undefined && entityId === undefined) { - throw new Error(`The '${service}' service does not have an 'id' property and no 'entityId' option is set.`); + throw new Error( + `The '${service}' service does not have an 'id' property and no 'entityId' option is set.` + ) } } - (this as any).hooks({ - create: [ connection('login'), event('login') ], - remove: [ connection('logout'), event('logout') ] - }); - - this.app.on('disconnect', async (connection) => { - await this.handleConnection('disconnect', connection); - }); - if (typeof this.publish === 'function') { - this.publish(() => null); + this.publish(() => null) } } } diff --git a/packages/authentication/src/strategy.ts b/packages/authentication/src/strategy.ts index 51fc84ac69..99a1ec9c58 100644 --- a/packages/authentication/src/strategy.ts +++ b/packages/authentication/src/strategy.ts @@ -1,34 +1,34 @@ -import { AuthenticationStrategy, AuthenticationBase } from './core'; -import { Application, Service } from '@feathersjs/feathers'; +import { AuthenticationStrategy, AuthenticationBase } from './core' +import { Application, Service } from '@feathersjs/feathers' export class AuthenticationBaseStrategy implements AuthenticationStrategy { - authentication?: AuthenticationBase; - app?: Application; - name?: string; + authentication?: AuthenticationBase + app?: Application + name?: string - setAuthentication (auth: AuthenticationBase) { - this.authentication = auth; + setAuthentication(auth: AuthenticationBase) { + this.authentication = auth } - setApplication (app: Application) { - this.app = app; + setApplication(app: Application) { + this.app = app } - setName (name: string) { - this.name = name; + setName(name: string) { + this.name = name } - get configuration () { - return this.authentication.configuration[this.name]; + get configuration(): any { + return this.authentication.configuration[this.name] } - get entityService (): Service { - const { service } = this.configuration; + get entityService(): Service { + const { service } = this.configuration if (!service) { - return null; + return null } - return this.app.service(service) || null; + return this.app.service(service) || null } } diff --git a/packages/authentication/test/core.test.ts b/packages/authentication/test/core.test.ts index 3471a0caeb..3ffcf97ec3 100644 --- a/packages/authentication/test/core.test.ts +++ b/packages/authentication/test/core.test.ts @@ -1,254 +1,303 @@ -import assert from 'assert'; -import { feathers, Application } from '@feathersjs/feathers'; -import jwt from 'jsonwebtoken'; +/* eslint-disable @typescript-eslint/ban-ts-comment */ +import assert from 'assert' +import { feathers, Application } from '@feathersjs/feathers' +import jwt from 'jsonwebtoken' +import { Infer, schema } from '@feathersjs/schema' -import { AuthenticationBase, AuthenticationRequest } from '../src/core'; -import { Strategy1, Strategy2, MockRequest } from './fixtures'; -import { ServerResponse } from 'http'; +import { AuthenticationBase, AuthenticationRequest } from '../src/core' +import { authenticationSettingsSchema } from '../src/options' +import { Strategy1, Strategy2, MockRequest } from './fixtures' +import { ServerResponse } from 'http' -const UUID = /[0-9a-f]{8}-[0-9a-f]{4}-[0-9a-f]{4}-[0-9a-f]{4}-[0-9a-f]{12}/; +const UUID = /[0-9a-f]{8}-[0-9a-f]{4}-[0-9a-f]{4}-[0-9a-f]{4}-[0-9a-f]{12}/ describe('authentication/core', () => { - let app: Application; - let auth: AuthenticationBase; + let app: Application + let auth: AuthenticationBase beforeEach(() => { - app = feathers(); + app = feathers() auth = new AuthenticationBase(app, 'authentication', { entity: 'user', service: 'users', secret: 'supersecret', first: { hello: 'test' } - }); + }) - auth.register('first', new Strategy1()); - auth.register('second', new Strategy2()); + auth.register('first', new Strategy1()) + auth.register('second', new Strategy2()) auth.register('dummy', { - async authenticate (data: AuthenticationRequest) { - return data; + async authenticate(data: AuthenticationRequest) { + return data } - }); - }); + }) + }) describe('configuration', () => { + it('infers configuration from settings schema', async () => { + const settingsSchema = schema({ + $id: 'AuthSettingsSchema', + ...authenticationSettingsSchema + } as const) + type Settings = Infer + const config: Settings = { + entity: 'user', + secret: 'supersecret', + authStrategies: ['some', 'thing'] + } + + await settingsSchema.validate(config) + }) + it('throws an error when app is not provided', () => { try { // @ts-ignore - const otherAuth = new AuthenticationBase(); - assert.fail('Should never get here'); - assert.ok(otherAuth); + const otherAuth = new AuthenticationBase() + assert.fail('Should never get here') + assert.ok(otherAuth) } catch (error: any) { - assert.strictEqual(error.message, + assert.strictEqual( + error.message, 'An application instance has to be passed to the authentication service' - ); + ) } - }); + }) it('sets defaults', () => { // Getting configuration twice returns a copy - assert.notStrictEqual(auth.configuration, auth.configuration); - assert.strictEqual(auth.configuration.entity, 'user'); - }); + assert.notStrictEqual(auth.configuration, auth.configuration) + assert.strictEqual(auth.configuration.entity, 'user') + }) it('allows to override jwtOptions, does not merge', () => { - const { jwtOptions } = auth.configuration; + const { jwtOptions } = auth.configuration const auth2options = { jwtOptions: { expiresIn: '1w' } - }; + } - app.set('auth2', auth2options); + app.set('auth2', auth2options) - const auth2 = new AuthenticationBase(app, 'auth2'); + const auth2 = new AuthenticationBase(app, 'auth2') - assert.ok(jwtOptions); - assert.strictEqual(jwtOptions.expiresIn, '1d'); - assert.strictEqual(jwtOptions.issuer, 'feathers'); + assert.ok(jwtOptions) + assert.strictEqual(jwtOptions.expiresIn, '1d') + assert.strictEqual(jwtOptions.issuer, 'feathers') - assert.deepStrictEqual(auth2.configuration.jwtOptions, auth2options.jwtOptions); - }); + assert.deepStrictEqual(auth2.configuration.jwtOptions, auth2options.jwtOptions) + }) it('sets configKey and defaultAuthentication', () => { - assert.strictEqual(app.get('defaultAuthentication'), 'authentication'); - }); + assert.strictEqual(app.get('defaultAuthentication'), 'authentication') + }) it('uses default configKey', () => { - const otherApp = feathers(); - const otherAuth = new AuthenticationBase(otherApp); + const otherApp = feathers() + const otherAuth = new AuthenticationBase(otherApp) - assert.ok(otherAuth); - assert.strictEqual(otherApp.get('defaultAuthentication'), 'authentication'); - assert.deepStrictEqual(otherApp.get('authentication'), {}); - }); - }); + assert.ok(otherAuth) + assert.strictEqual(otherApp.get('defaultAuthentication'), 'authentication') + assert.deepStrictEqual(otherApp.get('authentication'), {}) + }) + }) describe('strategies', () => { it('strategyNames', () => { - assert.deepStrictEqual(auth.strategyNames, [ 'first', 'second', 'dummy' ]); - }); + assert.deepStrictEqual(auth.strategyNames, ['first', 'second', 'dummy']) + }) it('getStrategies', () => { - const first = auth.getStrategies('first'); - const invalid = auth.getStrategies('first', 'invalid', 'second'); + const first = auth.getStrategies('first') + const invalid = auth.getStrategies('first', 'invalid', 'second') - assert.strictEqual(first.length, 1); - assert.strictEqual(invalid.length, 2, 'Filtered out invalid strategies'); - }); + assert.strictEqual(first.length, 1) + assert.strictEqual(invalid.length, 2, 'Filtered out invalid strategies') + }) it('getStrategy', () => { - const first = auth.getStrategy('first'); + const first = auth.getStrategy('first') - assert.ok(first); - }); + assert.ok(first) + }) it('calls setName, setApplication and setAuthentication if available', () => { - const [ first ] = auth.getStrategies('first') as [ Strategy1 ]; + const [first] = auth.getStrategies('first') as [Strategy1] - assert.strictEqual(first.name, 'first'); - assert.strictEqual(first.app, app); - assert.strictEqual(first.authentication, auth); - }); + assert.strictEqual(first.name, 'first') + assert.strictEqual(first.app, app) + assert.strictEqual(first.authentication, auth) + }) it('strategy configuration getter', () => { - const [ first ] = auth.getStrategies('first') as [ Strategy1 ]; + const [first] = auth.getStrategies('first') as [Strategy1] - assert.deepStrictEqual(first.configuration, { hello: 'test' }); - }); + assert.deepStrictEqual(first.configuration, { hello: 'test' }) + }) it('strategy configuration getter', () => { - const [ first ] = auth.getStrategies('first') as [ Strategy1 ]; - const oldService = auth.configuration.service; + const [first] = auth.getStrategies('first') as [Strategy1] + const oldService = auth.configuration.service - delete auth.configuration.service; + delete auth.configuration.service - assert.strictEqual(first.entityService, null); + assert.strictEqual(first.entityService, null) - auth.configuration.service = oldService; - }); - }); + auth.configuration.service = oldService + }) + }) describe('authenticate', () => { describe('with strategy set in params', () => { it('returns first success', async () => { - const result = await auth.authenticate({ - strategy: 'first', - username: 'David' - }, {}, 'first', 'second'); + const result = await auth.authenticate( + { + strategy: 'first', + username: 'David' + }, + {}, + 'first', + 'second' + ) - assert.deepStrictEqual(result, Strategy1.result); - }); + assert.deepStrictEqual(result, Strategy1.result) + }) it('returns error when failed', async () => { try { - await auth.authenticate({ - strategy: 'first', - username: 'Steve' - }, {}, 'first', 'second'); - assert.fail('Should never get here'); + await auth.authenticate( + { + strategy: 'first', + username: 'Steve' + }, + {}, + 'first', + 'second' + ) + assert.fail('Should never get here') } catch (error: any) { - assert.strictEqual(error.name, 'NotAuthenticated'); - assert.strictEqual(error.message, 'Invalid Dave'); + assert.strictEqual(error.name, 'NotAuthenticated') + assert.strictEqual(error.message, 'Invalid Dave') } - }); + }) it('returns second success', async () => { const authentication = { strategy: 'second', v2: true, password: 'supersecret' - }; + } - const result = await auth.authenticate(authentication, {}, 'first', 'second'); + const result = await auth.authenticate(authentication, {}, 'first', 'second') - assert.deepStrictEqual(result, Object.assign({}, Strategy2.result, { - authentication, - params: { authenticated: true } - })); - }); + assert.deepStrictEqual( + result, + Object.assign({}, Strategy2.result, { + authentication, + params: { authenticated: true } + }) + ) + }) it('passes params', async () => { const params = { some: 'thing' - }; + } const authentication = { strategy: 'second', v2: true, password: 'supersecret' - }; - - const result = await auth.authenticate(authentication, params, 'first', 'second'); + } - assert.deepStrictEqual(result, Object.assign({ - params: Object.assign(params, { - authenticated: true - }), - authentication - }, Strategy2.result)); - }); + const result = await auth.authenticate(authentication, params, 'first', 'second') + + assert.deepStrictEqual( + result, + Object.assign( + { + params: Object.assign(params, { + authenticated: true + }), + authentication + }, + Strategy2.result + ) + ) + }) it('throws error when allowed and passed strategy does not match', async () => { try { - await auth.authenticate({ - strategy: 'first', - username: 'Dummy' - }, {}, 'second'); - assert.fail('Should never get here'); + await auth.authenticate( + { + strategy: 'first', + username: 'Dummy' + }, + {}, + 'second' + ) + assert.fail('Should never get here') } catch (error: any) { - assert.strictEqual(error.name, 'NotAuthenticated'); - assert.strictEqual(error.message, 'Invalid authentication information (strategy not allowed in authStrategies)'); + assert.strictEqual(error.name, 'NotAuthenticated') + assert.strictEqual( + error.message, + 'Invalid authentication information (strategy not allowed in authStrategies)' + ) } - }); + }) it('throws error when strategy is not set', async () => { try { - await auth.authenticate({ - username: 'Dummy' - }, {}, 'second'); - assert.fail('Should never get here'); + await auth.authenticate( + { + username: 'Dummy' + }, + {}, + 'second' + ) + assert.fail('Should never get here') } catch (error: any) { - assert.strictEqual(error.message, 'Invalid authentication information (no `strategy` set)'); + assert.strictEqual(error.message, 'Invalid authentication information (no `strategy` set)') } - }); - }); - }); + }) + }) + }) describe('parse', () => { - const res = {} as ServerResponse; + const res = {} as ServerResponse it('returns null when no names are given', async () => { - const req = {} as MockRequest; + const req = {} as MockRequest - assert.strictEqual(await auth.parse(req, res), null); - }); + assert.strictEqual(await auth.parse(req, res), null) + }) it('successfully parses a request (first)', async () => { - const req = { isDave: true } as MockRequest; + const req = { isDave: true } as MockRequest - const result = await auth.parse(req, res, 'first', 'second'); + const result = await auth.parse(req, res, 'first', 'second') - assert.deepStrictEqual(result, Strategy1.result); - }); + assert.deepStrictEqual(result, Strategy1.result) + }) it('successfully parses a request (second)', async () => { - const req = { isV2: true } as MockRequest; + const req = { isV2: true } as MockRequest - const result = await auth.parse(req, res, 'first', 'second'); + const result = await auth.parse(req, res, 'first', 'second') - assert.deepStrictEqual(result, Strategy2.result); - }); + assert.deepStrictEqual(result, Strategy2.result) + }) it('null when no success', async () => { - const req = {} as MockRequest; + const req = {} as MockRequest - const result = await auth.parse(req, res, 'first', 'second'); + const result = await auth.parse(req, res, 'first', 'second') - assert.strictEqual(result, null); - }); - }); + assert.strictEqual(result, null) + }) + }) describe('jwt', () => { - const message = 'Some payload'; + const message = 'Some payload' describe('createAccessToken', () => { // it('errors with no payload', () => { @@ -262,132 +311,135 @@ describe('authentication/core', () => { // }); it('with default options', async () => { - const msg = 'Some payload'; + const msg = 'Some payload' - const accessToken = await auth.createAccessToken({ message: msg }); - const decoded = jwt.decode(accessToken); - const settings = auth.configuration.jwtOptions; + const accessToken = await auth.createAccessToken({ message: msg }) + const decoded = jwt.decode(accessToken) + const settings = auth.configuration.jwtOptions if (decoded === null || typeof decoded === 'string') { - throw new Error('Not encoded properly'); + throw new Error('Not encoded properly') } - assert.ok(typeof accessToken === 'string'); - assert.strictEqual(decoded.message, msg, 'Set payload'); - assert.ok(UUID.test(decoded.jti), 'Set `jti` to default UUID'); - assert.strictEqual(decoded.aud, settings.audience); - assert.strictEqual(decoded.iss, settings.issuer); - }); + assert.ok(typeof accessToken === 'string') + assert.strictEqual(decoded.message, msg, 'Set payload') + assert.ok(UUID.test(decoded.jti), 'Set `jti` to default UUID') + assert.strictEqual(decoded.aud, settings.audience) + assert.strictEqual(decoded.iss, settings.issuer) + }) it('with default and overriden options', async () => { const overrides = { issuer: 'someoneelse', audience: 'people', jwtid: 'something' - }; + } - const accessToken = await auth.createAccessToken({ message }, overrides); + const accessToken = await auth.createAccessToken({ message }, overrides) - assert.ok(typeof accessToken === 'string'); + assert.ok(typeof accessToken === 'string') - const decoded = jwt.decode(accessToken); + const decoded = jwt.decode(accessToken) if (decoded === null || typeof decoded === 'string') { - throw new Error('Not encoded properly'); + throw new Error('Not encoded properly') } - assert.strictEqual(decoded.message, message, 'Set payload'); - assert.strictEqual(decoded.jti, 'something'); - assert.strictEqual(decoded.aud, overrides.audience); - assert.strictEqual(decoded.iss, overrides.issuer); - }); + assert.strictEqual(decoded.message, message, 'Set payload') + assert.strictEqual(decoded.jti, 'something') + assert.strictEqual(decoded.aud, overrides.audience) + assert.strictEqual(decoded.iss, overrides.issuer) + }) it('errors with invalid options', async () => { const overrides = { algorithm: 'fdjsklfsndkl' - }; + } try { // @ts-ignore - await auth.createAccessToken({}, overrides); - assert.fail('Should never get here'); + await auth.createAccessToken({}, overrides) + assert.fail('Should never get here') } catch (error: any) { - assert.strictEqual(error.message, '"algorithm" must be a valid string enum value'); + assert.strictEqual(error.message, '"algorithm" must be a valid string enum value') } - }); - }); + }) + }) describe('verifyAccessToken', () => { - let validToken: string; - let expiredToken: string; + let validToken: string + let expiredToken: string beforeEach(async () => { - validToken = await auth.createAccessToken({ message }); - expiredToken = await auth.createAccessToken({}, { - expiresIn: '1ms' - }); - }); + validToken = await auth.createAccessToken({ message }) + expiredToken = await auth.createAccessToken( + {}, + { + expiresIn: '1ms' + } + ) + }) it('returns payload when token is valid', async () => { - const payload = await auth.verifyAccessToken(validToken); + const payload = await auth.verifyAccessToken(validToken) - assert.strictEqual(payload.message, message); - }); + assert.strictEqual(payload.message, message) + }) it('errors when custom algorithm property does not match', async () => { try { await auth.verifyAccessToken(validToken, { - algorithm: [ 'HS512' ] - }); - assert.fail('Should never get here'); + algorithm: ['HS512'] + }) + assert.fail('Should never get here') } catch (error: any) { - assert.strictEqual(error.message, 'invalid algorithm'); + assert.strictEqual(error.message, 'invalid algorithm') } - }); + }) it('errors when algorithms property does not match', async () => { try { await auth.verifyAccessToken(validToken, { - algorithms: [ 'HS512' ] - }); - assert.fail('Should never get here'); + algorithms: ['HS512'] + }) + assert.fail('Should never get here') } catch (error: any) { - assert.strictEqual(error.message, 'invalid algorithm'); + assert.strictEqual(error.message, 'invalid algorithm') } - }); + }) it('errors when secret is different', async () => { try { - await auth.verifyAccessToken(validToken, {}, 'fdjskl'); + await auth.verifyAccessToken(validToken, {}, 'fdjskl') - assert.fail('Should never get here'); + assert.fail('Should never get here') } catch (error: any) { - assert.strictEqual(error.message, 'invalid signature'); + assert.strictEqual(error.message, 'invalid signature') } - }); + }) it('errors when other custom options do not match', async () => { try { - await auth.verifyAccessToken(validToken, { issuer: 'someonelse' }); + await auth.verifyAccessToken(validToken, { issuer: 'someonelse' }) - assert.fail('Should never get here'); + assert.fail('Should never get here') } catch (error: any) { - assert.strictEqual(error.name, 'NotAuthenticated'); - assert.ok(/jwt issuer invalid/.test(error.message)); + assert.strictEqual(error.name, 'NotAuthenticated') + assert.ok(/jwt issuer invalid/.test(error.message)) } - }); + }) it('errors when token is expired', async () => { try { - await auth.verifyAccessToken(expiredToken); - assert.fail('Should never get here'); + await auth.verifyAccessToken(expiredToken) + assert.fail('Should never get here') } catch (error: any) { - assert.strictEqual(error.name, 'NotAuthenticated'); - assert.strictEqual(error.message, 'jwt expired'); - assert.strictEqual(error.data.name, 'TokenExpiredError'); - assert.ok(error.data.expiredAt); + assert.strictEqual(error.name, 'NotAuthenticated') + assert.strictEqual(error.message, 'jwt expired') + assert.strictEqual(error.data.name, 'TokenExpiredError') + assert.ok(error.data.expiredAt) } - }); - }); - }); -}); + }) + }) + }) +}) diff --git a/packages/authentication/test/fixtures.ts b/packages/authentication/test/fixtures.ts index 40c1991f1e..aba18afde3 100644 --- a/packages/authentication/test/fixtures.ts +++ b/packages/authentication/test/fixtures.ts @@ -1,13 +1,13 @@ -import { NotAuthenticated } from '@feathersjs/errors'; -import { Params } from '@feathersjs/feathers'; +import { NotAuthenticated } from '@feathersjs/errors' +import { Params } from '@feathersjs/feathers' -import { AuthenticationRequest } from '../src/core'; -import { IncomingMessage } from 'http'; -import { AuthenticationBaseStrategy } from '../src/strategy'; +import { AuthenticationRequest } from '../src/core' +import { IncomingMessage } from 'http' +import { AuthenticationBaseStrategy } from '../src/strategy' export interface MockRequest extends IncomingMessage { - isDave?: boolean; - isV2?: boolean; + isDave?: boolean + isV2?: boolean } export class Strategy1 extends AuthenticationBaseStrategy { @@ -17,22 +17,22 @@ export class Strategy1 extends AuthenticationBaseStrategy { name: 'Dave' }, authenticated: true - }; + } - async authenticate (authentication: AuthenticationRequest) { + async authenticate(authentication: AuthenticationRequest) { if (authentication.username === 'David' || authentication.both) { - return Strategy1.result; + return { ...Strategy1.result } } - throw new NotAuthenticated('Invalid Dave'); + throw new NotAuthenticated('Invalid Dave') } - async parse (req: MockRequest) { + async parse(req: MockRequest) { if (req.isDave) { - return Strategy1.result; + return { ...Strategy1.result } } - return null; + return null } } @@ -43,23 +43,23 @@ export class Strategy2 extends AuthenticationBaseStrategy { version: 2 }, authenticated: true - }; + } - authenticate (authentication: AuthenticationRequest, params: Params) { - const isV2 = authentication.v2 === true && authentication.password === 'supersecret'; + authenticate(authentication: AuthenticationRequest, params: Params) { + const isV2 = authentication.v2 === true && authentication.password === 'supersecret' if (isV2 || authentication.both) { - return Promise.resolve(Object.assign({ params, authentication }, Strategy2.result)); + return Promise.resolve(Object.assign({ params, authentication }, Strategy2.result)) } - return Promise.reject(new NotAuthenticated('Invalid v2 user')); + return Promise.reject(new NotAuthenticated('Invalid v2 user')) } - async parse (req: MockRequest) { + async parse(req: MockRequest) { if (req.isV2) { - return Strategy2.result; + return Strategy2.result } - return null; + return null } } diff --git a/packages/authentication/test/hooks/authenticate.test.ts b/packages/authentication/test/hooks/authenticate.test.ts index e13debb63c..89b7bad514 100644 --- a/packages/authentication/test/hooks/authenticate.test.ts +++ b/packages/authentication/test/hooks/authenticate.test.ts @@ -1,102 +1,109 @@ -import assert from 'assert'; -import { feathers, Application, Params, ServiceMethods } from '@feathersjs/feathers'; +/* eslint-disable @typescript-eslint/ban-ts-comment */ +import assert from 'assert' +import { feathers, Application, Params, ServiceMethods } from '@feathersjs/feathers' -import { Strategy1, Strategy2 } from '../fixtures'; -import { AuthenticationService, hooks } from '../../src'; +import { Strategy1, Strategy2 } from '../fixtures' +import { AuthenticationService, hooks } from '../../src' -const { authenticate } = hooks; +const { authenticate } = hooks describe('authentication/hooks/authenticate', () => { let app: Application<{ - authentication: AuthenticationService, - 'auth-v2': AuthenticationService, + authentication: AuthenticationService + 'auth-v2': AuthenticationService users: Partial & { id: string } - }>; + }> beforeEach(() => { - app = feathers(); - app.use('authentication', new AuthenticationService(app, 'authentication', { - entity: 'user', - service: 'users', - secret: 'supersecret', - authStrategies: [ 'first' ] - })); - app.use('auth-v2', new AuthenticationService(app, 'auth-v2', { - entity: 'user', - service: 'users', - secret: 'supersecret', - authStrategies: [ 'test' ] - })); + app = feathers() + app.use( + 'authentication', + new AuthenticationService(app, 'authentication', { + entity: 'user', + service: 'users', + secret: 'supersecret', + authStrategies: ['first'] + }) + ) + app.use( + 'auth-v2', + new AuthenticationService(app, 'auth-v2', { + entity: 'user', + service: 'users', + secret: 'supersecret', + authStrategies: ['test'] + }) + ) app.use('users', { id: 'id', - async find () { - return []; + async find() { + return [] }, - async get (_id: string|number, params: Params) { - return params; + async get(_id: string | number, params: Params) { + return params } - }); + }) - const service = app.service('authentication'); + const service = app.service('authentication') - service.register('first', new Strategy1()); - service.register('second', new Strategy2()); + service.register('first', new Strategy1()) + service.register('second', new Strategy2()) - app.service('auth-v2').register('test', new Strategy1()); + app.service('auth-v2').register('test', new Strategy1()) app.service('users').hooks({ get: [authenticate('first', 'second')] - }); + }) - app.service('users').id = 'name'; - app.setup(); - }); + app.service('users').id = 'name' + app.setup() + }) it('throws an error when no strategies are passed', () => { try { // @ts-ignore - authenticate(); - assert.fail('Should never get here'); + authenticate() + assert.fail('Should never get here') } catch (error: any) { - assert.strictEqual(error.message, 'The authenticate hook needs at least one allowed strategy'); + assert.strictEqual(error.message, 'The authenticate hook needs at least one allowed strategy') } - }); + }) it('throws an error when not a before hook', async () => { - const users = app.service('users'); + const users = app.service('users') users.hooks({ after: { - all: [ authenticate('first') ] + all: [authenticate('first')] } - }); + }) try { - await users.find(); - assert.fail('Should never get here'); + await users.find() + assert.fail('Should never get here') } catch (error: any) { - assert.strictEqual(error.name, 'NotAuthenticated'); - assert.strictEqual(error.message, 'The authenticate hook must be used as a before hook'); + assert.strictEqual(error.name, 'NotAuthenticated') + assert.strictEqual(error.message, 'The authenticate hook must be used as a before hook') } - }); + }) it('throws an error if authentication service is gone', async () => { - delete app.services.authentication; + delete app.services.authentication try { await app.service('users').get(1, { authentication: { some: 'thing' } - }); - assert.fail('Should never get here'); + }) + assert.fail('Should never get here') } catch (error: any) { - assert.strictEqual(error.name, 'NotAuthenticated'); - assert.strictEqual(error.message, 'Could not find a valid authentication service'); + assert.strictEqual(error.name, 'NotAuthenticated') + assert.strictEqual(error.message, 'Could not find a valid authentication service') } - }); + }) it('authenticates with first strategy, merges params', async () => { const params = { @@ -104,35 +111,35 @@ describe('authentication/hooks/authenticate', () => { strategy: 'first', username: 'David' } - }; + } - const result = await app.service('users').get(1, params); + const result = await app.service('users').get(1, params) - assert.deepStrictEqual(result, Object.assign({}, params, Strategy1.result)); - }); + assert.deepStrictEqual(result, Object.assign({}, params, Strategy1.result)) + }) it('authenticates with first strategy, keeps references alive (#1629)', async () => { - const connection = {}; + const connection = {} const params = { connection, authentication: { strategy: 'first', username: 'David' } - }; + } app.service('users').hooks({ after: { - get: context => { - context.result.params = context.params; + get: (context) => { + context.result.params = context.params } } - }); + }) - const result = await app.service('users').get(1, params); + const result = await app.service('users').get(1, params) - assert.ok(result.params.connection === connection); - }); + assert.ok(result.params.connection === connection) + }) it('authenticates with different authentication service', async () => { const params = { @@ -140,21 +147,23 @@ describe('authentication/hooks/authenticate', () => { strategy: 'test', username: 'David' } - }; + } app.service('users').hooks({ before: { - find: [authenticate({ - service: 'auth-v2', - strategies: [ 'test' ] - })] + find: [ + authenticate({ + service: 'auth-v2', + strategies: ['test'] + }) + ] } - }); + }) - const result = await app.service('users').find(params); + const result = await app.service('users').find(params) - assert.deepStrictEqual(result, []); - }); + assert.deepStrictEqual(result, []) + }) it('authenticates with second strategy', async () => { const params = { @@ -163,21 +172,27 @@ describe('authentication/hooks/authenticate', () => { v2: true, password: 'supersecret' } - }; + } - const result = await app.service('users').get(1, params); + const result = await app.service('users').get(1, params) - assert.deepStrictEqual(result, Object.assign({ - authentication: params.authentication, - params: { authenticated: true } - }, Strategy2.result)); - }); + assert.deepStrictEqual( + result, + Object.assign( + { + authentication: params.authentication, + params: { authenticated: true } + }, + Strategy2.result + ) + ) + }) it('passes for internal calls without authentication', async () => { - const result = await app.service('users').get(1); + const result = await app.service('users').get(1) - assert.deepStrictEqual(result, {}); - }); + assert.deepStrictEqual(result, {}) + }) it('fails for invalid params.authentication', async () => { try { @@ -186,55 +201,56 @@ describe('authentication/hooks/authenticate', () => { strategy: 'first', some: 'thing' } - }); - assert.fail('Should never get here'); + }) + assert.fail('Should never get here') } catch (error: any) { - assert.strictEqual(error.name, 'NotAuthenticated'); - assert.strictEqual(error.message, 'Invalid Dave'); + assert.strictEqual(error.name, 'NotAuthenticated') + assert.strictEqual(error.message, 'Invalid Dave') } - }); + }) it('fails for external calls without authentication', async () => { try { await app.service('users').get(1, { provider: 'rest' - }); - assert.fail('Should never get here'); + }) + assert.fail('Should never get here') } catch (error: any) { - assert.strictEqual(error.name, 'NotAuthenticated'); - assert.strictEqual(error.message, 'Not authenticated'); + assert.strictEqual(error.name, 'NotAuthenticated') + assert.strictEqual(error.message, 'Not authenticated') } - }); + }) it('passes with authenticated: true but external call', async () => { const params = { provider: 'rest', authenticated: true - }; - const result = await app.service('users').get(1, params); + } + const result = await app.service('users').get(1, params) - assert.deepStrictEqual(result, params); - }); + assert.deepStrictEqual(result, params) + }) it('errors when used on the authentication service', async () => { - const auth = app.service('authentication'); + const auth = app.service('authentication') auth.hooks({ before: { create: authenticate('first') } - }); + }) try { await auth.create({ strategy: 'first', username: 'David' - }); - assert.fail('Should never get here'); + }) + assert.fail('Should never get here') } catch (error: any) { - assert.strictEqual(error.message, + assert.strictEqual( + error.message, 'The authenticate hook does not need to be used on the authentication service' - ); + ) } - }); -}); + }) +}) diff --git a/packages/authentication/test/hooks/event.test.ts b/packages/authentication/test/hooks/event.test.ts index 817be37102..e602febdff 100644 --- a/packages/authentication/test/hooks/event.test.ts +++ b/packages/authentication/test/hooks/event.test.ts @@ -1,83 +1,83 @@ -import assert from 'assert'; -import { feathers, Params, HookContext } from '@feathersjs/feathers'; +import assert from 'assert' +import { feathers, HookContext } from '@feathersjs/feathers' -import hook from '../../src/hooks/event'; -import { AuthenticationRequest, AuthenticationResult } from '../../src/core'; +import hook from '../../src/hooks/event' +import { AuthenticationParams, AuthenticationRequest, AuthenticationResult } from '../../src/core' describe('authentication/hooks/events', () => { - const app = feathers().use('/authentication', { - async create (data: AuthenticationRequest) { - return data; + const app = feathers().use('authentication', { + async create(data: AuthenticationRequest) { + return data }, - async remove (id: string) { - return { id }; + async remove(id: string) { + return { id } } - }); + }) - const service = app.service('authentication'); + const service = app.service('authentication') service.hooks({ - create: [ hook('login') ], - remove: [ hook('logout') ] - }); + create: [hook('login')], + remove: [hook('logout')] + }) - it('login', done => { + it('login', (done) => { const data = { message: 'test' - }; + } - app.once('login', (result: AuthenticationResult, params: Params, context: HookContext) => { + app.once('login', (result: AuthenticationResult, params: AuthenticationParams, context: HookContext) => { try { - assert.deepStrictEqual(result, data); - assert.ok(params.testParam); - assert.ok(context.method, 'create'); - done(); + assert.deepStrictEqual(result, data) + assert.ok(params.testParam) + assert.ok(context.method, 'create') + done() } catch (error: any) { - done(error); + done(error) } - }); + }) service.create(data, { testParam: true, provider: 'test' - }); - }); + } as any) + }) - it('logout', done => { - app.once('logout', (result: AuthenticationResult, params: Params, context: HookContext) => { + it('logout', (done) => { + app.once('logout', (result: AuthenticationResult, params: AuthenticationParams, context: HookContext) => { try { assert.deepStrictEqual(result, { id: 'test' - }); - assert.ok(params.testParam); - assert.ok(context.method, 'remove'); - done(); + }) + assert.ok(params.testParam) + assert.ok(context.method, 'remove') + done() } catch (error: any) { - done(error); + done(error) } - }); + }) service.remove('test', { testParam: true, provider: 'test' - }); - }); + } as any) + }) - it('does nothing when provider is not set', done => { + it('does nothing when provider is not set', (done) => { const handler = () => { - done(new Error('Should never get here')); - }; + done(new Error('Should never get here')) + } - app.on('logout', handler); + app.on('logout', handler) service.once('removed', (result: AuthenticationResult) => { - app.removeListener('logout', handler); + app.removeListener('logout', handler) assert.deepStrictEqual(result, { id: 'test' - }); - done(); - }); + }) + done() + }) - service.remove('test'); - }); -}); + service.remove('test') + }) +}) diff --git a/packages/authentication/test/jwt.test.ts b/packages/authentication/test/jwt.test.ts index e1d23bb7ee..526cbe02b4 100644 --- a/packages/authentication/test/jwt.test.ts +++ b/packages/authentication/test/jwt.test.ts @@ -1,195 +1,244 @@ -import assert from 'assert'; -import merge from 'lodash/merge'; -import { feathers, Application, Service } from '@feathersjs/feathers'; -import { memory } from '@feathersjs/memory'; +import assert from 'assert' +import merge from 'lodash/merge' +import { feathers, Application, Service } from '@feathersjs/feathers' +import { memory } from '@feathersjs/memory' +import { getDispatch, resolve, resolveDispatch } from '@feathersjs/schema' -import { AuthenticationService, JWTStrategy, hooks } from '../src'; -import { ServerResponse } from 'http'; -import { MockRequest } from './fixtures'; +import { AuthenticationService, JWTStrategy, hooks } from '../src' +import { ServerResponse } from 'http' +import { MockRequest } from './fixtures' -const { authenticate } = hooks; +const { authenticate } = hooks describe('authentication/jwt', () => { let app: Application<{ - authentication: AuthenticationService, - users: Partial, + authentication: AuthenticationService + users: Partial protected: Partial - }>; - let user: any; - let accessToken: string; - let payload: any; + }> + let user: any + let accessToken: string + let payload: any + + const userDispatchResolver = resolve({ + converter: async () => { + return { + dispatch: true, + message: 'Hello world' + } + }, + properties: {} + }) beforeEach(async () => { - app = feathers(); + app = feathers() const authService = new AuthenticationService(app, 'authentication', { entity: 'user', service: 'users', secret: 'supersecret', - authStrategies: [ 'jwt' ] - }); + authStrategies: ['jwt'] + }) - authService.register('jwt', new JWTStrategy()); + authService.register('jwt', new JWTStrategy()) - app.use('users', memory()); + app.use('users', memory()) app.use('protected', { - async get (id, params) { + async get(id, params) { return { - id, params - }; + id, + params + } } - }); - app.use('authentication', authService); + }) + app.use('authentication', authService) - const service = app.service('authentication'); + const service = app.service('authentication') app.service('protected').hooks({ before: { - all: [ authenticate('jwt') ] + all: [authenticate('jwt')] } - }); + }) app.service('users').hooks({ + around: { + all: [resolveDispatch(userDispatchResolver)] + }, after: { - get: [context => { - if (context.params.provider) { - context.result.isExternal = true; - } + get: [ + (context) => { + if (context.params.provider) { + context.result.isExternal = true + } - return context; - }] + return context + } + ] } - }); + }) user = await app.service('users').create({ name: 'David' - }); + }) - accessToken = await service.createAccessToken({}, { - subject: `${user.id}` - }); + accessToken = await service.createAccessToken( + {}, + { + subject: `${user.id}` + } + ) - payload = await service.verifyAccessToken(accessToken); - app.setup(); - }); + payload = await service.verifyAccessToken(accessToken) + app.setup() + }) it('getEntity', async () => { - const [ strategy ] = app.service('authentication').getStrategies('jwt') as JWTStrategy[]; + const [strategy] = app.service('authentication').getStrategies('jwt') as JWTStrategy[] let entity = await strategy.getEntity(user.id, { query: { name: 'Dave' } - }); + }) - assert.deepStrictEqual(entity, user); + assert.deepStrictEqual(entity, user) entity = await strategy.getEntity(user.id, { provider: 'rest' - }); + }) assert.deepStrictEqual(entity, { ...user, isExternal: true - }); - }); + }) + }) describe('handleConnection', () => { it('adds authentication information on create', async () => { - const connection: any = {}; + const connection: any = {} - await app.service('authentication').create({ + await app.service('authentication').create( + { + strategy: 'jwt', + accessToken + }, + { connection } + ) + + assert.deepStrictEqual(connection.user, user) + assert.deepStrictEqual(connection.authentication, { strategy: 'jwt', accessToken - }, { connection }); + }) + }) - assert.deepStrictEqual(connection.user, user); - assert.deepStrictEqual(connection.authentication, { + it('resolves safe dispatch data in authentication result', async () => { + const authResult = await app.service('authentication').create({ strategy: 'jwt', accessToken - }); - }); + }) + + const dispatch = getDispatch(authResult) + + assert.deepStrictEqual(dispatch.user, { dispatch: true, message: 'Hello world' }) + }) it('sends disconnect event when connection token expires and removes all connection information', async () => { - const connection: any = {}; - const token: string = await app.service('authentication').createAccessToken({}, { - subject: `${user.id}`, - expiresIn: '1s' - }); + const connection: any = {} + const token: string = await app.service('authentication').createAccessToken( + {}, + { + subject: `${user.id}`, + expiresIn: '1s' + } + ) - const result = await app.service('authentication').create({ - strategy: 'jwt', - accessToken: token - }, { connection }); + const result = await app.service('authentication').create( + { + strategy: 'jwt', + accessToken: token + }, + { connection } + ) - assert.ok(connection.authentication); + assert.ok(connection.authentication) - assert.strictEqual(result.accessToken, token); + assert.strictEqual(result.accessToken, token) - const disconnection = await new Promise(resolve => app.once('disconnect', resolve)); + const disconnection = await new Promise((resolve) => app.once('disconnect', resolve)) - assert.strictEqual(disconnection, connection); + assert.strictEqual(disconnection, connection) - assert.ok(!connection.authentication); - assert.ok(!connection.user); - assert.strictEqual(Object.keys(connection).length, 0); - }); + assert.ok(!connection.authentication) + assert.ok(!connection.user) + assert.strictEqual(Object.keys(connection).length, 0) + }) it('deletes authentication information on remove', async () => { - const connection: any = {}; + const connection: any = {} - await app.service('authentication').create({ - strategy: 'jwt', - accessToken - }, { connection }); + await app.service('authentication').create( + { + strategy: 'jwt', + accessToken + }, + { connection } + ) - assert.ok(connection.authentication); + assert.ok(connection.authentication) await app.service('authentication').remove(null, { authentication: connection.authentication, connection - }); + }) - assert.ok(!connection.authentication); - assert.ok(!connection.user); - }); + assert.ok(!connection.authentication) + assert.ok(!connection.user) + }) it('does not remove if accessToken does not match', async () => { - const connection: any = {}; + const connection: any = {} - await app.service('authentication').create({ - strategy: 'jwt', - accessToken - }, { connection }); + await app.service('authentication').create( + { + strategy: 'jwt', + accessToken + }, + { connection } + ) - assert.ok(connection.authentication); + assert.ok(connection.authentication) await app.service('authentication').remove(null, { authentication: { strategy: 'jwt', - accessToken: await app.service('authentication').createAccessToken({}, { - subject: `${user.id}` - }) + accessToken: await app.service('authentication').createAccessToken( + {}, + { + subject: `${user.id}` + } + ) }, connection - }); + }) - assert.ok(connection.authentication); - }); - }); + assert.ok(connection.authentication) + }) + }) describe('with authenticate hook', () => { it('fails for protected service and external call when not set', async () => { try { await app.service('protected').get('test', { provider: 'rest' - }); - assert.fail('Should never get here'); + }) + assert.fail('Should never get here') } catch (error: any) { - assert.strictEqual(error.name, 'NotAuthenticated'); - assert.strictEqual(error.message, 'Not authenticated'); + assert.strictEqual(error.name, 'NotAuthenticated') + assert.strictEqual(error.message, 'Not authenticated') } - }); + }) it('fails for protected service and external call when not strategy', async () => { try { @@ -198,27 +247,31 @@ describe('authentication/jwt', () => { authentication: { username: 'Dave' } - }); - assert.fail('Should never get here'); + }) + assert.fail('Should never get here') } catch (error: any) { - assert.strictEqual(error.name, 'NotAuthenticated'); - assert.strictEqual(error.message, 'Invalid authentication information (no `strategy` set)'); + assert.strictEqual(error.name, 'NotAuthenticated') + assert.strictEqual(error.message, 'Invalid authentication information (no `strategy` set)') } - }); + }) it('fails when entity service was not found', async () => { - delete app.services.users; - - await assert.rejects(() => app.service('protected').get('test', { - provider: 'rest', - authentication: { - strategy: 'jwt', - accessToken + delete app.services.users + + await assert.rejects( + () => + app.service('protected').get('test', { + provider: 'rest', + authentication: { + strategy: 'jwt', + accessToken + } + }), + { + message: "Can not find service 'users'" } - }), { - message: 'Can not find service \'users\'' - }); - }); + ) + }) it('fails when accessToken is not set', async () => { try { @@ -227,13 +280,13 @@ describe('authentication/jwt', () => { authentication: { strategy: 'jwt' } - }); - assert.fail('Should never get here'); + }) + assert.fail('Should never get here') } catch (error: any) { - assert.strictEqual(error.name, 'NotAuthenticated'); - assert.strictEqual(error.message, 'No access token'); + assert.strictEqual(error.name, 'NotAuthenticated') + assert.strictEqual(error.message, 'No access token') } - }); + }) it('passes when authentication is set and merges params', async () => { const params = { @@ -242,12 +295,12 @@ describe('authentication/jwt', () => { strategy: 'jwt', accessToken } - }; + } - const result = await app.service('protected').get('test', params); + const result = await app.service('protected').get('test', params) - assert.strictEqual(Object.keys(result.params).length, 4); - assert.ok(!result.params.accessToken, 'Did not merge accessToken'); + assert.strictEqual(Object.keys(result.params).length, 4) + assert.ok(!result.params.accessToken, 'Did not merge accessToken') assert.deepStrictEqual(result, { id: 'test', params: merge({}, params, { @@ -255,8 +308,8 @@ describe('authentication/jwt', () => { authentication: { payload }, authenticated: true }) - }); - }); + }) + }) it('works with entity set to null', async () => { const params = { @@ -265,111 +318,114 @@ describe('authentication/jwt', () => { strategy: 'jwt', accessToken } - }; + } - app.get('authentication').entity = null; + app.get('authentication').entity = null - const result = await app.service('protected').get('test', params); + const result = await app.service('protected').get('test', params) - assert.strictEqual(Object.keys(result.params).length, 3); - assert.ok(!result.params.accessToken, 'Did not merge accessToken'); + assert.strictEqual(Object.keys(result.params).length, 3) + assert.ok(!result.params.accessToken, 'Did not merge accessToken') assert.deepStrictEqual(result, { id: 'test', params: merge({}, params, { authentication: { payload }, authenticated: true }) - }); - }); - }); + }) + }) + }) describe('on authentication service', () => { it('authenticates but does not return a new accessToken', async () => { const authResult = await app.service('authentication').create({ strategy: 'jwt', accessToken - }); + }) - assert.strictEqual(authResult.accessToken, accessToken); - assert.deepStrictEqual(authResult.user, user); - assert.deepStrictEqual(authResult.authentication.payload, payload); - }); + assert.strictEqual(authResult.accessToken, accessToken) + assert.deepStrictEqual(authResult.user, user) + assert.deepStrictEqual(authResult.authentication.payload, payload) + }) it('errors when trying to set invalid option', () => { app.get('authentication').otherJwt = { expiresIn: 'something' - }; + } try { - app.service('authentication').register('otherJwt', new JWTStrategy()); - assert.fail('Should never get here'); + app.service('authentication').register('otherJwt', new JWTStrategy()) + assert.fail('Should never get here') } catch (error: any) { - assert.strictEqual(error.message, 'Invalid JwtStrategy option \'authentication.otherJwt.expiresIn\'. Did you mean to set it in \'authentication.jwtOptions\'?'); + assert.strictEqual( + error.message, + "Invalid JwtStrategy option 'authentication.otherJwt.expiresIn'. Did you mean to set it in 'authentication.jwtOptions'?" + ) } - }); + }) it('errors when `header` option is an object`', () => { app.get('authentication').otherJwt = { header: { message: 'This is wrong' } - }; + } assert.throws(() => app.service('authentication').register('otherJwt', new JWTStrategy()), { - message: 'The \'header\' option for the otherJwt strategy must be a string' - }); - }); - }); + message: "The 'header' option for the otherJwt strategy must be a string" + }) + }) + }) describe('parse', () => { - const res = {} as ServerResponse; + const res = {} as ServerResponse it('returns null when header not set', async () => { - const req = {} as MockRequest; + const req = {} as MockRequest - const result = await app.service('authentication').parse(req, res, 'jwt'); + const result = await app.service('authentication').parse(req, res, 'jwt') - assert.strictEqual(result, null); - }); + assert.strictEqual(result, null) + }) it('parses plain Authorization header', async () => { const req = { headers: { authorization: accessToken } - } as MockRequest; + } as MockRequest - const result = await app.service('authentication').parse(req, res, 'jwt'); + const result = await app.service('authentication').parse(req, res, 'jwt') assert.deepStrictEqual(result, { strategy: 'jwt', accessToken - }); - }); + }) + }) it('parses Authorization header with Bearer scheme', async () => { const req = { headers: { authorization: ` Bearer ${accessToken} ` } - } as MockRequest; + } as MockRequest - const result = await app.service('authentication').parse(req, res, 'jwt'); + const result = await app.service('authentication').parse(req, res, 'jwt') assert.deepStrictEqual(result, { strategy: 'jwt', accessToken - }); - }); + }) + }) it('return null when scheme does not match', async () => { const req = { headers: { authorization: ' Basic something' } - } as MockRequest; + } as MockRequest - const result = await app.service('authentication').parse(req, res, 'jwt'); + const result = await app.service('authentication').parse(req, res, 'jwt') - assert.strictEqual(result, null); - }); - }); -}); + assert.strictEqual(result, null) + }) + }) +}) diff --git a/packages/authentication/test/service.test.ts b/packages/authentication/test/service.test.ts index e5ed22d817..3594822bba 100644 --- a/packages/authentication/test/service.test.ts +++ b/packages/authentication/test/service.test.ts @@ -1,176 +1,192 @@ -import assert from 'assert'; -import omit from 'lodash/omit'; -import jwt from 'jsonwebtoken'; -import { feathers, Application } from '@feathersjs/feathers'; -import { memory, Service as MemoryService } from '@feathersjs/memory'; +/* eslint-disable @typescript-eslint/ban-ts-comment */ +import assert from 'assert' +import omit from 'lodash/omit' +import jwt from 'jsonwebtoken' +import { feathers, Application } from '@feathersjs/feathers' +import { memory, MemoryService } from '@feathersjs/memory' -import defaultOptions from '../src/options'; -import { AuthenticationService } from '../src'; +import { defaultOptions } from '../src/options' +import { AuthenticationService } from '../src' -import { Strategy1 } from './fixtures'; +import { Strategy1 } from './fixtures' -const UUID = /[0-9a-f]{8}-[0-9a-f]{4}-[0-9a-f]{4}-[0-9a-f]{4}-[0-9a-f]{12}/; +const UUID = /[0-9a-f]{8}-[0-9a-f]{4}-[0-9a-f]{4}-[0-9a-f]{4}-[0-9a-f]{12}/ describe('authentication/service', () => { - const message = 'Some payload'; + const message = 'Some payload' let app: Application<{ - authentication: AuthenticationService, + authentication: AuthenticationService users: MemoryService - }>; + }> beforeEach(() => { - app = feathers(); - app.use('authentication', new AuthenticationService(app, 'authentication', { - entity: 'user', - service: 'users', - secret: 'supersecret', - authStrategies: [ 'first' ] - })); - app.use('users', memory()); - - app.service('authentication').register('first', new Strategy1()); - }); + app = feathers() + app.use( + 'authentication', + new AuthenticationService(app, 'authentication', { + entity: 'user', + service: 'users', + secret: 'supersecret', + authStrategies: ['first'] + }) + ) + app.use('users', memory()) + + app.service('authentication').register('first', new Strategy1()) + }) it('settings returns authentication options', () => { - assert.deepStrictEqual(app.service('authentication').configuration, Object.assign({}, defaultOptions, app.get('authentication'))); - }); + assert.deepStrictEqual( + app.service('authentication').configuration, + Object.assign({}, defaultOptions, app.get('authentication')) + ) + }) it('app.defaultAuthentication()', () => { - assert.strictEqual(app.defaultAuthentication(), app.service('authentication')); + assert.strictEqual(app.defaultAuthentication(), app.service('authentication')) assert.throws(() => app.defaultAuthentication('dummy'), { - message: 'Can not find service \'dummy\'' - }); - }); + message: "Can not find service 'dummy'" + }) + }) describe('create', () => { it('creates a valid accessToken and includes strategy result', async () => { - const service = app.service('authentication'); + const service = app.service('authentication') const result = await service.create({ strategy: 'first', username: 'David' - }); + }) - const settings = service.configuration.jwtOptions; - const decoded = jwt.decode(result.accessToken); + const settings = service.configuration.jwtOptions + const decoded = jwt.decode(result.accessToken) if (typeof decoded === 'string') { - throw new Error('Unexpected decoded JWT type'); + throw new Error('Unexpected decoded JWT type') } - assert.ok(result.accessToken); - assert.deepStrictEqual(omit(result, 'accessToken', 'authentication'), Strategy1.result); - assert.deepStrictEqual(result.authentication.payload, decoded); - assert.ok(UUID.test(decoded.jti), 'Set `jti` to default UUID'); - assert.strictEqual(decoded.aud, settings.audience); - assert.strictEqual(decoded.iss, settings.issuer); - }); + assert.ok(result.accessToken) + assert.deepStrictEqual(omit(result, 'accessToken', 'authentication'), Strategy1.result) + assert.deepStrictEqual(result.authentication.payload, decoded) + assert.ok(UUID.test(decoded.jti), 'Set `jti` to default UUID') + assert.strictEqual(decoded.aud, settings.audience) + assert.strictEqual(decoded.iss, settings.issuer) + }) it('fails when strategy fails', async () => { try { await app.service('authentication').create({ strategy: 'first', username: 'Dave' - }); - assert.fail('Should never get here'); + }) + assert.fail('Should never get here') } catch (error: any) { - assert.strictEqual(error.name, 'NotAuthenticated'); - assert.strictEqual(error.message, 'Invalid Dave'); + assert.strictEqual(error.name, 'NotAuthenticated') + assert.strictEqual(error.message, 'Invalid Dave') } - }); + }) it('creates a valid accessToken with strategy and params.payload', async () => { - const result = await app.service('authentication').create({ - strategy: 'first', - username: 'David' - }, { - payload: { message } - }); + const result = await app.service('authentication').create( + { + strategy: 'first', + username: 'David' + }, + { + payload: { message } + } + ) - const decoded = jwt.decode(result.accessToken); + const decoded = jwt.decode(result.accessToken) if (typeof decoded === 'string') { - throw new Error('Unexpected decoded JWT type'); + throw new Error('Unexpected decoded JWT type') } - assert.strictEqual(decoded.message, message); - }); + assert.strictEqual(decoded.message, message) + }) it('sets the subject authResult[entity][entityService.id]', async () => { const { accessToken } = await app.service('authentication').create({ strategy: 'first', username: 'David' - }); + }) - const decoded = jwt.decode(accessToken); + const decoded = jwt.decode(accessToken) - assert.strictEqual(decoded.sub, Strategy1.result.user.id.toString()); - }); + assert.strictEqual(decoded.sub, Strategy1.result.user.id.toString()) + }) it('sets the subject authResult[entity][entityId]', async () => { - app.get('authentication').entityId = 'name'; + app.get('authentication').entityId = 'name' const { accessToken } = await app.service('authentication').create({ strategy: 'first', username: 'David' - }); + }) - const decoded = jwt.decode(accessToken); + const decoded = jwt.decode(accessToken) - assert.strictEqual(decoded.sub, Strategy1.result.user.name.toString()); - }); + assert.strictEqual(decoded.sub, Strategy1.result.user.name.toString()) + }) it('does not override the subject if already set', async () => { - const subject = 'Davester'; + const subject = 'Davester' - const { accessToken } = await app.service('authentication').create({ - strategy: 'first', - username: 'David' - }, { - jwt: { subject } - }); + const { accessToken } = await app.service('authentication').create( + { + strategy: 'first', + username: 'David' + }, + { + jwt: { subject } + } + ) - const decoded = jwt.decode(accessToken); + const decoded = jwt.decode(accessToken) - assert.strictEqual(decoded.sub, subject); - }); + assert.strictEqual(decoded.sub, subject) + }) it('errors when subject can not be found', async () => { // @ts-ignore - app.service('users').options.id = 'somethingElse'; + app.service('users').options.id = 'somethingElse' try { await app.service('authentication').create({ strategy: 'first', username: 'David' - }); - assert.fail('Should never get here'); + }) + assert.fail('Should never get here') } catch (error: any) { - assert.strictEqual(error.name, 'NotAuthenticated'); - assert.strictEqual(error.message, 'Can not set subject from user.somethingElse'); + assert.strictEqual(error.name, 'NotAuthenticated') + assert.strictEqual(error.message, 'Can not set subject from user.somethingElse') } - }); + }) it('errors when no allowed strategies are set', async () => { - const service = app.service('authentication'); - const configuration = service.configuration; + const service = app.service('authentication') + const configuration = service.configuration - delete configuration.authStrategies; + delete configuration.authStrategies - app.set('authentication', configuration); + app.set('authentication', configuration) try { await service.create({ strategy: 'first', username: 'Dave' - }); - assert.fail('Should never get here'); + }) + assert.fail('Should never get here') } catch (error: any) { - assert.strictEqual(error.name, 'NotAuthenticated'); - assert.strictEqual(error.message, 'No authentication strategies allowed for creating a JWT (`authStrategies`)'); + assert.strictEqual(error.name, 'NotAuthenticated') + assert.strictEqual( + error.message, + 'No authentication strategies allowed for creating a JWT (`authStrategies`)' + ) } - }); - }); + }) + }) describe('remove', () => { it('can remove with authentication strategy set', async () => { @@ -179,10 +195,10 @@ describe('authentication/service', () => { strategy: 'first', username: 'David' } - }); + }) - assert.deepStrictEqual(authResult, Strategy1.result); - }); + assert.deepStrictEqual(authResult, Strategy1.result) + }) it('passes when id is set and matches accessToken', async () => { const authResult = await app.service('authentication').remove('test', { @@ -191,106 +207,116 @@ describe('authentication/service', () => { username: 'David', accessToken: 'test' } - }); - - assert.deepStrictEqual(authResult, Strategy1.result); - }); - - it('passes when id is set and does not match accessToken', async () => { - try { - await app.service('authentication').remove('test', { - authentication: { - strategy: 'first', - username: 'David', - accessToken: 'testing' - } - }); - assert.fail('Should never get here'); - } catch (error: any) { - assert.strictEqual(error.name, 'NotAuthenticated'); - assert.strictEqual(error.message, 'Invalid access token'); - } - }); + }) + + assert.deepStrictEqual(authResult, Strategy1.result) + }) + + it('fails when id is set and does not match accessToken', async () => { + await assert.rejects( + () => + app.service('authentication').remove('test', { + authentication: { + strategy: 'first', + username: 'David', + accessToken: 'testing' + } + }), + { + name: 'NotAuthenticated', + message: 'Invalid access token' + } + ) + }) it('errors when trying to remove with nothing', async () => { try { - await app.service('authentication').remove(null); - assert.fail('Should never get here'); + await app.service('authentication').remove(null) + assert.fail('Should never get here') } catch (error: any) { - assert.strictEqual(error.message, 'Invalid authentication information (no `strategy` set)'); + assert.strictEqual(error.message, 'Invalid authentication information (no `strategy` set)') } - }); - }); + }) + }) describe('setup', () => { it('errors when there is no secret', async () => { - delete app.get('authentication').secret; + delete app.get('authentication').secret await assert.rejects(() => app.setup(), { - message: 'A \'secret\' must be provided in your authentication configuration' - }); - }); + message: "A 'secret' must be provided in your authentication configuration" + }) + }) it('throws an error if service name is not set', async () => { - const otherApp = feathers(); + const otherApp = feathers() - otherApp.use('/authentication', new AuthenticationService(otherApp, 'authentication', { - secret: 'supersecret', - authStrategies: [ 'first' ] - })); + otherApp.use( + '/authentication', + new AuthenticationService(otherApp, 'authentication', { + secret: 'supersecret', + authStrategies: ['first'] + }) + ) await assert.rejects(() => otherApp.setup(), { - message: 'The \'service\' option is not set in the authentication configuration' - }); - }); + message: "The 'service' option is not set in the authentication configuration" + }) + }) it('throws an error if entity service does not exist', async () => { - const otherApp = feathers(); - - otherApp.use('/authentication', new AuthenticationService(otherApp, 'authentication', { - entity: 'user', - service: 'users', - secret: 'supersecret', - authStrategies: [ 'first' ] - })); + const otherApp = feathers() + + otherApp.use( + '/authentication', + new AuthenticationService(otherApp, 'authentication', { + entity: 'user', + service: 'users', + secret: 'supersecret', + authStrategies: ['first'] + }) + ) await assert.rejects(() => otherApp.setup(), { - message: 'Can not find service \'users\'' - }); - }); + message: "Can not find service 'users'" + }) + }) it('throws an error if entity service exists but has no `id`', async () => { - const otherApp = feathers(); - - otherApp.use('/authentication', new AuthenticationService(otherApp, 'authentication', { - entity: 'user', - service: 'users', - secret: 'supersecret', - strategies: [ 'first' ] - })); + const otherApp = feathers() + + otherApp.use( + '/authentication', + new AuthenticationService(otherApp, 'authentication', { + entity: 'user', + service: 'users', + secret: 'supersecret', + strategies: ['first'] + }) + ) otherApp.use('/users', { - async get () { - return {}; + async get() { + return {} } - }); + }) await assert.rejects(() => otherApp.setup(), { - message: 'The \'users\' service does not have an \'id\' property and no \'entityId\' option is set.' - }); - }); + message: "The 'users' service does not have an 'id' property and no 'entityId' option is set." + }) + }) it('passes when entity service exists and `entityId` property is set', () => { - app.get('authentication').entityId = 'id'; - app.use('users', memory()); + app.get('authentication').entityId = 'id' + app.use('users', memory()) - app.setup(); - }); + app.setup() + }) it('does nothing when `entity` is explicitly `null`', () => { - app.get('authentication').entity = null; + app.get('authentication').entity = null - app.setup(); - }); - }); -}); + app.setup() + }) + }) +}) diff --git a/packages/cli/CHANGELOG.md b/packages/cli/CHANGELOG.md new file mode 100644 index 0000000000..eee586169f --- /dev/null +++ b/packages/cli/CHANGELOG.md @@ -0,0 +1,72 @@ +# Change Log + +All notable changes to this project will be documented in this file. +See [Conventional Commits](https://conventionalcommits.org) for commit guidelines. + +# [5.0.0-pre.31](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.30...v5.0.0-pre.31) (2022-10-12) + +### Features + +- **cli:** Generate full client test suite and improve typed client ([#2788](https://github.com/feathersjs/feathers/issues/2788)) ([57119b6](https://github.com/feathersjs/feathers/commit/57119b6bb2797f7297cf054268a248c093ecd538)) +- **cli:** Improve generated schema definitions ([#2783](https://github.com/feathersjs/feathers/issues/2783)) ([474a9fd](https://github.com/feathersjs/feathers/commit/474a9fda2107e9bcf357746320a8e00cda8182b6)) + +# [5.0.0-pre.30](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.29...v5.0.0-pre.30) (2022-10-07) + +### Bug Fixes + +- **core:** Ensure setup and teardown can be overriden and maintain hook functionality ([#2779](https://github.com/feathersjs/feathers/issues/2779)) ([ab580cb](https://github.com/feathersjs/feathers/commit/ab580cbcaa68d19144d86798c13bf564f9d424a6)) + +### Features + +- **cli:** Add ability to `npm init feathers` ([#2755](https://github.com/feathersjs/feathers/issues/2755)) ([d734931](https://github.com/feathersjs/feathers/commit/d734931ffd4f983a05d9e771ce0e43b696c2bc0e)) +- **cli:** Improve CLI interface ([#2753](https://github.com/feathersjs/feathers/issues/2753)) ([c7e1b7e](https://github.com/feathersjs/feathers/commit/c7e1b7e80aacb84441908c3d73512d9cf7557f7e)) +- **core:** Allow to unregister services at runtime ([#2756](https://github.com/feathersjs/feathers/issues/2756)) ([d16601f](https://github.com/feathersjs/feathers/commit/d16601f2277dca5357866ffdefba2a611f6dc7fa)) +- **schema:** Make schemas validation library independent and add TypeBox support ([#2772](https://github.com/feathersjs/feathers/issues/2772)) ([44172d9](https://github.com/feathersjs/feathers/commit/44172d99b566d11d9ceda04f1d0bf72b6d05ce76)) + +# [5.0.0-pre.29](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.28...v5.0.0-pre.29) (2022-09-16) + +### Features + +- Add CORS support to oAuth, Express, Koa and generated application ([#2744](https://github.com/feathersjs/feathers/issues/2744)) ([fd218f2](https://github.com/feathersjs/feathers/commit/fd218f289f8ca4c101e9938e8683e2efef6e8131)) +- **authentication-oauth:** Koa and transport independent oAuth authentication ([#2737](https://github.com/feathersjs/feathers/issues/2737)) ([9231525](https://github.com/feathersjs/feathers/commit/9231525a24bb790ba9c5d940f2867a9c727691c9)) +- **cli:** Add custom environment variable support to generated application ([#2751](https://github.com/feathersjs/feathers/issues/2751)) ([c7bf80d](https://github.com/feathersjs/feathers/commit/c7bf80d82c28c190e3f0136d51af5b7de1bc4868)) +- **cli:** Adding ClientService to CLI ([#2750](https://github.com/feathersjs/feathers/issues/2750)) ([1d45427](https://github.com/feathersjs/feathers/commit/1d45427988521ac028755cbe128685fcdf34f636)) + +# [5.0.0-pre.28](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.27...v5.0.0-pre.28) (2022-08-03) + +### Bug Fixes + +- **cli:** Improve generated application and client ([#2701](https://github.com/feathersjs/feathers/issues/2701)) ([bd55ffb](https://github.com/feathersjs/feathers/commit/bd55ffb812e89bf215f4515e7f137656ea888c3f)) + +# [5.0.0-pre.27](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.26...v5.0.0-pre.27) (2022-07-13) + +### Bug Fixes + +- **cli:** Fix flaky authentication migration and SQL id schema types ([#2676](https://github.com/feathersjs/feathers/issues/2676)) ([04ce9a5](https://github.com/feathersjs/feathers/commit/04ce9a53f4226cd6283f9dc241876e90ddf48618)) + +### Features + +- **cli:** Add support for Prettier ([#2684](https://github.com/feathersjs/feathers/issues/2684)) ([83aa8f9](https://github.com/feathersjs/feathers/commit/83aa8f9f212cb122d831dca8858852b0ac9b4da8)) +- **cli:** Improve generated application folder structure ([#2678](https://github.com/feathersjs/feathers/issues/2678)) ([d114557](https://github.com/feathersjs/feathers/commit/d114557721e73d6302aa88c11e3726dbcbd5c92b)) + +# [5.0.0-pre.26](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.25...v5.0.0-pre.26) (2022-06-22) + +### Bug Fixes + +- **cli:** Fix compilation folders that got mixed up ([fc4cb74](https://github.com/feathersjs/feathers/commit/fc4cb742f7f9164096d9319b13dfaaa5f54686a6)) + +# [5.0.0-pre.25](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.24...v5.0.0-pre.25) (2022-06-22) + +### Bug Fixes + +- **cli:** Generator fixes to work with the new guide ([#2674](https://github.com/feathersjs/feathers/issues/2674)) ([b773fa5](https://github.com/feathersjs/feathers/commit/b773fa5dbd7ff450cfb2f7b93e64882592262712)) + +# [5.0.0-pre.24](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.23...v5.0.0-pre.24) (2022-06-21) + +### Features + +- **cli:** Add generators for new Knex SQL database adapter ([#2673](https://github.com/feathersjs/feathers/issues/2673)) ([0fb2c0f](https://github.com/feathersjs/feathers/commit/0fb2c0f629116f71184b8698c383af8cfd149688)) +- **cli:** Add hook generator ([#2667](https://github.com/feathersjs/feathers/issues/2667)) ([24e4bc0](https://github.com/feathersjs/feathers/commit/24e4bc04a67fadee0e6a96a8389d788faba5c305)) +- **cli:** Add support for JavaScript to the new CLI ([#2668](https://github.com/feathersjs/feathers/issues/2668)) ([ebac587](https://github.com/feathersjs/feathers/commit/ebac587f7d00dc7607c3f546352d79f79b89a5d4)) +- **cli:** Add typed client to a generated app ([#2669](https://github.com/feathersjs/feathers/issues/2669)) ([5b801b5](https://github.com/feathersjs/feathers/commit/5b801b5017ddc3eaa95622b539f51d605916bc86)) +- **cli:** Initial Feathers v5 CLI and Pinion generator ([#2578](https://github.com/feathersjs/feathers/issues/2578)) ([7f59ae7](https://github.com/feathersjs/feathers/commit/7f59ae7f1471895ba8a82aa4702f1a23f71b7682)) diff --git a/_templates/package/new/LICENSE.t b/packages/cli/LICENSE similarity index 96% rename from _templates/package/new/LICENSE.t rename to packages/cli/LICENSE index e7a776c184..3f395cc665 100644 --- a/_templates/package/new/LICENSE.t +++ b/packages/cli/LICENSE @@ -1,7 +1,3 @@ ---- -to: packages/<%= name %>/LICENSE ---- - The MIT License (MIT) Copyright (c) 2021 Feathers diff --git a/_templates/package/new/README.md.t b/packages/cli/README.md similarity index 53% rename from _templates/package/new/README.md.t rename to packages/cli/README.md index bbc842bc64..a1d489f9cd 100644 --- a/_templates/package/new/README.md.t +++ b/packages/cli/README.md @@ -1,19 +1,25 @@ ---- -to: packages/<%= name %>/README.md ---- - -# @feathersjs/<%= name %> +# @feathersjs/cli [![CI](https://github.com/feathersjs/feathers/workflows/CI/badge.svg)](https://github.com/feathersjs/feathers/actions?query=workflow%3ACI) -[![Dependency Status](https://img.shields.io/david/feathersjs/feathers.svg?style=flat-square&path=packages/<%= name %>)](https://david-dm.org/feathersjs/feathers?path=packages/<%= name %>) -[![Download Status](https://img.shields.io/npm/dm/@feathersjs/<%= name %>.svg?style=flat-square)](https://www.npmjs.com/package/@feathersjs/<%= name %>) +[![Dependency Status](https://img.shields.io/david/feathersjs/feathers.svg?style=flat-square&path=packages/socketio)](https://david-dm.org/feathersjs/feathers?path=packages/cli) +[![Download Status](https://img.shields.io/npm/dm/@feathersjs/cli.svg?style=flat-square)](https://www.npmjs.com/package/@feathersjs/cli) -> <%= description %> +> The command line interface for creating Feathers applications ## Installation ``` -npm install @feathersjs/<%= name %> --save +npm install -g @feathersjs/cli +``` + +## Usage + +``` +$ mkdir myproject + +$ cd myproject + +$ feathers help ``` ## Documentation diff --git a/packages/cli/bin/feathers b/packages/cli/bin/feathers new file mode 100755 index 0000000000..7266b01c6f --- /dev/null +++ b/packages/cli/bin/feathers @@ -0,0 +1,6 @@ +#!/usr/bin/env node +'use strict' + +const { program } = require('../lib') + +program.parse() diff --git a/packages/cli/package.json b/packages/cli/package.json new file mode 100644 index 0000000000..aec43bb7d5 --- /dev/null +++ b/packages/cli/package.json @@ -0,0 +1,88 @@ +{ + "name": "@feathersjs/cli", + "description": "The command line interface for creating Feathers applications", + "version": "5.0.0-pre.31", + "homepage": "https://feathersjs.com", + "main": "lib/", + "bin": { + "feathers": "./bin/feathers" + }, + "keywords": [ + "feathers", + "feathers-plugin" + ], + "license": "MIT", + "funding": { + "type": "github", + "url": "https://github.com/sponsors/daffl" + }, + "repository": { + "type": "git", + "url": "git://github.com/feathersjs/feathers.git" + }, + "author": { + "name": "Feathers contributors", + "email": "hello@feathersjs.com", + "url": "https://feathersjs.com" + }, + "contributors": [], + "bugs": { + "url": "https://github.com/feathersjs/feathers/issues" + }, + "engines": { + "node": ">= 14" + }, + "files": [ + "CHANGELOG.md", + "LICENSE", + "README.md", + "lib/**", + "bin/**", + "*.d.ts", + "*.js" + ], + "scripts": { + "prepublish": "npm run compile", + "compile": "shx rm -rf lib/ && tsc && shx cp -r src/. lib/", + "mocha": "mocha --timeout 60000 --config ../../.mocharc.json --recursive test/**.test.ts test/**/*.test.ts", + "test": "npm run compile && npm run mocha" + }, + "publishConfig": { + "access": "public" + }, + "dependencies": { + "@feathershq/pinion": "^0.3.5", + "chalk": "^4.0.1", + "commander": "^9.4.1", + "lodash": "^4.17.21", + "prettier": "^2.7.1" + }, + "devDependencies": { + "@feathersjs/authentication": "^5.0.0-pre.31", + "@feathersjs/authentication-client": "^5.0.0-pre.31", + "@feathersjs/authentication-local": "^5.0.0-pre.31", + "@feathersjs/authentication-oauth": "^5.0.0-pre.31", + "@feathersjs/configuration": "^5.0.0-pre.31", + "@feathersjs/errors": "^5.0.0-pre.31", + "@feathersjs/express": "^5.0.0-pre.31", + "@feathersjs/feathers": "^5.0.0-pre.31", + "@feathersjs/knex": "^5.0.0-pre.31", + "@feathersjs/koa": "^5.0.0-pre.31", + "@feathersjs/mongodb": "^5.0.0-pre.31", + "@feathersjs/rest-client": "^5.0.0-pre.31", + "@feathersjs/schema": "^5.0.0-pre.31", + "@feathersjs/socketio": "^5.0.0-pre.31", + "@feathersjs/transport-commons": "^5.0.0-pre.31", + "@feathersjs/typebox": "^5.0.0-pre.31", + "@types/mocha": "^10.0.0", + "@types/node": "^18.8.2", + "@types/prettier": "^2.7.1", + "axios": "^0.27.2", + "mocha": "^10.0.0", + "shx": "^0.3.4", + "ts-node": "^10.9.1", + "type-fest": "^3.0.0", + "typescript": "^4.8.4" + }, + "gitHead": "4500dbeb8cea566678cf88b3313a88efd93a2ed9" +} diff --git a/packages/cli/src/app/index.ts b/packages/cli/src/app/index.ts new file mode 100644 index 0000000000..3f31afdfb1 --- /dev/null +++ b/packages/cli/src/app/index.ts @@ -0,0 +1,235 @@ +import { sep } from 'path' +import chalk from 'chalk' +import { + generator, + prompt, + runGenerators, + fromFile, + install, + copyFiles, + toFile, + when +} from '@feathershq/pinion' +import { FeathersBaseContext, FeathersAppInfo, initializeBaseContext, addVersions } from '../commons' +import { generate as authenticationGenerator, prompts as authenticationPrompts } from '../authentication' +import { generate as connectionGenerator, prompts as connectionPrompts } from '../connection' + +export interface AppGeneratorData extends FeathersAppInfo { + /** + * The application name + */ + name: string + /** + * A short description of the app + */ + description: string + /** + * The selected user authentication strategies + */ + authStrategies: string[] + /** + * The database connection string + */ + connectionString: string + /** + * The source folder where files are put + */ + lib: string +} + +export type AppGeneratorContext = FeathersBaseContext & + AppGeneratorData & { + dependencies: string[] + devDependencies: string[] + } + +export type AppGeneratorArguments = FeathersBaseContext & Partial + +export const generate = (ctx: AppGeneratorArguments) => + generator(ctx) + .then(initializeBaseContext()) + .then((ctx) => ({ + ...ctx, + dependencies: [], + devDependencies: [] + })) + .then( + prompt((ctx) => [ + { + name: 'language', + type: 'list', + message: 'Do you want to use JavaScript or TypeScript?', + when: !ctx.language, + choices: [ + { name: 'TypeScript', value: 'ts' }, + { name: 'JavaScript', value: 'js' } + ] + }, + { + name: 'name', + type: 'input', + when: !ctx.name, + message: 'What is the name of your application?', + default: ctx.cwd.split(sep).pop(), + validate: (input) => { + if (ctx.dependencyVersions[input]) { + return `Application can not have the same name as a dependency` + } + + return true + } + }, + { + name: 'description', + type: 'input', + when: !ctx.description, + message: 'Write a short description' + }, + { + type: 'list', + name: 'framework', + when: !ctx.framework, + message: 'Which HTTP framework do you want to use?', + choices: [ + { value: 'koa', name: `KoaJS ${chalk.grey('(recommended)')}` }, + { value: 'express', name: 'Express' } + ] + }, + { + type: 'checkbox', + name: 'transports', + when: !ctx.transports, + message: 'What APIs do you want to offer?', + choices: [ + { value: 'rest', name: 'HTTP (REST)', checked: true }, + { value: 'websockets', name: 'Real-time', checked: true } + ] + }, + { + name: 'packager', + type: 'list', + when: !ctx.packager, + message: 'Which package manager are you using?', + choices: [ + { value: 'npm', name: 'npm' }, + { value: 'yarn', name: 'Yarn' }, + { value: 'pnpm', name: 'pnpm' } + ] + }, + { + type: 'list', + name: 'schema', + when: !ctx.schema, + message: 'What is your preferred schema (model) definition format?', + choices: [ + { value: 'typebox', name: `TypeBox ${chalk.grey('(recommended)')}` }, + { value: 'json', name: 'JSON schema' } + ] + }, + ...connectionPrompts(ctx), + ...authenticationPrompts({ + ...ctx, + service: 'user', + path: 'users', + entity: 'user' + }) + ]) + ) + .then(runGenerators(__dirname, 'templates')) + .then(copyFiles(fromFile(__dirname, 'static'), toFile('.'))) + .then(initializeBaseContext()) + .then(async (ctx) => { + const { dependencies } = await connectionGenerator(ctx) + + return { + ...ctx, + dependencies + } + }) + .then( + when( + ({ authStrategies }) => authStrategies.length > 0, + async (ctx) => { + const { dependencies } = await authenticationGenerator({ + ...ctx, + service: 'user', + path: 'users', + entity: 'user' + }) + + return { + ...ctx, + dependencies + } + } + ) + ) + .then( + install( + ({ transports, framework, dependencyVersions, dependencies, schema }) => { + const hasSocketio = transports.includes('websockets') + + dependencies.push( + '@feathersjs/feathers', + '@feathersjs/errors', + '@feathersjs/schema', + '@feathersjs/configuration', + '@feathersjs/transport-commons', + '@feathersjs/authentication', + 'winston' + ) + + if (hasSocketio) { + dependencies.push('@feathersjs/socketio') + } + + if (framework === 'koa') { + dependencies.push('@feathersjs/koa', 'koa-static') + } + + if (framework === 'express') { + dependencies.push('@feathersjs/express', 'compression') + } + + if (schema === 'typebox') { + dependencies.push('@feathersjs/typebox') + } + + return addVersions(dependencies, dependencyVersions) + }, + false, + ctx.packager + ) + ) + .then( + install( + ({ language, framework, devDependencies, dependencyVersions }) => { + devDependencies.push( + 'nodemon', + 'axios', + 'mocha', + 'cross-env', + 'prettier', + '@feathersjs/cli', + '@feathersjs/rest-client', + '@feathersjs/authentication-client' + ) + + if (language === 'ts') { + devDependencies.push( + '@types/mocha', + framework === 'koa' ? '@types/koa-static' : '@types/compression', + '@types/node', + 'nodemon', + 'ts-node', + 'typescript', + 'shx' + ) + } + + return addVersions(devDependencies, dependencyVersions) + }, + true, + ctx.packager + ) + ) diff --git a/packages/cli/src/app/static/.gitignore b/packages/cli/src/app/static/.gitignore new file mode 100644 index 0000000000..82cf9aa04b --- /dev/null +++ b/packages/cli/src/app/static/.gitignore @@ -0,0 +1,121 @@ +# Logs +logs +*.log +npm-debug.log* +yarn-debug.log* +yarn-error.log* +lerna-debug.log* +.pnpm-debug.log* + +# Diagnostic reports (https://nodejs.org/api/report.html) +report.[0-9]*.[0-9]*.[0-9]*.[0-9]*.json + +# Runtime data +pids +*.pid +*.seed +*.pid.lock + +# Directory for instrumented libs generated by jscoverage/JSCover +lib-cov + +# Coverage directory used by tools like istanbul +coverage +*.lcov + +# nyc test coverage +.nyc_output + +# Grunt intermediate storage (https://gruntjs.com/creating-plugins#storing-task-files) +.grunt + +# Bower dependency directory (https://bower.io/) +bower_components + +# node-waf configuration +.lock-wscript + +# Compiled binary addons (https://nodejs.org/api/addons.html) +build/Release + +# Dependency directories +node_modules/ +jspm_packages/ + +# Snowpack dependency directory (https://snowpack.dev/) +web_modules/ + +# TypeScript cache +*.tsbuildinfo + +# Optional npm cache directory +.npm + +# Optional eslint cache +.eslintcache + +# Microbundle cache +.rpt2_cache/ +.rts2_cache_cjs/ +.rts2_cache_es/ +.rts2_cache_umd/ + +# Optional REPL history +.node_repl_history + +# Output of 'npm pack' +*.tgz + +# Yarn Integrity file +.yarn-integrity + +# dotenv environment variables file +.env +.env.test +.env.production + +# parcel-bundler cache (https://parceljs.org/) +.cache +.parcel-cache + +# Next.js build output +.next +out + +# Nuxt.js build / generate output +.nuxt +dist + +# Gatsby files +.cache/ +# Comment in the public line in if your project uses Gatsby and not Next.js +# https://nextjs.org/blog/next-9-1#public-directory-support +# public + +# vuepress build output +.vuepress/dist + +# Serverless directories +.serverless/ + +# FuseBox cache +.fusebox/ + +# DynamoDB Local files +.dynamodb/ + +# TernJS port file +.tern-port + +# Stores VSCode versions used for testing VSCode extensions +.vscode-test + +# yarn v2 +.yarn/cache +.yarn/unplugged +.yarn/build-state.yml +.yarn/install-state.gz +.pnp.* +.sqlite + +lib/ diff --git a/packages/cli/src/app/templates/app.test.tpl.ts b/packages/cli/src/app/templates/app.test.tpl.ts new file mode 100644 index 0000000000..f2d9334297 --- /dev/null +++ b/packages/cli/src/app/templates/app.test.tpl.ts @@ -0,0 +1,47 @@ +import { generator, toFile } from '@feathershq/pinion' +import { renderSource } from '../../commons' +import { AppGeneratorContext } from '../index' + +const template = ({ lib }: AppGeneratorContext) => /* ts */ `import assert from 'assert' +import axios from 'axios' +import type { Server } from 'http' +import { app } from '../${lib}/app' + +const port = app.get('port') +const appUrl = \`http://\${app.get('host')}:\${port}\` + +describe('Feathers application tests', () => { + let server: Server + + before(async () => { + server = await app.listen(port) + }) + + after(async () => { + await app.teardown() + }) + + it('starts and shows the index page', async () => { + const { data } = await axios.get(appUrl) + + assert.ok(data.indexOf('') !== -1) + }) + + it('shows a 404 JSON error', async () => { + try { + await axios.get(\`\${appUrl}/path/to/nowhere\`, { + responseType: 'json' + }) + assert.fail('should never get here') + } catch (error: any) { + const { response } = error + assert.strictEqual(response?.status, 404) + assert.strictEqual(response?.data?.code, 404) + assert.strictEqual(response?.data?.name, 'NotFound') + } + }) +}) +` + +export const generate = (ctx: AppGeneratorContext) => + generator(ctx).then(renderSource(template, toFile('test', 'app.test'))) diff --git a/packages/cli/src/app/templates/app.tpl.ts b/packages/cli/src/app/templates/app.tpl.ts new file mode 100644 index 0000000000..4977c95935 --- /dev/null +++ b/packages/cli/src/app/templates/app.tpl.ts @@ -0,0 +1,133 @@ +import { generator, toFile } from '@feathershq/pinion' +import { renderSource } from '../../commons' +import { AppGeneratorContext } from '../index' + +const tsKoaApp = ({ transports }: AppGeneratorContext) => /* ts */ `import serveStatic from 'koa-static' +import { feathers } from '@feathersjs/feathers' +import configuration from '@feathersjs/configuration' +import { koa, rest, bodyParser, errorHandler, parseAuthentication, cors } from '@feathersjs/koa' +${transports.includes('websockets') ? "import socketio from '@feathersjs/socketio'" : ''} + +import type { Application } from './declarations' +import { configurationValidator } from './schemas/configuration' +import { logErrorHook } from './logger' +import { services } from './services/index' +import { channels } from './channels' + +const app: Application = koa(feathers()) + +// Load our app configuration (see config/ folder) +app.configure(configuration(configurationValidator)) + +// Set up Koa middleware +app.use(cors()) +app.use(serveStatic(app.get('public'))) +app.use(errorHandler()) +app.use(parseAuthentication()) +app.use(bodyParser()) + +// Configure services and transports +app.configure(rest()) +${ + transports.includes('websockets') + ? `app.configure(socketio({ + cors: { + origin: app.get('origins') + } +}))` + : '' +} +app.configure(services) +app.configure(channels) + +// Register hooks that run on all service methods +app.hooks({ + around: { + all: [ logErrorHook ] + }, + before: {}, + after: {}, + error: {} +}) +// Register application setup and teardown hooks here +app.hooks({ + setup: [], + teardown: [] +}) + +export { app } +` + +const tsExpressApp = ({ transports }: AppGeneratorContext) => /* ts */ `import compress from 'compression' + +import { feathers } from '@feathersjs/feathers' +import express, { + rest, json, urlencoded, cors, + serveStatic, notFound, errorHandler +} from '@feathersjs/express' +import configuration from '@feathersjs/configuration' +${transports.includes('websockets') ? "import socketio from '@feathersjs/socketio'" : ''} + +import type { Application } from './declarations' +import { configurationValidator } from './schemas/configuration' +import { logger, logErrorHook } from './logger' +import { services } from './services/index' +import { channels } from './channels' + +const app: Application = express(feathers()) + +// Load app configuration +app.configure(configuration(configurationValidator)) +app.use(cors()) +app.use(compress()) +app.use(json()) +app.use(urlencoded({ extended: true })) +// Host the public folder +app.use('/', serveStatic(app.get('public'))) + +// Configure services and real-time functionality +app.configure(rest()) +${ + transports.includes('websockets') + ? `app.configure(socketio({ + cors: { + origin: app.get('origins') + } +}))` + : '' +} +app.configure(services) +app.configure(channels) + +// Configure a middleware for 404s and the error handler +app.use(notFound()) +app.use(errorHandler({ logger })) + +// Register hooks that run on all service methods +app.hooks({ + around: { + all: [ logErrorHook ] + }, + before: {}, + after: {}, + error: {} +}) +// Register application setup and teardown hooks here +app.hooks({ + setup: [], + teardown: [] +}) + +export { app } +` + +const template = (ctx: AppGeneratorContext) => + ctx.framework === 'express' ? tsExpressApp(ctx) : tsKoaApp(ctx) + +export const generate = (ctx: AppGeneratorContext) => + generator(ctx).then( + renderSource( + template, + toFile(({ lib }) => lib, 'app') + ) + ) diff --git a/packages/cli/src/app/templates/channels.tpl.ts b/packages/cli/src/app/templates/channels.tpl.ts new file mode 100644 index 0000000000..3d5390fa15 --- /dev/null +++ b/packages/cli/src/app/templates/channels.tpl.ts @@ -0,0 +1,78 @@ +import { generator, toFile } from '@feathershq/pinion' +import { renderSource } from '../../commons' +import { AppGeneratorContext } from '../index' + +const template = ({ language }: AppGeneratorContext) => /* ts */ `import '@feathersjs/transport-commons' +import type { Application, HookContext } from './declarations' +import { logger } from './logger' + +export const channels = (app: Application) => { + if(typeof app.channel !== 'function') { + // If no real-time functionality has been configured just return + return + } + + logger.warn('Publishing all events to all authenticated users. See \`channels.${language}\` and https://docs.feathersjs.com/api/channels.html for more information.') + + app.on('connection', (connection: any) => { + // On a new real-time connection, add it to the anonymous channel + app.channel('anonymous').join(connection) + }) + + app.on('login', (authResult: any, { connection }: any) => { + // connection can be undefined if there is no + // real-time connection, e.g. when logging in via REST + if(connection) { + // Obtain the logged in user + // const user = authResult.user + + // The connection is no longer anonymous, remove it + app.channel('anonymous').leave(connection) + + // Add it to the authenticated user channel + app.channel('authenticated').join(connection) + + // Channels can be named anything and joined on any condition + + // E.g. to send real-time events only to admins use + // if(user.isAdmin) { app.channel('admins').join(connection) } + + // If the user has joined e.g. chat rooms + // if(Array.isArray(user.rooms)) user.rooms.forEach(room => app.channel(\`rooms/\${room.id}\`).join(connection)) + + // Easily organize users by email and userid for things like messaging + // app.channel(\`emails/\${user.email}\`).join(connection) + // app.channel(\`userIds/\${user.id}\`).join(connection) + } + }) + + // eslint-disable-next-line no-unused-vars + app.publish((data: any, hook: HookContext) => { + // Here you can add event publishers to channels set up in \`channels.js\` + // To publish only for a specific event use \`app.publish(eventname, () => {})\` + + // e.g. to publish all service events to all authenticated users use + return app.channel('authenticated') + }) + + // Here you can also add service specific event publishers + // e.g. the publish the \`users\` service \`created\` event to the \`admins\` channel + // app.service('users').publish('created', () => app.channel('admins')) + + // With the userid and email organization from above you can easily select involved users + // app.service('messages').publish(() => { + // return [ + // app.channel(\`userIds/\${data.createdBy}\`), + // app.channel(\`emails/\${data.recipientEmail}\`) + // ] + // }) +} +` + +export const generate = (ctx: AppGeneratorContext) => + generator(ctx).then( + renderSource( + template, + toFile(({ lib }) => lib, 'channels') + ) + ) diff --git a/packages/cli/src/app/templates/client.test.tpl.ts b/packages/cli/src/app/templates/client.test.tpl.ts new file mode 100644 index 0000000000..b2c7578275 --- /dev/null +++ b/packages/cli/src/app/templates/client.test.tpl.ts @@ -0,0 +1,26 @@ +import { generator, toFile } from '@feathershq/pinion' +import { renderSource } from '../../commons' +import { AppGeneratorContext } from '../index' + +const template = ({ lib }: AppGeneratorContext) => /* ts */ `import assert from 'assert' +import axios from 'axios' +import type { Server } from 'http' +import { app } from '../${lib}/app' +import { createClient } from '../${lib}/client' + +import rest from '@feathersjs/rest-client' + +const port = app.get('port') +const appUrl = \`http://\${app.get('host')}:\${port}\` + +describe('client tests', () => { + const client = createClient(rest(appUrl).axios(axios)) + + it('initialized the client', () => { + assert.ok(client) + }) +}) +` + +export const generate = (ctx: AppGeneratorContext) => + generator(ctx).then(renderSource(template, toFile('test', 'client.test'))) diff --git a/packages/cli/src/app/templates/client.tpl.ts b/packages/cli/src/app/templates/client.tpl.ts new file mode 100644 index 0000000000..1788ccfbe2 --- /dev/null +++ b/packages/cli/src/app/templates/client.tpl.ts @@ -0,0 +1,27 @@ +import { generator, toFile } from '@feathershq/pinion' +import { renderSource } from '../../commons' +import { AppGeneratorContext } from '../index' + +const template = ({}: AppGeneratorContext) => /* ts */ `import { feathers } from '@feathersjs/feathers' +import type { TransportConnection, Params } from '@feathersjs/feathers' + +export interface ServiceTypes { + // +} + +export const createClient = (connection: TransportConnection) => { + const client = feathers() + + client.configure(connection) + + return client +} +` + +export const generate = async (ctx: AppGeneratorContext) => + generator(ctx).then( + renderSource( + template, + toFile(({ lib }) => lib, 'client') + ) + ) diff --git a/packages/cli/src/app/templates/config.tpl.ts b/packages/cli/src/app/templates/config.tpl.ts new file mode 100644 index 0000000000..05971de523 --- /dev/null +++ b/packages/cli/src/app/templates/config.tpl.ts @@ -0,0 +1,31 @@ +import { generator, toFile, writeJSON } from '@feathershq/pinion' +import { AppGeneratorContext } from '../index' + +const defaultConfig = ({}: AppGeneratorContext) => ({ + host: 'localhost', + port: 3030, + public: './public/', + origins: ['http://localhost:3030'], + paginate: { + default: 10, + max: 50 + } +}) + +const customEnvironment = { + port: { + __name: 'PORT', + __format: 'number' + }, + host: 'HOSTNAME' +} + +const testConfig = { + port: 8998 +} + +export const generate = (ctx: AppGeneratorContext) => + generator(ctx) + .then(writeJSON(defaultConfig, toFile('config', 'default.json'))) + .then(writeJSON(testConfig, toFile('config', 'test.json'))) + .then(writeJSON(customEnvironment, toFile('config', 'custom-environment-variables.json'))) diff --git a/packages/cli/src/app/templates/declarations.tpl.ts b/packages/cli/src/app/templates/declarations.tpl.ts new file mode 100644 index 0000000000..106fc7e538 --- /dev/null +++ b/packages/cli/src/app/templates/declarations.tpl.ts @@ -0,0 +1,33 @@ +import { generator, toFile, when, renderTemplate } from '@feathershq/pinion' +import { AppGeneratorContext } from '../index' + +const template = ({ + framework +}: AppGeneratorContext) => /* ts */ `import { HookContext as FeathersHookContext, NextFunction } from '@feathersjs/feathers' +import { Application as FeathersApplication } from '@feathersjs/${framework}' +import { ApplicationConfiguration } from './schemas/configuration' + +export { NextFunction } + +export interface Configuration extends ApplicationConfiguration {} + +// A mapping of service names to types. Will be extended in service files. +export interface ServiceTypes {} + +// The application instance type that will be used everywhere else +export type Application = FeathersApplication + +// The context for hook functions - can be typed with a service class +export type HookContext = FeathersHookContext +` + +export const generate = (ctx: AppGeneratorContext) => + generator(ctx).then( + when( + ({ language }) => language === 'ts', + renderTemplate( + template, + toFile(({ lib }) => lib, 'declarations.ts') + ) + ) + ) diff --git a/packages/cli/src/app/templates/index.html.tpl.ts b/packages/cli/src/app/templates/index.html.tpl.ts new file mode 100644 index 0000000000..171da72480 --- /dev/null +++ b/packages/cli/src/app/templates/index.html.tpl.ts @@ -0,0 +1,44 @@ +import { generator, renderTemplate, toFile } from '@feathershq/pinion' +import { AppGeneratorContext } from '../index' + +const template = ({ name, description }: AppGeneratorContext) => /* html */ ` + + + ${name} + + + + + + + + + +` + +export const generate = (ctx: AppGeneratorContext) => + generator(ctx).then(renderTemplate(template, toFile('public', 'index.html'))) diff --git a/packages/cli/src/app/templates/index.tpl.ts b/packages/cli/src/app/templates/index.tpl.ts new file mode 100644 index 0000000000..c44a202d2c --- /dev/null +++ b/packages/cli/src/app/templates/index.tpl.ts @@ -0,0 +1,22 @@ +import { generator, toFile } from '@feathershq/pinion' +import { renderSource } from '../../commons' +import { AppGeneratorContext } from '../index' + +const template = ({}: AppGeneratorContext) => /* ts */ `import { app } from './app' +import { logger } from './logger' + +const port = app.get('port') +const host = app.get('host') + +app.listen(port).then(() => { + logger.info(\`Feathers app listening on http://\${host}:\${port}\`) +}) +` + +export const generate = (ctx: AppGeneratorContext) => + generator(ctx).then( + renderSource( + template, + toFile(({ lib }) => lib, 'index') + ) + ) diff --git a/packages/cli/src/app/templates/logger.tpl.ts b/packages/cli/src/app/templates/logger.tpl.ts new file mode 100644 index 0000000000..709808126f --- /dev/null +++ b/packages/cli/src/app/templates/logger.tpl.ts @@ -0,0 +1,44 @@ +import { generator, toFile } from '@feathershq/pinion' +import { renderSource } from '../../commons' +import { AppGeneratorContext } from '../index' + +const template = + ({}: AppGeneratorContext) => /* ts */ `import { createLogger, format, transports } from 'winston' +import type { HookContext, NextFunction } from './declarations' + +// Configure the Winston logger. For the complete documentation see https://github.com/winstonjs/winston +export const logger = createLogger({ + // To see more detailed errors, change this to 'debug' + level: 'info', + format: format.combine( + format.splat(), + format.simple() + ), + transports: [ + new transports.Console() + ] +}) + +export const logErrorHook = async (context: HookContext, next: NextFunction) => { + try { + await next() + } catch (error: any) { + logger.error(error.stack) + + // Log validation errors + if (error.errors) { + logger.error(error.errors) + } + + throw error + } +} +` + +export const generate = (ctx: AppGeneratorContext) => + generator(ctx).then( + renderSource( + template, + toFile(({ lib }) => lib, 'logger') + ) + ) diff --git a/packages/cli/src/app/templates/package.json.tpl.ts b/packages/cli/src/app/templates/package.json.tpl.ts new file mode 100644 index 0000000000..e8c75b04b7 --- /dev/null +++ b/packages/cli/src/app/templates/package.json.tpl.ts @@ -0,0 +1,68 @@ +import { generator, toFile, writeJSON } from '@feathershq/pinion' +import { AppGeneratorContext } from '../index' + +const jsPackageJson = (lib: string) => ({ + type: 'module', + scripts: { + start: `node ${lib}`, + dev: `nodemon ${lib}/`, + prettier: 'npx prettier "**/*.js" --write', + mocha: 'cross-env NODE_ENV=test mocha test/ --recursive --exit', + test: 'npm run mocha' + } +}) + +const tsPackageJson = (lib: string) => ({ + scripts: { + dev: `nodemon -x ts-node ${lib}/index.ts`, + compile: 'shx rm -rf lib/ && tsc', + start: 'node lib/', + prettier: 'npx prettier "**/*.ts" --write', + mocha: + 'cross-env NODE_ENV=test mocha test/ --require ts-node/register --recursive --extension .ts --exit', + test: 'npm run mocha' + } +}) + +const packageJson = ({ + name, + description, + language, + packager, + database, + framework, + transports, + lib, + test, + schema +}: AppGeneratorContext) => ({ + name, + description, + version: '0.0.0', + homepage: '', + private: true, + keywords: ['feathers'], + author: {}, + contributors: [] as string[], + bugs: {}, + engines: { + node: `>= ${process.version.substring(1)}` + }, + feathers: { + language, + packager, + database, + framework, + transports, + schema + }, + directories: { + lib, + test + }, + main: language === 'ts' ? 'lib/client' : `${lib}/client`, + ...(language === 'ts' ? tsPackageJson(lib) : jsPackageJson(lib)) +}) + +export const generate = (ctx: AppGeneratorContext) => + generator(ctx).then(writeJSON(packageJson, toFile('package.json'))) diff --git a/packages/cli/src/app/templates/prettierrc.tpl.ts b/packages/cli/src/app/templates/prettierrc.tpl.ts new file mode 100644 index 0000000000..a97512d6b6 --- /dev/null +++ b/packages/cli/src/app/templates/prettierrc.tpl.ts @@ -0,0 +1,14 @@ +import { generator, toFile, writeJSON } from '@feathershq/pinion' +import { AppGeneratorContext } from '../index' +import { PRETTIERRC } from '../../commons' + +export const generate = (ctx: AppGeneratorContext) => + generator(ctx).then( + writeJSON( + (ctx) => ({ + ...PRETTIERRC, + parser: ctx.language === 'ts' ? 'typescript' : 'babel' + }), + toFile('.prettierrc') + ) + ) diff --git a/packages/cli/src/app/templates/readme.md.tpl.ts b/packages/cli/src/app/templates/readme.md.tpl.ts new file mode 100644 index 0000000000..7ac54db41f --- /dev/null +++ b/packages/cli/src/app/templates/readme.md.tpl.ts @@ -0,0 +1,57 @@ +import { generator, renderTemplate, toFile } from '@feathershq/pinion' +import { AppGeneratorContext } from '../index' + +const template = ({ name, description, language, database }: AppGeneratorContext) => /* md */ `# ${name} + +> ${description} + +## About + +This project uses [Feathers](http://feathersjs.com). An open source framework for building APIs and real-time applications. + +## Getting Started + +1. Make sure you have [NodeJS](https://nodejs.org/) and [npm](https://www.npmjs.com/) installed. +2. Install your dependencies + + \`\`\` + cd path/to/${name} + npm install + \`\`\` + +3. Start your app + + \`\`\`${ + language === 'ts' + ? ` + npm run compile # Compile TypeScript source` + : '' + }${ + database !== 'mongodb' + ? ` + npm run migrate # Run migrations to set up the database` + : '' +} + npm start + \`\`\` + +## Testing + +Run \`npm test\` and all your tests in the \`test/\` directory will be run. + +## Scaffolding + +This app comes with a powerful command line interface for Feathers. Here are a few things it can do: + +\`\`\` +$ npx feathers help # Show all commands +$ npx feathers generate service # Generate a new Service +\`\`\` + +## Help + +For more information on all the things you can do with Feathers visit [docs.feathersjs.com](http://docs.feathersjs.com). +` + +export const generate = (ctx: AppGeneratorContext) => + generator(ctx).then(renderTemplate(template, toFile('readme.md'))) diff --git a/packages/cli/src/app/templates/schemas.tpl.ts b/packages/cli/src/app/templates/schemas.tpl.ts new file mode 100644 index 0000000000..2182986a78 --- /dev/null +++ b/packages/cli/src/app/templates/schemas.tpl.ts @@ -0,0 +1,89 @@ +import { generator, toFile } from '@feathershq/pinion' +import { renderSource } from '../../commons' +import { AppGeneratorContext } from '../index' + +const validatorTemplate = /* ts */ `import { Ajv, addFormats } from '@feathersjs/schema' +import type { FormatsPluginOptions } from '@feathersjs/schema' + +const formats: FormatsPluginOptions = [ + 'date-time', + 'time', + 'date', + 'email', + 'hostname', + 'ipv4', + 'ipv6', + 'uri', + 'uri-reference', + 'uuid', + 'uri-template', + 'json-pointer', + 'relative-json-pointer', + 'regex' +] + +export const dataValidator = addFormats(new Ajv({}), formats) + +export const queryValidator = addFormats(new Ajv({ + coerceTypes: true +}), formats) +` + +const configurationJsonTemplate = + ({}: AppGeneratorContext) => /* ts */ `import { defaultAppSettings, getValidator } from '@feathersjs/schema' +import type { FromSchema } from '@feathersjs/schema' + +import { dataValidator } from './validators' + +export const configurationSchema = { + type: 'object', + additionalProperties: false, + required: [ 'host', 'port', 'public' ], + properties: { + ...defaultAppSettings, + host: { type: 'string' }, + port: { type: 'number' }, + public: { type: 'string' } + } +} as const + +export const configurationValidator = getValidator(configurationSchema, dataValidator) + +export type ApplicationConfiguration = FromSchema +` + +const configurationTypeboxTemplate = + ({}: AppGeneratorContext) => /* ts */ `import { Type, getValidator, defaultAppConfiguration } from '@feathersjs/typebox' +import type { Static } from '@feathersjs/typebox' + +import { dataValidator } from './validators' + +export const configurationSchema = Type.Intersect([ + defaultAppConfiguration, + Type.Object({ + host: Type.String(), + port: Type.Number(), + public: Type.String() + }) +]) + +export type ApplicationConfiguration = Static + +export const configurationValidator = getValidator(configurationSchema, dataValidator) +` + +export const generate = (ctx: AppGeneratorContext) => + generator(ctx) + .then( + renderSource( + async (ctx) => + ctx.schema === 'typebox' ? configurationTypeboxTemplate(ctx) : configurationJsonTemplate(ctx), + toFile(({ lib }) => lib, 'schemas', 'configuration') + ) + ) + .then( + renderSource( + validatorTemplate, + toFile(({ lib }) => lib, 'schemas', 'validators') + ) + ) diff --git a/packages/cli/src/app/templates/services.tpl.ts b/packages/cli/src/app/templates/services.tpl.ts new file mode 100644 index 0000000000..87c9b1f3d9 --- /dev/null +++ b/packages/cli/src/app/templates/services.tpl.ts @@ -0,0 +1,18 @@ +import { generator, toFile } from '@feathershq/pinion' +import { renderSource } from '../../commons' +import { AppGeneratorContext } from '../index' + +const template = ({}: AppGeneratorContext) => /* ts */ `import type { Application } from '../declarations' + +export const services = (app: Application) => { + // All services will be registered here +} +` + +export const generate = (ctx: AppGeneratorContext) => + generator(ctx).then( + renderSource( + template, + toFile(({ lib }) => lib, 'services', 'index') + ) + ) diff --git a/packages/cli/src/app/templates/tsconfig.json.tpl.ts b/packages/cli/src/app/templates/tsconfig.json.tpl.ts new file mode 100644 index 0000000000..adc3432ae8 --- /dev/null +++ b/packages/cli/src/app/templates/tsconfig.json.tpl.ts @@ -0,0 +1,28 @@ +import { generator, toFile, when, writeJSON } from '@feathershq/pinion' +import { AppGeneratorContext } from '../index' + +export const generate = (ctx: AppGeneratorContext) => + generator(ctx).then( + when( + (ctx) => ctx.language === 'ts', + writeJSON( + ({ lib }) => ({ + 'ts-node': { + files: true + }, + compilerOptions: { + target: 'es2020', + module: 'commonjs', + outDir: './lib', + rootDir: `./${lib}`, + declaration: true, + strict: true, + esModuleInterop: true + }, + include: [lib], + exclude: ['test'] + }), + toFile('tsconfig.json') + ) + ) + ) diff --git a/packages/cli/src/authentication/index.ts b/packages/cli/src/authentication/index.ts new file mode 100644 index 0000000000..553e81c4e9 --- /dev/null +++ b/packages/cli/src/authentication/index.ts @@ -0,0 +1,121 @@ +import chalk from 'chalk' +import { generator, runGenerators, prompt, install } from '@feathershq/pinion' +import { + addVersions, + checkPreconditions, + FeathersBaseContext, + getDatabaseAdapter, + initializeBaseContext +} from '../commons' +import { generate as serviceGenerator, ServiceGeneratorContext } from '../service/index' + +export interface AuthenticationGeneratorContext extends ServiceGeneratorContext { + service: string + entity: string + authStrategies: string[] + dependencies: string[] +} + +export type AuthenticationGeneratorArguments = FeathersBaseContext & + Partial> + +export const prompts = (ctx: AuthenticationGeneratorArguments) => [ + { + type: 'checkbox', + name: 'authStrategies', + when: !ctx.authStrategies, + message: 'Which authentication methods do you want to use?', + suffix: chalk.grey(' Other methods and providers can be added at any time.'), + choices: [ + { + name: 'Email + Password', + value: 'local', + checked: true + }, + { + name: 'Google', + value: 'google' + }, + { + name: 'Facebook', + value: 'facebook' + }, + { + name: 'Twitter', + value: 'twitter' + }, + { + name: 'GitHub', + value: 'github' + }, + { + name: 'Auth0', + value: 'auth0' + } + ] + }, + { + name: 'service', + type: 'input', + when: !ctx.service, + message: 'What is your authentication service name?', + default: 'user' + }, + { + name: 'path', + type: 'input', + when: !ctx.path, + message: 'What path should the service be registered on?', + default: 'users' + }, + { + name: 'entity', + type: 'input', + when: !ctx.entity, + message: 'What is your authenticated entity name?', + suffix: chalk.grey(' Will be available in params (e.g. params.user)'), + default: 'user' + } +] + +export const generate = (ctx: AuthenticationGeneratorArguments) => + generator(ctx) + .then(initializeBaseContext()) + .then(checkPreconditions()) + .then(prompt(prompts)) + .then(async (ctx) => { + const serviceContext = await serviceGenerator({ + ...ctx, + name: ctx.service, + isEntityService: true, + type: getDatabaseAdapter(ctx.feathers?.database) + }) + + return { + ...ctx, + ...serviceContext + } + }) + .then(runGenerators(__dirname, 'templates')) + .then((ctx) => { + const dependencies: string[] = [] + + dependencies.push('@feathersjs/authentication-oauth') + + if (ctx.authStrategies.includes('local')) { + dependencies.push('@feathersjs/authentication-local') + } + + if (ctx.dependencies) { + return { + ...ctx, + dependencies: [...ctx.dependencies, ...dependencies] + } + } + + return install( + addVersions(dependencies, ctx.dependencyVersions), + false, + ctx.feathers.packager + )(ctx) + }) diff --git a/packages/cli/src/authentication/templates/authentication.tpl.ts b/packages/cli/src/authentication/templates/authentication.tpl.ts new file mode 100644 index 0000000000..a0c64d96a0 --- /dev/null +++ b/packages/cli/src/authentication/templates/authentication.tpl.ts @@ -0,0 +1,50 @@ +import { generator, before, toFile } from '@feathershq/pinion' +import { injectSource, renderSource } from '../../commons' +import { AuthenticationGeneratorContext } from '../index' + +const template = ({ + authStrategies +}: AuthenticationGeneratorContext) => /* ts */ `import { AuthenticationService, JWTStrategy } from '@feathersjs/authentication' +import { LocalStrategy } from '@feathersjs/authentication-local' +import { OAuthStrategy } from '@feathersjs/authentication-oauth' +import { oauth } from '@feathersjs/authentication-oauth' +import type { Application } from './declarations' + +declare module './declarations' { + interface ServiceTypes { + 'authentication': AuthenticationService + } +} + +export const authentication = (app: Application) => { + const authentication = new AuthenticationService(app) + + authentication.register('jwt', new JWTStrategy()) + ${authStrategies + .map( + (strategy) => + ` authentication.register('${strategy}', ${ + strategy === 'local' ? `new LocalStrategy()` : `new OAuthStrategy()` + })` + ) + .join('\n')} + + app.use('authentication', authentication) + app.configure(oauth()) +} +` + +const importTemplate = "import { authentication } from './authentication'" +const configureTemplate = 'app.configure(authentication)' +const toAppFile = toFile(({ lib }) => [lib, 'app']) + +export const generate = (ctx: AuthenticationGeneratorContext) => + generator(ctx) + .then( + renderSource( + template, + toFile(({ lib }) => lib, 'authentication') + ) + ) + .then(injectSource(importTemplate, before('import { services } from'), toAppFile)) + .then(injectSource(configureTemplate, before('app.configure(services)'), toAppFile)) diff --git a/packages/cli/src/authentication/templates/client.test.tpl.ts b/packages/cli/src/authentication/templates/client.test.tpl.ts new file mode 100644 index 0000000000..34a994947a --- /dev/null +++ b/packages/cli/src/authentication/templates/client.test.tpl.ts @@ -0,0 +1,80 @@ +import { generator, toFile } from '@feathershq/pinion' +import { renderSource } from '../../commons' +import { AuthenticationGeneratorContext } from '../index' + +const template = ({ + authStrategies, + upperName, + type, + lib +}: AuthenticationGeneratorContext) => /* ts */ `import assert from 'assert' +import axios from 'axios' + +import rest from '@feathersjs/rest-client' +${ + authStrategies.includes('local') + ? `import authenticationClient from '@feathersjs/authentication-client'` + : '' +} +import { app } from '../${lib}/app' +import { createClient } from '../${lib}/client' +${authStrategies.includes('local') ? `import type { ${upperName}Data } from '../${lib}/client'` : ''} + +const port = app.get('port') +const appUrl = \`http://\${app.get('host')}:\${port}\` + +describe('application client tests', () => { + const client = createClient(rest(appUrl).axios(axios)) + + client.configure(authenticationClient()) + + before(async () => { + await app.listen(port) + }) + + after(async () => { + await app.teardown() + }) + + it('initialized the client', () => { + assert.ok(client) + }) + + ${ + authStrategies.includes('local') + ? ` + it('creates and authenticates a user with email and password', async () => { + const userData: ${upperName}Data = { + email: 'someone@example.com', + password: 'supersecret' + } + + await client.service('users').create(userData) + + const { user, accessToken } = await client.authenticate({ + strategy: 'local', + ...userData + }) + + assert.ok(accessToken, 'Created access token for user') + assert.ok(user, 'Includes user in authentication data') + assert.strictEqual(user.password, undefined, 'Password is hidden to clients') + + await client.logout() + + // Remove the test user on the server + await app.service('users').remove(user.${type === 'mongodb' ? '_id' : 'id'}) + })` + : '' + } +}) +` + +export const generate = (ctx: AuthenticationGeneratorContext) => + generator(ctx).then( + renderSource( + template, + toFile(({ test }) => test, 'client.test'), + { force: true } + ) + ) diff --git a/packages/cli/src/authentication/templates/client.tpl.ts b/packages/cli/src/authentication/templates/client.tpl.ts new file mode 100644 index 0000000000..033a201181 --- /dev/null +++ b/packages/cli/src/authentication/templates/client.tpl.ts @@ -0,0 +1,19 @@ +import { generator, toFile, after, when } from '@feathershq/pinion' +import { injectSource } from '../../commons' +import { ServiceGeneratorContext } from '../../service' + +const importTemplate = /* ts */ `import type { AuthenticationService } from '@feathersjs/authentication' +` +const declarationTemplate = ` authentication: Pick` + +const toClientFile = toFile(({ lib }) => [lib, 'client']) + +export const generate = async (ctx: ServiceGeneratorContext) => + generator(ctx) + .then(injectSource(importTemplate, after("from '@feathersjs/feathers'"), toClientFile)) + .then( + when( + ({ language }) => language === 'ts', + injectSource(declarationTemplate, after('export interface ServiceTypes'), toClientFile) + ) + ) diff --git a/packages/cli/src/authentication/templates/config.tpl.ts b/packages/cli/src/authentication/templates/config.tpl.ts new file mode 100644 index 0000000000..598f0a84cc --- /dev/null +++ b/packages/cli/src/authentication/templates/config.tpl.ts @@ -0,0 +1,57 @@ +import crypto from 'crypto' +import { generator, toFile, mergeJSON } from '@feathershq/pinion' +import { AuthenticationGeneratorContext } from '../index' + +export const generate = (ctx: AuthenticationGeneratorContext) => + generator(ctx) + .then( + mergeJSON(({ authStrategies }) => { + const authentication: any = { + entity: ctx.entity, + service: ctx.path, + secret: crypto.randomBytes(24).toString('base64'), + authStrategies: ['jwt'], + jwtOptions: { + header: { + typ: 'access' + }, + audience: 'https://yourdomain.com', + algorithm: 'HS256', + expiresIn: '1d' + } + } + + if (authStrategies.includes('local')) { + authentication.authStrategies.push('local') + authentication.local = { + usernameField: 'email', + passwordField: 'password' + } + } + + const oauthStrategies = authStrategies.filter((name) => name !== 'local') + + if (oauthStrategies.length) { + authentication.oauth = oauthStrategies.reduce((oauth, name) => { + oauth[name] = { + key: '', + secret: '' + } + + return oauth + }, {} as any) + } + + return { authentication } + }, toFile('config', 'default.json')) + ) + .then( + mergeJSON( + { + authentication: { + secret: 'FEATHERS_SECRET' + } + }, + toFile('config', 'custom-environment-variables.json') + ) + ) diff --git a/packages/cli/src/authentication/templates/declarations.tpl.ts b/packages/cli/src/authentication/templates/declarations.tpl.ts new file mode 100644 index 0000000000..a1681ca7f3 --- /dev/null +++ b/packages/cli/src/authentication/templates/declarations.tpl.ts @@ -0,0 +1,34 @@ +import { generator, inject, before, toFile, when, append } from '@feathershq/pinion' +import { AuthenticationGeneratorContext } from '../index' + +const importTemplate = ({ + upperName, + folder, + fileName +}: AuthenticationGeneratorContext) => /* ts */ `import { ${upperName} } from './services/${folder.join( + '/' +)}/${fileName}' +` + +const paramsTemplate = ({ + entity, + upperName +}: AuthenticationGeneratorContext) => /* ts */ `// Add the ${entity} as an optional property to all params +declare module '@feathersjs/feathers' { + interface Params { + ${entity}?: ${upperName} + } +} +` + +const toDeclarationFile = toFile(({ lib }) => lib, 'declarations.ts') + +export const generate = (ctx: AuthenticationGeneratorContext) => + generator(ctx) + .then( + when( + (ctx) => ctx.language === 'ts', + inject(importTemplate, before('export { NextFunction }'), toDeclarationFile) + ) + ) + .then(when((ctx) => ctx.language === 'ts', inject(paramsTemplate, append(), toDeclarationFile))) diff --git a/packages/cli/src/authentication/templates/knex.tpl.ts b/packages/cli/src/authentication/templates/knex.tpl.ts new file mode 100644 index 0000000000..0ad4f8f31c --- /dev/null +++ b/packages/cli/src/authentication/templates/knex.tpl.ts @@ -0,0 +1,62 @@ +import { generator, when, toFile } from '@feathershq/pinion' +import { getDatabaseAdapter, renderSource } from '../../commons' +import { AuthenticationGeneratorContext } from '../index' + +const migrationTemplate = ({ + kebabPath, + authStrategies +}: AuthenticationGeneratorContext) => /* ts */ `import type { Knex } from 'knex' + +export async function up(knex: Knex): Promise { + await knex.schema.alterTable('${kebabPath}', function (table) { + table.dropColumn('text')${authStrategies + .map((name) => + name === 'local' + ? ` + table.string('email').unique() + table.string('password')` + : ` + table.string('${name}Id')` + ) + .join('\n')} + }) +} + +export async function down(knex: Knex): Promise { + await knex.schema.alterTable('${kebabPath}', function (table) { + table.string('text')${authStrategies + .map((name) => + name === 'local' + ? ` + table.dropColumn('email') + table.dropColumn('password')` + : ` + table.dropColumn('${name}Id') + ` + ) + .join('\n')} + }) +} +` + +export const generate = (ctx: AuthenticationGeneratorContext) => + generator(ctx).then( + when( + (ctx) => getDatabaseAdapter(ctx.feathers?.database) === 'knex', + renderSource( + migrationTemplate, + toFile( + toFile('migrations', () => { + // Probably not great but it works to align with the Knex migration file format + // We add 2 seconds so that the migrations run in the correct order + const migrationDate = new Date(Date.now() + 2000) + .toISOString() + .replace(/\D/g, '') + .substring(0, 14) + + return `${migrationDate}_authentication` + }) + ) + ) + ) + ) diff --git a/packages/cli/src/authentication/templates/schema.json.tpl.ts b/packages/cli/src/authentication/templates/schema.json.tpl.ts new file mode 100644 index 0000000000..dfb6b1fcad --- /dev/null +++ b/packages/cli/src/authentication/templates/schema.json.tpl.ts @@ -0,0 +1,108 @@ +import { generator, toFile, when } from '@feathershq/pinion' +import { renderSource } from '../../commons' +import { AuthenticationGeneratorContext } from '../index' + +const template = ({ + camelName, + upperName, + authStrategies, + type, + relative +}: AuthenticationGeneratorContext) => /* ts */ `import { resolve, querySyntax, getValidator, getDataValidator } from '@feathersjs/schema' +import type { FromSchema } from '@feathersjs/schema' +${authStrategies.includes('local') ? `import { passwordHash } from '@feathersjs/authentication-local'` : ''} + +import type { HookContext } from '${relative}/declarations' +import { dataValidator, queryValidator } from '${relative}/schemas/validators' + +// Main data model schema +export const ${camelName}Schema = { + $id: '${upperName}', + type: 'object', + additionalProperties: false, + required: [ '${type === 'mongodb' ? '_id' : 'id'}'${authStrategies.includes('local') ? ", 'email'" : ''} ], + properties: { + ${type === 'mongodb' ? '_id' : 'id'}: { + type: '${type === 'mongodb' ? 'string' : 'number'}' + }, + ${authStrategies + .map((name) => + name === 'local' + ? ` email: { type: 'string' }, + password: { type: 'string' }` + : ` ${name}Id: { type: 'string' }` + ) + .join(',\n')} + } +} as const +export type ${upperName} = FromSchema +export const ${camelName}Resolver = resolve<${upperName}, HookContext>({ + properties: {} +}) + +// Schema for the basic data model (e.g. creating new entries) +export const ${camelName}DataSchema = { + $id: '${upperName}Data', + type: 'object', + additionalProperties: false, + required: [ ], + properties: { + ...${camelName}Schema.properties + } +} as const +export type ${upperName}Data = FromSchema +export const ${camelName}DataValidator = getDataValidator(${camelName}DataSchema, dataValidator) +export const ${camelName}DataResolver = resolve<${upperName}Data, HookContext>({ + properties: { + ${authStrategies.includes('local') ? `password: passwordHash({ strategy: 'local' })` : ''} + } +}) + +export const ${camelName}ExternalResolver = resolve<${upperName}, HookContext>({ + properties: { + // The password should never be visible externally + password: async () => undefined + } +}) + +// Schema for allowed query properties +export const ${camelName}QuerySchema = { + $id: '${upperName}Query', + type: 'object', + additionalProperties: false, + properties: { + ...querySyntax(${camelName}Schema.properties) + } +} as const +export type ${upperName}Query = FromSchema +export const ${camelName}QueryValidator = getValidator(${camelName}QuerySchema, queryValidator) +export const ${camelName}QueryResolver = resolve<${upperName}Query, HookContext>({ + properties: { + // If there is a user (e.g. with authentication), they are only allowed to see their own data + ${type === 'mongodb' ? '_id' : 'id'}: async (value, user, context) => { + if (context.params.user) { + return context.params.user.${type === 'mongodb' ? '_id' : 'id'} + } + + return value + } + } +}) +` + +export const generate = (ctx: AuthenticationGeneratorContext) => + generator(ctx).then( + when( + ({ schema }) => schema === 'json', + renderSource( + template, + toFile(({ lib, folder, fileName }: AuthenticationGeneratorContext) => [ + lib, + 'services', + ...folder, + `${fileName}.schema` + ]), + { force: true } + ) + ) + ) diff --git a/packages/cli/src/authentication/templates/schema.typebox.tpl.ts b/packages/cli/src/authentication/templates/schema.typebox.tpl.ts new file mode 100644 index 0000000000..36a3ccba90 --- /dev/null +++ b/packages/cli/src/authentication/templates/schema.typebox.tpl.ts @@ -0,0 +1,94 @@ +import { generator, toFile, when } from '@feathershq/pinion' +import { renderSource } from '../../commons' +import { AuthenticationGeneratorContext } from '../index' + +export const template = ({ + camelName, + upperName, + authStrategies, + type, + relative +}: AuthenticationGeneratorContext) => /* ts */ `import { resolve } from '@feathersjs/schema' +import { Type, getDataValidator, getValidator, querySyntax } from '@feathersjs/typebox' +import type { Static } from '@feathersjs/typebox' +${authStrategies.includes('local') ? `import { passwordHash } from '@feathersjs/authentication-local'` : ''} + +import type { HookContext } from '${relative}/declarations' +import { dataValidator, queryValidator } from '${relative}/schemas/validators' + +// Main data model schema +export const ${camelName}Schema = Type.Object({ + ${type === 'mongodb' ? '_id: Type.String()' : 'id: Type.Number()'}, + ${authStrategies + .map((name) => + name === 'local' + ? ` email: Type.String(), + password: Type.Optional(Type.String())` + : ` ${name}Id: Type.Optional(Type.String())` + ) + .join(',\n')} +},{ $id: '${upperName}', additionalProperties: false }) +export type ${upperName} = Static +export const ${camelName}Resolver = resolve<${upperName}, HookContext>({ + properties: {} +}) + +export const ${camelName}ExternalResolver = resolve<${upperName}, HookContext>({ + properties: { + // The password should never be visible externally + password: async () => undefined + } +}) + +// Schema for the basic data model (e.g. creating new entries) +export const ${camelName}DataSchema = Type.Pick(${camelName}Schema, [ + ${authStrategies.map((name) => (name === 'local' ? `'email', 'password'` : `'${name}Id'`)).join(', ')} +], + { $id: '${upperName}Data', additionalProperties: false } +) +export type ${upperName}Data = Static +export const ${camelName}DataValidator = getDataValidator(${camelName}DataSchema, dataValidator) +export const ${camelName}DataResolver = resolve<${upperName}, HookContext>({ + properties: { + ${authStrategies.includes('local') ? `password: passwordHash({ strategy: 'local' })` : ''} + } +}) + +// Schema for allowed query properties +export const ${camelName}QueryProperties = Type.Pick(${camelName}Schema, ['${ + type === 'mongodb' ? '_id' : 'id' +}', ${authStrategies.map((name) => (name === 'local' ? `'email'` : `'${name}Id'`)).join(', ')} +]) +export const ${camelName}QuerySchema = querySyntax(${camelName}QueryProperties) +export type ${upperName}Query = Static +export const ${camelName}QueryValidator = getValidator(${camelName}QuerySchema, queryValidator) +export const ${camelName}QueryResolver = resolve<${upperName}Query, HookContext>({ + properties: { + // If there is a user (e.g. with authentication), they are only allowed to see their own data + ${type === 'mongodb' ? '_id' : 'id'}: async (value, user, context) => { + if (context.params.user) { + return context.params.user.${type === 'mongodb' ? '_id' : 'id'} + } + + return value + } + } +}) +` + +export const generate = (ctx: AuthenticationGeneratorContext) => + generator(ctx).then( + when( + ({ schema }) => schema === 'typebox', + renderSource( + template, + toFile(({ lib, folder, fileName }: AuthenticationGeneratorContext) => [ + lib, + 'services', + ...folder, + `${fileName}.schema` + ]), + { force: true } + ) + ) + ) diff --git a/packages/cli/src/cli.ts b/packages/cli/src/cli.ts new file mode 100644 index 0000000000..16287aad7b --- /dev/null +++ b/packages/cli/src/cli.ts @@ -0,0 +1,68 @@ +import chalk from 'chalk' +import { Command } from 'commander' +import { generator, runGenerator, getContext } from '@feathershq/pinion' +import { FeathersBaseContext, version } from './commons' + +export * from 'commander' +export { chalk } + +export const commandRunner = (name: string) => async (options: any) => { + const ctx = getContext({ + ...options + }) + + await generator(ctx) + .then(runGenerator(__dirname, name, 'index')) + .catch((error) => { + const { logger } = ctx.pinion + + logger.error(`Error: ${chalk.white(error.message)}`) + }) +} + +export const program = new Command() + +program + .name('feathers') + .description('The Feathers command line interface 🕊️') + .version(version) + .showHelpAfterError() + +const generate = program.command('generate').alias('g') + +generate + .command('app') + .description('Generate a new application') + .option('--name ', 'The name of the application') + .action(commandRunner('app')) + +generate + .command('service') + .description('Generate a new service') + .option('--name ', 'The service name') + .option('--path ', 'The path to register the service on') + .option('--type ', 'The service type (knex, mongodb, custom)') + .action(commandRunner('service')) + +generate + .command('hook') + .description('Generate a hook') + .option('--name ', 'The name of the hook') + .option('--type ', 'The hook type (around or regular)') + .action(commandRunner('hook')) + +generate + .command('connection') + .description('Add a new database connection') + .action(commandRunner('connection')) + +generate + .command('authentication') + .description('Add authentication to the application') + .action(commandRunner('authentication')) + +generate.description( + `Run a generator. Currently available: \n ${generate.commands + .map((cmd) => `${chalk.blue(cmd.name())}: ${cmd.description()} `) + .join('\n ')}` +) diff --git a/packages/cli/src/commons.ts b/packages/cli/src/commons.ts new file mode 100644 index 0000000000..d21a031ac7 --- /dev/null +++ b/packages/cli/src/commons.ts @@ -0,0 +1,276 @@ +import fs from 'fs' +import { join } from 'path' +import { PackageJson } from 'type-fest' +import { readFile, writeFile } from 'fs/promises' +import { + Callable, + PinionContext, + loadJSON, + fromFile, + getCallable, + renderTemplate, + inject, + Location +} from '@feathershq/pinion' +import * as ts from 'typescript' +import prettier, { Options as PrettierOptions } from 'prettier' +import path from 'path' + +export const { version } = JSON.parse(fs.readFileSync(join(__dirname, '..', 'package.json')).toString()) + +export type DependencyVersions = { [key: string]: string } + +/** + * The database types supported by this generator + */ +export type DatabaseType = 'mongodb' | 'mysql' | 'postgresql' | 'sqlite' | 'mssql' + +/** + * Returns the name of the Feathers database adapter for a supported database type + * + * @param database The type of the database + * @returns The name of the adapter + */ +export const getDatabaseAdapter = (database: DatabaseType) => (database === 'mongodb' ? 'mongodb' : 'knex') + +export type FeathersAppInfo = { + /** + * The application language + */ + language: 'ts' | 'js' + /** + * The main database + */ + database: DatabaseType + /** + * The package manager used + */ + packager: 'yarn' | 'npm' + /** + * A list of all chosen transports + */ + transports: ('rest' | 'websockets')[] + /** + * The HTTP framework used + */ + framework: 'koa' | 'express' + /** + * The main schema definition format + */ + schema: 'typebox' | 'json' +} + +export interface AppPackageJson extends PackageJson { + feathers?: FeathersAppInfo +} + +export interface FeathersBaseContext extends PinionContext { + /** + * Information about the Feathers application (like chosen language, database etc.) + * usually taken from `package.json` + */ + feathers: FeathersAppInfo + /** + * The package.json file + */ + pkg: AppPackageJson + /** + * The folder where source files are put + */ + lib: string + /** + * The folder where test files are put + */ + test: string + /** + * The language the app is generated in + */ + language: 'js' | 'ts' + /** + * A list dependencies that should be installed with a certain version. + * Used for installing development dependencies during testing. + */ + dependencyVersions?: DependencyVersions +} + +/** + * Returns dependencies with the versions from the context attached (if available) + * + * @param dependencies The dependencies to install + * @param versions The dependency version list + * @returns A list of dependencies with their versions + */ +export const addVersions = (dependencies: string[], versions: DependencyVersions) => + dependencies.map((dep) => `${dep}@${versions[dep] ? versions[dep] : 'latest'}`) + +/** + * Loads the application package.json and populates information like the library and test directory + * and Feathers app specific information. + * + * @returns The updated context + */ +export const initializeBaseContext = + () => + (ctx: C) => + Promise.resolve(ctx) + .then(loadJSON(fromFile('package.json'), (pkg) => ({ pkg }), {})) + .then( + loadJSON(path.join(__dirname, '..', 'package.json'), (pkg: PackageJson) => ({ + dependencyVersions: { + ...pkg.devDependencies, + ...ctx.dependencyVersions, + '@feathersjs/cli': version + } + })) + ) + .then((ctx) => ({ + ...ctx, + lib: ctx.pkg?.directories?.lib || 'src', + test: ctx.pkg?.directories?.test || 'test', + language: ctx.language || ctx.pkg?.feathers?.language, + feathers: ctx.pkg?.feathers + })) + +/** + * Checks if the current context contains a valid generated application. This is necesary for most + * generators (besides the app generator). + * + * @param ctx The context to check against + * @returns Throws an error or returns the original context + */ +export const checkPreconditions = + () => + async (ctx: T) => { + if (!ctx.feathers) { + throw new Error(`Can not run generator since the current folder does not appear to be a Feathers application. +Either your package.json is missing or it does not have \`feathers\` property. +`) + } + + return ctx + } + +const importRegex = /from '(\..*)'/g +const escapeNewLines = (code: string) => code.replace(/\n\n/g, '\n/* :newline: */') +const restoreNewLines = (code: string) => code.replace(/\/\* :newline: \*\//g, '\n') +const fixLocalImports = (code: string) => code.replace(importRegex, "from '$1.js'") + +/** + * Returns the transpiled and prettified JavaScript for a TypeScript source code + * + * @param typescript The TypeScript source code + * @param options TypeScript transpilation options + * @returns The formatted JavaScript source code + */ +export const getJavaScript = (typescript: string, options: ts.TranspileOptions = {}) => { + const source = escapeNewLines(typescript) + const transpiled = ts.transpileModule(source, { + ...options, + compilerOptions: { + module: ts.ModuleKind.ESNext, + target: ts.ScriptTarget.ES2020, + preserveValueImports: true, + ...options.compilerOptions + } + }) + + return fixLocalImports(restoreNewLines(transpiled.outputText)) +} + +const getFileName = async ( + target: Callable, + ctx: C +) => `${await getCallable(target, ctx)}.${ctx.language}` + +/** + * The default configuration for prettifying files + */ +export const PRETTIERRC: PrettierOptions = { + tabWidth: 2, + useTabs: false, + printWidth: 110, + semi: false, + trailingComma: 'none', + singleQuote: true +} + +/* + * Format a source file using Prettier. Will use the local configuration, the settings set in + * `options` or a default configuration + * + * @param target The file to prettify + * @param options The Prettier options + * @returns The updated context + */ +export const prettify = + ( + target: Callable, + options: PrettierOptions = PRETTIERRC + ) => + async (ctx: C) => { + const fileName = await getFileName(target, ctx) + const config = (await prettier.resolveConfig(ctx.cwd)) || options + const content = (await readFile(fileName)).toString() + + try { + await writeFile( + fileName, + await prettier.format(content, { + parser: ctx.language === 'ts' ? 'typescript' : 'babel', + ...config + }) + ) + } catch (error: any) { + throw new Error(`Error prettifying ${fileName}: ${error.message}`) + } + + return ctx + } + +/** + * Render a source file template for the language set in the context. + * + * @param templates The JavaScript and TypeScript template to render + * @param target The target filename without extension (will be added based on language) + * @returns The updated context + */ +export const renderSource = + ( + template: Callable, + target: Callable, + options?: { force: boolean } + ) => + async (ctx: C) => { + const { language } = ctx + const fileName = await getFileName(target, ctx) + const content = language === 'js' ? getJavaScript(await getCallable(template, ctx)) : template + const renderer = renderTemplate(content, fileName, options) + + return renderer(ctx).then(prettify(target)) + } + +/** + * Inject a source template as the language set in the context. + * + * @param template The source template to render + * @param location The location to inject the code to. Must use the target language. + * @param target The target file name + * @param transpile Set to `false` if the code should not be transpiled to JavaScript + * @returns + */ +export const injectSource = + ( + template: Callable, + location: Location, + target: Callable, + transpile = true + ) => + async (ctx: C) => { + const { language } = ctx + const source = + language === 'js' && transpile ? getJavaScript(await getCallable(template, ctx)) : template + const fileName = await getFileName(target, ctx) + const injector = inject(source, location, fileName) + + return injector(ctx).then(prettify(target)) + } diff --git a/packages/cli/src/connection/index.ts b/packages/cli/src/connection/index.ts new file mode 100644 index 0000000000..a836e41260 --- /dev/null +++ b/packages/cli/src/connection/index.ts @@ -0,0 +1,123 @@ +import { generator, runGenerator, prompt, install, mergeJSON, toFile } from '@feathershq/pinion' +import chalk from 'chalk' +import { + FeathersBaseContext, + DatabaseType, + getDatabaseAdapter, + addVersions, + checkPreconditions, + initializeBaseContext +} from '../commons' + +export interface ConnectionGeneratorContext extends FeathersBaseContext { + name?: string + database: DatabaseType + connectionString: string + dependencies: string[] +} + +export type ConnectionGeneratorArguments = FeathersBaseContext & + Partial> + +export const defaultConnectionString = (type: DatabaseType, name: string) => { + const connectionStrings = { + mongodb: `mongodb://localhost:27017/${name}`, + mysql: `mysql://root:@localhost:3306/${name}`, + postgresql: `postgres://postgres:@localhost:5432/${name}`, + sqlite: `${name}.sqlite`, + mssql: `mssql://root:password@localhost:1433/${name}` + } + + return connectionStrings[type] +} + +export const prompts = ({ database, connectionString, pkg, name }: ConnectionGeneratorArguments) => [ + { + name: 'database', + type: 'list', + when: !database, + message: 'Which database are you connecting to?', + suffix: chalk.grey(' Other databases can be added at any time'), + choices: [ + { value: 'sqlite', name: 'SQLite' }, + { value: 'mongodb', name: 'MongoDB' }, + { value: 'postgresql', name: 'PostgreSQL' }, + { value: 'mysql', name: 'MySQL/MariaDB' }, + { value: 'mssql', name: 'Microsoft SQL' } + ] + }, + { + name: 'connectionString', + type: 'input', + when: !connectionString, + message: 'Enter your database connection string', + default: (answers: { name?: string; database: DatabaseType }) => + defaultConnectionString(answers.database, answers.name || name || pkg.name) + } +] + +export const DATABASE_CLIENTS = { + mongodb: 'mongodb', + sqlite: 'sqlite3', + postgresql: 'pg', + mysql: 'mysql', + mssql: 'tedious' +} + +export const getDatabaseClient = (database: DatabaseType) => DATABASE_CLIENTS[database] + +export const generate = (ctx: ConnectionGeneratorArguments) => + generator(ctx) + .then(initializeBaseContext()) + .then(checkPreconditions()) + .then(prompt(prompts)) + .then( + runGenerator( + __dirname, + 'templates', + ({ database }) => `${getDatabaseAdapter(database)}.tpl` + ) + ) + .then( + mergeJSON( + ({ connectionString, database }) => + getDatabaseAdapter(database) === 'knex' + ? { + [database]: { + client: getDatabaseClient(database), + connection: connectionString, + ...(database === 'sqlite' ? { useNullAsDefault: true } : {}) + } + } + : { + [database]: connectionString + }, + toFile('config', 'default.json') + ) + ) + .then((ctx: ConnectionGeneratorContext) => { + const dependencies: string[] = [] + const adapter = getDatabaseAdapter(ctx.database) + const dbClient = getDatabaseClient(ctx.database) + + dependencies.push(`@feathersjs/${adapter}`) + + if (adapter === 'knex') { + dependencies.push('knex') + } + + dependencies.push(dbClient) + + if (ctx.dependencies) { + return { + ...ctx, + dependencies: [...ctx.dependencies, ...dependencies] + } + } + + return install( + addVersions(dependencies, ctx.dependencyVersions), + false, + ctx.feathers.packager + )(ctx) + }) diff --git a/packages/cli/src/connection/templates/knex.tpl.ts b/packages/cli/src/connection/templates/knex.tpl.ts new file mode 100644 index 0000000000..bbc0f5a9df --- /dev/null +++ b/packages/cli/src/connection/templates/knex.tpl.ts @@ -0,0 +1,63 @@ +import { generator, toFile, before, mergeJSON } from '@feathershq/pinion' +import { ConnectionGeneratorContext } from '../index' +import { injectSource, renderSource } from '../../commons' + +const template = ({ database }: ConnectionGeneratorContext) => /* ts */ `import knex from 'knex' +import type { Knex } from 'knex' +import type { Application } from './declarations' + +declare module './declarations' { + interface Configuration { + ${database}Client: Knex + } +} + +export const ${database} = (app: Application) => { + const config = app.get('${database}') + const db = knex(config!) + + app.set('${database}Client', db) +} +` + +const knexfile = ({ + lib, + language, + database +}: ConnectionGeneratorContext) => /* ts */ `import { app } from './${lib}/app' + +// Load our database connection info from the app configuration +const config = app.get('${database}') + +${language === 'js' ? 'export default config' : 'module.exports = config'} +` + +const importTemplate = ({ database }: ConnectionGeneratorContext) => + `import { ${database} } from './${database}'` +const configureTemplate = ({ database }: ConnectionGeneratorContext) => `app.configure(${database})` + +const toAppFile = toFile(({ lib }) => [lib, 'app']) + +export const generate = (ctx: ConnectionGeneratorContext) => + generator(ctx) + .then( + renderSource( + template, + toFile(({ lib, database }) => [lib, database]) + ) + ) + .then(renderSource(knexfile, toFile('knexfile'))) + .then( + mergeJSON( + { + scripts: { + migrate: 'knex migrate:latest', + 'migrate:make': 'knex migrate:make', + test: 'cross-env NODE_ENV=test npm run migrate && npm run mocha' + } + }, + toFile('package.json') + ) + ) + .then(injectSource(importTemplate, before('import { services } from'), toAppFile)) + .then(injectSource(configureTemplate, before('app.configure(services)'), toAppFile)) diff --git a/packages/cli/src/connection/templates/mongodb.tpl.ts b/packages/cli/src/connection/templates/mongodb.tpl.ts new file mode 100644 index 0000000000..4c17545d91 --- /dev/null +++ b/packages/cli/src/connection/templates/mongodb.tpl.ts @@ -0,0 +1,38 @@ +import { generator, toFile, before } from '@feathershq/pinion' +import { ConnectionGeneratorContext } from '../index' +import { injectSource, renderSource } from '../../commons' + +const template = ({}: ConnectionGeneratorContext) => /* ts */ `import { MongoClient } from 'mongodb' +import type { Db } from 'mongodb' +import type { Application } from './declarations' + +declare module './declarations' { + interface Configuration { + mongodbClient: Promise + } +} + +export const mongodb = (app: Application) => { + const connection = app.get('mongodb') as string + const database = connection.substring(connection.lastIndexOf('/') + 1) + const mongoClient = MongoClient.connect(connection) + .then(client => client.db(database)) + + app.set('mongodbClient', mongoClient) +} +` + +const importTemplate = "import { mongodb } from './mongodb'" +const configureTemplate = 'app.configure(mongodb)' +const toAppFile = toFile(({ lib }) => [lib, 'app']) + +export const generate = (ctx: ConnectionGeneratorContext) => + generator(ctx) + .then( + renderSource( + template, + toFile(({ lib }) => lib, 'mongodb') + ) + ) + .then(injectSource(importTemplate, before('import { services } from'), toAppFile)) + .then(injectSource(configureTemplate, before('app.configure(services)'), toAppFile)) diff --git a/packages/cli/src/hook/index.ts b/packages/cli/src/hook/index.ts new file mode 100644 index 0000000000..3f0b430d98 --- /dev/null +++ b/packages/cli/src/hook/index.ts @@ -0,0 +1,47 @@ +import { generator, prompt, runGenerators } from '@feathershq/pinion' +import _ from 'lodash' +import { checkPreconditions, FeathersBaseContext, initializeBaseContext } from '../commons' + +export interface HookGeneratorContext extends FeathersBaseContext { + name: string + camelName: string + kebabName: string + type: 'regular' | 'around' +} + +export const generate = (ctx: HookGeneratorContext) => + generator(ctx) + .then(initializeBaseContext()) + .then(checkPreconditions()) + .then( + prompt(({ type, name }) => [ + { + type: 'input', + name: 'name', + message: 'What is the name of the hook?', + when: !name + }, + { + name: 'type', + type: 'list', + when: !type, + message: 'What kind of hook is it?', + choices: [ + { value: 'around', name: 'Around' }, + { value: 'regular', name: 'Before, After or Error' } + ] + } + ]) + ) + .then((ctx) => { + const { name } = ctx + const kebabName = _.kebabCase(name) + const camelName = _.camelCase(name) + + return { + ...ctx, + kebabName, + camelName + } + }) + .then(runGenerators(__dirname, 'templates')) diff --git a/packages/cli/src/hook/templates/hook.tpl.ts b/packages/cli/src/hook/templates/hook.tpl.ts new file mode 100644 index 0000000000..8671e9d980 --- /dev/null +++ b/packages/cli/src/hook/templates/hook.tpl.ts @@ -0,0 +1,31 @@ +import { generator, toFile } from '@feathershq/pinion' +import { HookGeneratorContext } from '../index' +import { renderSource } from '../../commons' + +const aroundTemplate = ({ + camelName, + name +}: HookGeneratorContext) => /* ts */ `import type { HookContext, NextFunction } from '../declarations' + +export const ${camelName} = async (context: HookContext, next: NextFunction) => { + console.log(\`Running hook ${name} on \${context.path}\.\${context.method}\`) + await next() +} +` + +const regularTemplate = ({ + camelName, + name +}: HookGeneratorContext) => /* ts */ `import type { HookContext } from '../declarations' + +export const ${camelName} = async (context: HookContext) => { + console.log(\`Running hook ${name} on \${context.path}\.\${context.method}\`) +}` + +export const generate = (ctx: HookGeneratorContext) => + generator(ctx).then( + renderSource( + (ctx) => (ctx.type === 'around' ? aroundTemplate(ctx) : regularTemplate(ctx)), + toFile(({ lib, kebabName }) => [lib, 'hooks', kebabName]) + ) + ) diff --git a/packages/cli/src/index.ts b/packages/cli/src/index.ts new file mode 100644 index 0000000000..f717fbb249 --- /dev/null +++ b/packages/cli/src/index.ts @@ -0,0 +1,2 @@ +export * from './cli' +export * from './commons' diff --git a/packages/cli/src/service/index.ts b/packages/cli/src/service/index.ts new file mode 100644 index 0000000000..3011cd155c --- /dev/null +++ b/packages/cli/src/service/index.ts @@ -0,0 +1,191 @@ +import _ from 'lodash' +import { generator, runGenerator, runGenerators, prompt } from '@feathershq/pinion' + +import { + checkPreconditions, + FeathersBaseContext, + getDatabaseAdapter, + initializeBaseContext +} from '../commons' + +export interface ServiceGeneratorContext extends FeathersBaseContext { + /** + * The chosen service name + */ + name: string + /** + * The path the service is registered on + */ + path: string + /** + * The list of subfolders this service is in + */ + folder: string[] + /** + * The `camelCase` service name starting with a lowercase letter + */ + camelName: string + /** + * The `CamelCase` service name starting with an uppercase letter + */ + upperName: string + /** + * The service class name combined as `CamelCaseService` + */ + className: string + /** + * A kebab-cased (filename friendly) version of the service name + */ + kebabName: string + /** + * The actual filename (the last element of the path) + */ + fileName: string + /** + * The kebab-cased name of the path. Will be used for e.g. database names + */ + kebabPath: string + /** + * Indicates how many file paths we should go up to import other things (e.g. `../../`) + */ + relative: string + /** + * The chosen service type + */ + type: 'knex' | 'mongodb' | 'custom' + /** + * Which schema definition format to use + */ + schema: 'typebox' | 'json' | false + /** + * Wether this service uses authentication + */ + authentication: boolean + /** + * Set to true if this service is for an authentication entity + */ + isEntityService?: boolean +} + +/** + * Parameters the generator is called with + */ +export type ServiceGeneratorArguments = FeathersBaseContext & + Partial< + Pick + > + +export const generate = (ctx: ServiceGeneratorArguments) => + generator(ctx) + .then(initializeBaseContext()) + .then(checkPreconditions()) + .then( + prompt( + ({ name, path, type, schema, authentication, isEntityService, feathers }) => [ + { + name: 'name', + type: 'input', + when: !name, + message: 'What is the name of your service?', + validate: (input) => { + if (!input || input === 'authentication') { + return 'Invalid service name' + } + + return true + } + }, + { + name: 'path', + type: 'input', + when: !path, + message: 'Which path should the service be registered on?', + default: (answers: ServiceGeneratorArguments) => `${_.kebabCase(answers.name)}`, + validate: (input) => { + if (!input || input === 'authentication') { + return 'Invalid service path' + } + + return true + } + }, + { + name: 'authentication', + type: 'confirm', + when: authentication === undefined && !isEntityService, + message: 'Does this service require authentication?' + }, + { + name: 'type', + type: 'list', + when: !type, + message: 'What kind of service is it?', + default: getDatabaseAdapter(feathers?.database), + choices: [ + { + value: 'knex', + name: 'SQL' + }, + { + value: 'mongodb', + name: 'MongoDB' + }, + { + value: 'custom', + name: 'A custom service' + } + ] + }, + { + name: 'schema', + type: 'list', + when: schema === undefined, + message: 'Which schema definition format do you want to use?', + default: feathers?.schema, + choices: [ + { + value: 'typebox', + name: 'TypeBox' + }, + { + value: 'json', + name: 'JSON schema' + }, + { + value: false, + name: 'No schema' + } + ] + } + ] + ) + ) + .then(async (ctx): Promise => { + const { name, path, type } = ctx + const kebabName = _.kebabCase(name) + const camelName = _.camelCase(name) + const upperName = _.upperFirst(camelName) + const className = `${upperName}Service` + + const folder = path.split('/').filter((el) => el !== '') + const relative = ['', ...folder].map(() => '..').join('/') + const fileName = _.last(folder) + const kebabPath = _.kebabCase(path) + + return { + name, + type, + path, + folder, + fileName, + upperName, + className, + kebabName, + camelName, + kebabPath, + relative, + ...ctx + } + }) + .then(runGenerators(__dirname, 'templates')) + .then(runGenerator(__dirname, 'type', ({ type }) => `${type}.tpl`)) diff --git a/packages/cli/src/service/templates/client.tpl.ts b/packages/cli/src/service/templates/client.tpl.ts new file mode 100644 index 0000000000..af6d751a98 --- /dev/null +++ b/packages/cli/src/service/templates/client.tpl.ts @@ -0,0 +1,64 @@ +import { generator, toFile, when, after, before } from '@feathershq/pinion' +import { injectSource } from '../../commons' +import { ServiceGeneratorContext } from '../index' + +const importTemplate = ({ + upperName, + folder, + fileName, + className +}: ServiceGeneratorContext) => /* ts */ `import type { + ${upperName}, + ${upperName}Data, + ${upperName}Query, + ${className} +} from './services/${folder.join('/')}/${fileName}' +export type { + ${upperName}, + ${upperName}Data, + ${upperName}Query +} +` + +const methodsTemplate = ({ camelName, upperName, className, type }: ServiceGeneratorContext) => + `const ${camelName}ServiceMethods = ['find', 'get', 'create', 'update', 'patch', 'remove'] as const +type ${upperName}ClientService = Pick<${className}${ + type !== 'custom' ? `>` : '' + }, typeof ${camelName}ServiceMethods[number]> +` + +const declarationTemplate = ({ path, upperName }: ServiceGeneratorContext) => + ` '${path}': ${upperName}ClientService` + +const registrationTemplate = ({ + camelName, + path +}: ServiceGeneratorContext) => ` client.use('${path}', connection.service('${path}'), { + methods: ${camelName}ServiceMethods +})` + +const toClientFile = toFile(({ lib }) => [lib, 'client']) + +export const generate = async (ctx: ServiceGeneratorContext) => + generator(ctx) + .then( + injectSource( + registrationTemplate, + before('return client'), + toFile(({ lib }) => [lib, 'client']) + ) + ) + .then( + when( + (ctx) => ctx.language === 'js', + injectSource(methodsTemplate, before('\nexport const createClient'), toClientFile) + ) + ) + .then( + when( + (ctx) => ctx.language === 'ts', + injectSource(methodsTemplate, before('\nexport interface ServiceTypes'), toClientFile), + injectSource(importTemplate, after("from '@feathersjs/feathers'"), toClientFile), + injectSource(declarationTemplate, after('export interface ServiceTypes'), toClientFile) + ) + ) diff --git a/packages/cli/src/service/templates/schema.json.tpl.ts b/packages/cli/src/service/templates/schema.json.tpl.ts new file mode 100644 index 0000000000..f713559151 --- /dev/null +++ b/packages/cli/src/service/templates/schema.json.tpl.ts @@ -0,0 +1,87 @@ +import { generator, toFile, when } from '@feathershq/pinion' +import { renderSource } from '../../commons' +import { ServiceGeneratorContext } from '../index' + +const template = ({ + camelName, + upperName, + relative, + type +}: ServiceGeneratorContext) => /* ts */ `import { resolve, getDataValidator, getValidator, querySyntax } from '@feathersjs/schema' +import type { FromSchema } from '@feathersjs/schema' + +import type { HookContext } from '${relative}/declarations' +import { dataValidator, queryValidator } from '${relative}/schemas/validators' + +// Main data model schema +export const ${camelName}Schema = { + $id: '${upperName}', + type: 'object', + additionalProperties: false, + required: [ '${type === 'mongodb' ? '_id' : 'id'}', 'text' ], + properties: { + ${type === 'mongodb' ? '_id' : 'id'}: { + type: '${type === 'mongodb' ? 'string' : 'number'}' + }, + text: { + type: 'string' + } + } +} as const +export type ${upperName} = FromSchema +export const ${camelName}Resolver = resolve<${upperName}, HookContext>({ + properties: {} +}) +export const ${camelName}ExternalResolver = resolve<${upperName}, HookContext>({ + properties: {} +}) + +// Schema for creating new data +export const ${camelName}DataSchema = { + $id: '${upperName}Data', + type: 'object', + additionalProperties: false, + required: [ 'text' ], + properties: { + text: { + type: 'string' + } + } +} as const +export type ${upperName}Data = FromSchema +export const ${camelName}DataValidator = getDataValidator(${camelName}DataSchema, dataValidator) +export const ${camelName}DataResolver = resolve<${upperName}Data, HookContext>({ + properties: {} +}) + +// Schema for allowed query properties +export const ${camelName}QuerySchema = { + $id: '${upperName}Query', + type: 'object', + additionalProperties: false, + properties: { + ...querySyntax(${camelName}Schema.properties) + } +} as const +export type ${upperName}Query = FromSchema +export const ${camelName}QueryValidator = getValidator(${camelName}QuerySchema, queryValidator) +export const ${camelName}QueryResolver = resolve<${upperName}Query, HookContext>({ + properties: {} +}) +` + +export const generate = (ctx: ServiceGeneratorContext) => + generator(ctx).then( + when( + ({ schema }) => schema === 'json', + renderSource( + template, + toFile(({ lib, folder, fileName }: ServiceGeneratorContext) => [ + lib, + 'services', + ...folder, + `${fileName}.schema` + ]) + ) + ) + ) diff --git a/packages/cli/src/service/templates/schema.typebox.tpl.ts b/packages/cli/src/service/templates/schema.typebox.tpl.ts new file mode 100644 index 0000000000..761472a105 --- /dev/null +++ b/packages/cli/src/service/templates/schema.typebox.tpl.ts @@ -0,0 +1,67 @@ +import { generator, toFile, when } from '@feathershq/pinion' +import { renderSource } from '../../commons' +import { ServiceGeneratorContext } from '../index' + +const template = ({ + camelName, + upperName, + relative, + type +}: ServiceGeneratorContext) => /* ts */ `import { resolve } from '@feathersjs/schema' +import { Type, getDataValidator, getValidator, querySyntax } from '@feathersjs/typebox' +import type { Static } from '@feathersjs/typebox' + +import type { HookContext } from '${relative}/declarations' +import { dataValidator, queryValidator } from '${relative}/schemas/validators' + +// Main data model schema +export const ${camelName}Schema = Type.Object({ + ${type === 'mongodb' ? '_id: Type.String()' : 'id: Type.Number()'}, + text: Type.String() + }, { $id: '${upperName}', additionalProperties: false }) +export type ${upperName} = Static +export const ${camelName}Resolver = resolve<${upperName}, HookContext>({ + properties: {} +}) + +export const ${camelName}ExternalResolver = resolve<${upperName}, HookContext>({ + properties: {} +}) + +// Schema for creating new entries +export const ${camelName}DataSchema = Type.Pick(${camelName}Schema, ['text'], { + $id: '${upperName}Data', additionalProperties: false +}) +export type ${upperName}Data = Static +export const ${camelName}DataValidator = getDataValidator(${camelName}DataSchema, dataValidator) +export const ${camelName}DataResolver = resolve<${upperName}, HookContext>({ + properties: {} +}) + +// Schema for allowed query properties +export const ${camelName}QueryProperties = Type.Pick(${camelName}Schema, [ + '${type === 'mongodb' ? '_id' : 'id'}', 'text' +], { additionalProperties: false }) +export const ${camelName}QuerySchema = querySyntax(${camelName}QueryProperties) +export type ${upperName}Query = Static +export const ${camelName}QueryValidator = getValidator(${camelName}QuerySchema, queryValidator) +export const ${camelName}QueryResolver = resolve<${upperName}Query, HookContext>({ + properties: {} +}) +` + +export const generate = (ctx: ServiceGeneratorContext) => + generator(ctx).then( + when( + ({ schema }) => schema === 'typebox', + renderSource( + template, + toFile(({ lib, folder, fileName }: ServiceGeneratorContext) => [ + lib, + 'services', + ...folder, + `${fileName}.schema` + ]) + ) + ) + ) diff --git a/packages/cli/src/service/templates/service.tpl.ts b/packages/cli/src/service/templates/service.tpl.ts new file mode 100644 index 0000000000..0e397471f2 --- /dev/null +++ b/packages/cli/src/service/templates/service.tpl.ts @@ -0,0 +1,134 @@ +import { generator, toFile, after, prepend } from '@feathershq/pinion' +import { injectSource, renderSource } from '../../commons' +import { ServiceGeneratorContext } from '../index' + +export const template = ({ + camelName, + authentication, + isEntityService, + path, + className, + relative, + schema, + fileName +}: ServiceGeneratorContext) => /* ts */ ` +${authentication || isEntityService ? `import { authenticate } from '@feathersjs/authentication'` : ''} +${ + schema + ? ` +import { hooks as schemaHooks } from '@feathersjs/schema' + +import { + ${camelName}DataValidator, + ${camelName}QueryValidator, + ${camelName}Resolver, + ${camelName}DataResolver, + ${camelName}QueryResolver, + ${camelName}ExternalResolver +} from './${fileName}.schema' +` + : '' +} + +import type { Application } from '${relative}/declarations' +import { ${className}, getOptions } from './${fileName}.class' + +export * from './${fileName}.class' +${schema ? `export * from './${fileName}.schema'` : ''} + +// A configure function that registers the service and its hooks via \`app.configure\` +export const ${camelName} = (app: Application) => { + // Register our service on the Feathers application + app.use('${path}', new ${className}(getOptions(app)), { + // A list of all methods this service exposes externally + methods: ['find', 'get', 'create', 'update', 'patch', 'remove'], + // You can add additional custom events to be sent to clients here + events: [] + }) + // Initialize hooks + app.service('${path}').hooks({ + around: { + all: [${ + authentication + ? ` + authenticate('jwt'),` + : '' + } + ]${ + isEntityService + ? `, + find: [ authenticate('jwt') ], + get: [ authenticate('jwt') ], + create: [], + update: [ authenticate('jwt') ], + patch: [ authenticate('jwt') ], + remove: [ authenticate('jwt') ]` + : '' + } + }, + before: { + all: [${ + schema + ? ` + schemaHooks.validateQuery(${camelName}QueryValidator), + schemaHooks.validateData(${camelName}DataValidator), + schemaHooks.resolveQuery(${camelName}QueryResolver), + schemaHooks.resolveData(${camelName}DataResolver) + ` + : '' + }] + }, + after: { + all: [${ + schema + ? ` + schemaHooks.resolveResult(${camelName}Resolver), + schemaHooks.resolveExternal(${camelName}ExternalResolver) + ` + : '' + }] + }, + error: { + all: [] + } + }) +} + +// Add this service to the service type index +declare module '${relative}/declarations' { + interface ServiceTypes { + '${path}': ${className} + } +} +` + +const toServiceIndex = toFile(({ lib }: ServiceGeneratorContext) => [lib, 'services', `index`]) + +export const generate = (ctx: ServiceGeneratorContext) => + generator(ctx) + .then( + renderSource( + template, + toFile(({ lib, fileName, folder }: ServiceGeneratorContext) => [ + lib, + 'services', + ...folder, + `${fileName}` + ]) + ) + ) + .then( + injectSource( + ({ camelName, folder, fileName }) => + `import { ${camelName} } from './${folder.join('/')}/${fileName}'`, + prepend(), + toServiceIndex + ) + ) + .then( + injectSource( + ({ camelName }) => ` app.configure(${camelName})`, + after('export const services'), + toServiceIndex + ) + ) diff --git a/packages/cli/src/service/templates/test.tpl.ts b/packages/cli/src/service/templates/test.tpl.ts new file mode 100644 index 0000000000..fe9ee5a887 --- /dev/null +++ b/packages/cli/src/service/templates/test.tpl.ts @@ -0,0 +1,28 @@ +import { generator, toFile } from '@feathershq/pinion' +import { renderSource } from '../../commons' +import { ServiceGeneratorContext } from '../index' + +const template = ({ relative, lib, path }: ServiceGeneratorContext) => /* ts */ `import assert from 'assert' +import { app } from '../${relative}/${lib}/app' + +describe('${path} service', () => { + it('registered the service', () => { + const service = app.service('${path}') + + assert.ok(service, 'Registered the service') + }) +}) +` + +export const generate = (ctx: ServiceGeneratorContext) => + generator(ctx).then( + renderSource( + template, + toFile(({ test, folder, fileName }) => [ + test, + 'services', + ...folder, + `${fileName}.test` + ]) + ) + ) diff --git a/packages/cli/src/service/type/custom.tpl.ts b/packages/cli/src/service/type/custom.tpl.ts new file mode 100644 index 0000000000..1c244601c9 --- /dev/null +++ b/packages/cli/src/service/type/custom.tpl.ts @@ -0,0 +1,99 @@ +import { generator, toFile } from '@feathershq/pinion' +import { renderSource } from '../../commons' +import { ServiceGeneratorContext } from '../index' + +export const template = ({ className, upperName, schema, fileName, relative }: ServiceGeneratorContext) => ` +import type { Id, NullableId, Params } from '@feathersjs/feathers' + +import type { Application } from '${relative}/declarations' +${ + schema + ? `import type { + ${upperName}, + ${upperName}Data, + ${upperName}Query +} from './${fileName}.schema' +` + : ` +export type ${upperName} = any +export type ${upperName}Data = any +export type ${upperName}Query = any +` +} + +export interface ${className}Options { + app: Application +} + +export interface ${upperName}Params extends Params<${upperName}Query> { + +} + +// This is a skeleton for a custom service class. Remove or add the methods you need here +export class ${className} { + constructor (public options: ${className}Options) { + } + + async find (_params?: ${upperName}Params): Promise<${upperName}[]> { + return [] + } + + async get (id: Id, _params?: ${upperName}Params): Promise<${upperName}> { + return { + id: 0, + text: \`A new message with ID: \${id}!\` + } + } + + async create (data: ${upperName}Data, params?: ${upperName}Params): Promise<${upperName}> + async create (data: ${upperName}Data[], params?: ${upperName}Params): Promise<${upperName}[]> + async create (data: ${upperName}Data|${upperName}Data[], params?: ${upperName}Params): Promise<${upperName}|${upperName}[]> { + if (Array.isArray(data)) { + return Promise.all(data.map(current => this.create(current, params))); + } + + return { + id: 0, + ...data + } + } + + async update (id: NullableId, data: ${upperName}Data, _params?: ${upperName}Params): Promise<${upperName}> { + return { + id: 0, + ...data + } + } + + async patch (id: NullableId, data: ${upperName}Data, _params?: ${upperName}Params): Promise<${upperName}> { + return { + id: 0, + ...data + } + } + + async remove (id: NullableId, _params?: ${upperName}Params): Promise<${upperName}> { + return { + id: 0, + text: 'removed' + } + } +} + +export const getOptions = (app: Application) => { + return { app } +} +` + +export const generate = (ctx: ServiceGeneratorContext) => + generator(ctx).then( + renderSource( + template, + toFile(({ lib, folder, fileName }) => [ + lib, + 'services', + ...folder, + `${fileName}.class` + ]) + ) + ) diff --git a/packages/cli/src/service/type/knex.tpl.ts b/packages/cli/src/service/type/knex.tpl.ts new file mode 100644 index 0000000000..0dd258746a --- /dev/null +++ b/packages/cli/src/service/type/knex.tpl.ts @@ -0,0 +1,88 @@ +import { generator, toFile } from '@feathershq/pinion' +import { renderSource } from '../../commons' +import { ServiceGeneratorContext } from '../index' + +const migrationTemplate = ({ + kebabPath +}: ServiceGeneratorContext) => /* ts */ `import type { Knex } from 'knex' + +export async function up(knex: Knex): Promise { + await knex.schema.createTable('${kebabPath}', table => { + table.increments('id') + table.string('text') + }) +} + +export async function down(knex: Knex): Promise { + await knex.schema.dropTable('${kebabPath}') +} +` + +export const template = ({ + className, + upperName, + feathers, + schema, + fileName, + relative +}: ServiceGeneratorContext) => /* ts */ `import type { Params } from '@feathersjs/feathers' +import { KnexService } from '@feathersjs/knex' +import type { KnexAdapterParams, KnexAdapterOptions } from '@feathersjs/knex' + +import type { Application } from '${relative}/declarations' +${ + schema + ? `import type { + ${upperName}, + ${upperName}Data, + ${upperName}Query +} from './${fileName}.schema' +` + : ` +export type ${upperName} = any +export type ${upperName}Data = any +export type ${upperName}Query = any +` +} + +export interface ${upperName}Params extends KnexAdapterParams<${upperName}Query> { +} + +// By default calls the standard Knex adapter service methods but can be customized with your own functionality. +export class ${className} + extends KnexService<${upperName}, ${upperName}Data, ServiceParams> { +} + +export const getOptions = (app: Application): KnexAdapterOptions => { + return { + paginate: app.get('paginate'), + Model: app.get('${feathers.database}Client'), + name: '${fileName}' + } +} +` + +export const generate = (ctx: ServiceGeneratorContext) => + generator(ctx) + .then( + renderSource( + template, + toFile(({ lib, folder, fileName }) => [ + lib, + 'services', + ...folder, + `${fileName}.class` + ]) + ) + ) + .then( + renderSource( + migrationTemplate, + toFile('migrations', ({ kebabName }) => { + // Probably not great but it works to align with the Knex migration file format + const migrationDate = new Date().toISOString().replace(/\D/g, '').substring(0, 14) + + return `${migrationDate}_${kebabName}` + }) + ) + ) diff --git a/packages/cli/src/service/type/mongodb.tpl.ts b/packages/cli/src/service/type/mongodb.tpl.ts new file mode 100644 index 0000000000..af819e404e --- /dev/null +++ b/packages/cli/src/service/type/mongodb.tpl.ts @@ -0,0 +1,59 @@ +import { generator, toFile } from '@feathershq/pinion' +import { renderSource } from '../../commons' +import { ServiceGeneratorContext } from '../index' + +export const template = ({ + className, + upperName, + schema, + fileName, + kebabPath, + relative +}: ServiceGeneratorContext) => /* ts */ `import type { Params } from '@feathersjs/feathers' +import { MongoDBService } from \'@feathersjs/mongodb\' +import type { MongoDBAdapterParams, MongoDBAdapterOptions } from \'@feathersjs/mongodb\' + +import type { Application } from '${relative}/declarations' +${ + schema + ? `import type { + ${upperName}, + ${upperName}Data, + ${upperName}Query +} from './${fileName}.schema' +` + : ` +export type ${upperName} = any +export type ${upperName}Data = any +export type ${upperName}Query = any +` +} + +export interface ${upperName}Params extends MongoDBAdapterParams<${upperName}Query> { +} + +// By default calls the standard MongoDB adapter service methods but can be customized with your own functionality. +export class ${className} + extends MongoDBService<${upperName}, ${upperName}Data, ServiceParams> { +} + +export const getOptions = (app: Application): MongoDBAdapterOptions => { + return { + paginate: app.get('paginate'), + Model: app.get('mongodbClient').then(db => db.collection('${kebabPath}')) + } +} +` + +export const generate = (ctx: ServiceGeneratorContext) => + generator(ctx).then( + renderSource( + template, + toFile(({ lib, folder, fileName }) => [ + lib, + 'services', + ...folder, + `${fileName}.class` + ]) + ) + ) diff --git a/packages/cli/test/build/.gitkeep b/packages/cli/test/build/.gitkeep new file mode 100644 index 0000000000..e69de29bb2 diff --git a/packages/cli/test/commons.test.ts b/packages/cli/test/commons.test.ts new file mode 100644 index 0000000000..f8bd9fb98a --- /dev/null +++ b/packages/cli/test/commons.test.ts @@ -0,0 +1,35 @@ +import { strictEqual } from 'assert' +import { getJavaScript } from '../src/commons' + +describe('common tests', () => { + it('getJavaScript returns transpiled JavaScript', () => { + const transpiled = getJavaScript( + `import bla from 'bla' +import something from './file' + +type X = { name: string } + +function test (arg: X) { + bla(something) +} + +// This is a comment +const otherThing: string = "Hello" +` + ) + + strictEqual( + transpiled, + `import bla from 'bla'; +import something from './file.js'; + + function test(arg) { + bla(something); +} + + // This is a comment +const otherThing = "Hello"; +` + ) + }) +}) diff --git a/packages/cli/test/generators.test.ts b/packages/cli/test/generators.test.ts new file mode 100644 index 0000000000..7a9e7b84fb --- /dev/null +++ b/packages/cli/test/generators.test.ts @@ -0,0 +1,144 @@ +/* eslint-disable @typescript-eslint/prefer-for-of */ +import os from 'os' +import path from 'path' +import { mkdtemp } from 'fs/promises' +import assert from 'assert' +import { getContext } from '@feathershq/pinion' + +import { AppGeneratorContext } from '../src/app' +import { FeathersBaseContext } from '../src/commons' +import { ConnectionGeneratorArguments } from '../src/connection' +import { ServiceGeneratorArguments } from '../src/service' +import { combinate, dependencyVersions } from './utils' + +import { generate as generateApp } from '../lib/app' +import { generate as generateConnection } from '../lib/connection' +import { generate as generateService } from '../lib/service' + +const matrix = { + language: ['js', 'ts'] as const, + framework: ['koa', 'express'] as const +} + +const defaultCombination = { + language: process.env.FEATHERS_LANGUAGE || 'ts', + framework: process.env.FEATHERS_FRAMEWORK || 'koa' +} + +const combinations = + process.version > 'v16.0.0' ? (process.env.CI ? combinate(matrix as any) : [defaultCombination]) : [] + +describe('@feathersjs/cli', () => { + for (const { language, framework } of combinations) { + describe(`${language} ${framework} app`, () => { + const name = `feathers_${language}_${framework}` + + let context: FeathersBaseContext + let cwd: string + + before(async () => { + cwd = await mkdtemp(path.join(os.tmpdir(), name + '-')) + console.log(cwd) + context = await generateApp( + getContext( + { + name, + framework, + language, + dependencyVersions, + lib: 'src', + description: 'A Feathers test app', + packager: 'npm', + database: 'sqlite', + connectionString: `${name}.sqlite`, + transports: ['rest', 'websockets'], + authStrategies: ['local', 'github'], + schema: 'typebox' + }, + { cwd } + ) + ) + }) + + it('generated app with SQLite and passes tests', async () => { + const testResult = await context.pinion.exec('npm', ['test'], { cwd }) + + assert.ok(context) + assert.strictEqual(testResult, 0) + }) + + it('generates a MongoDB connection and service and passes tests', async () => { + const connectionContext = await generateConnection( + getContext( + { + dependencyVersions, + database: 'mongodb' as const, + connectionString: `mongodb://localhost:27017/${name}` + }, + { cwd } + ) + ) + const mongoService1Context = await generateService( + getContext( + { + dependencyVersions, + name: 'testing', + path: 'path/to/test', + authentication: true, + type: 'mongodb', + schema: false + }, + { cwd } + ) + ) + const messageServiceContext = await generateService( + getContext( + { + dependencyVersions, + name: 'message', + path: 'messages', + authentication: true, + type: 'mongodb', + schema: 'typebox' + }, + { cwd } + ) + ) + const testResult = await context.pinion.exec('npm', ['test'], { cwd }) + + assert.ok(connectionContext) + assert.ok(mongoService1Context) + assert.ok(messageServiceContext) + assert.strictEqual(testResult, 0) + }) + + it('generates a custom service and passes tests', async () => { + const customServiceContext = await generateService( + getContext( + { + dependencyVersions, + name: 'Custom', + path: 'customized', + authentication: false, + type: 'custom', + schema: 'json' + }, + { cwd } + ) + ) + const testResult = await context.pinion.exec('npm', ['test'], { cwd }) + + assert.ok(customServiceContext) + assert.strictEqual(testResult, 0) + }) + + it('compiles successfully', async () => { + if (language === 'ts' && framework === 'koa') { + const testResult = await context.pinion.exec('npm', ['run', 'compile'], { cwd }) + + assert.strictEqual(testResult, 0) + } + }) + }) + } +}) diff --git a/packages/cli/test/utils.ts b/packages/cli/test/utils.ts new file mode 100644 index 0000000000..42c1745969 --- /dev/null +++ b/packages/cli/test/utils.ts @@ -0,0 +1,30 @@ +import path from 'path' +import pkg from '../package.json' +import { DependencyVersions } from '../src/commons' +import lernaConfig from '../../../lerna.json' + +export function combinate>(obj: O) { + let combos: { [k in keyof O]: O[k][number] }[] = [] + for (const key of Object.keys(obj)) { + const values = obj[key] + const all: any[] = [] + for (let i = 0; i < values.length; i++) { + for (let j = 0; j < (combos.length || 1); j++) { + const newCombo = { ...combos[j], [key]: values[i] } + all.push(newCombo) + } + } + combos = all + } + return combos +} + +export const dependencyVersions = Object.keys(pkg.devDependencies as any) + .filter((dep) => dep.startsWith('@feathersjs/')) + .reduce((acc, dep) => { + const [, name] = dep.split('/') + + acc[dep] = path.join(__dirname, 'build', `feathersjs-${name}-${lernaConfig.version}.tgz`) + + return acc + }, {} as DependencyVersions) diff --git a/packages/cli/tsconfig.json b/packages/cli/tsconfig.json new file mode 100644 index 0000000000..3e7a45e4a0 --- /dev/null +++ b/packages/cli/tsconfig.json @@ -0,0 +1,10 @@ +{ + "extends": "../../tsconfig", + "include": [ + "src/**/*.ts" + ], + "compilerOptions": { + "outDir": "lib", + "resolveJsonModule": true + } +} diff --git a/packages/client/CHANGELOG.md b/packages/client/CHANGELOG.md index c5ab10c8ed..d8af269b66 100644 --- a/packages/client/CHANGELOG.md +++ b/packages/client/CHANGELOG.md @@ -3,591 +3,402 @@ All notable changes to this project will be documented in this file. See [Conventional Commits](https://conventionalcommits.org) for commit guidelines. -# [5.0.0-pre.16](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.15...v5.0.0-pre.16) (2022-01-12) +# [5.0.0-pre.31](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.30...v5.0.0-pre.31) (2022-10-12) + +**Note:** Version bump only for package @feathersjs/client +# [5.0.0-pre.30](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.29...v5.0.0-pre.30) (2022-10-07) ### Features -* **express, koa:** make transports similar ([#2486](https://github.com/feathersjs/feathers/issues/2486)) ([26aa937](https://github.com/feathersjs/feathers/commit/26aa937c114fb8596dfefc599b1f53cead69c159)) +- **core:** Allow to unregister services at runtime ([#2756](https://github.com/feathersjs/feathers/issues/2756)) ([d16601f](https://github.com/feathersjs/feathers/commit/d16601f2277dca5357866ffdefba2a611f6dc7fa)) +# [5.0.0-pre.29](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.28...v5.0.0-pre.29) (2022-09-16) +**Note:** Version bump only for package @feathersjs/client +# [5.0.0-pre.28](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.27...v5.0.0-pre.28) (2022-08-03) +**Note:** Version bump only for package @feathersjs/client -# [5.0.0-pre.15](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.14...v5.0.0-pre.15) (2021-11-27) +# [5.0.0-pre.27](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.26...v5.0.0-pre.27) (2022-07-13) **Note:** Version bump only for package @feathersjs/client +# [5.0.0-pre.26](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.25...v5.0.0-pre.26) (2022-06-22) +**Note:** Version bump only for package @feathersjs/client +# [5.0.0-pre.25](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.24...v5.0.0-pre.25) (2022-06-22) +**Note:** Version bump only for package @feathersjs/client -# [5.0.0-pre.14](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.13...v5.0.0-pre.14) (2021-10-13) +# [5.0.0-pre.24](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.23...v5.0.0-pre.24) (2022-06-21) **Note:** Version bump only for package @feathersjs/client +# [5.0.0-pre.23](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.22...v5.0.0-pre.23) (2022-06-06) +**Note:** Version bump only for package @feathersjs/client +# [5.0.0-pre.22](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.21...v5.0.0-pre.22) (2022-05-24) +**Note:** Version bump only for package @feathersjs/client -# [5.0.0-pre.13](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.12...v5.0.0-pre.13) (2021-10-13) +# [5.0.0-pre.21](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.20...v5.0.0-pre.21) (2022-05-23) **Note:** Version bump only for package @feathersjs/client +# [5.0.0-pre.20](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.19...v5.0.0-pre.20) (2022-05-04) +### Bug Fixes +- **dependencies:** Lock monorepo package version numbers ([#2623](https://github.com/feathersjs/feathers/issues/2623)) ([5640c10](https://github.com/feathersjs/feathers/commit/5640c1020cc139994e695d658c08bad3494db507)) +# [5.0.0-pre.19](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.18...v5.0.0-pre.19) (2022-05-01) -# [5.0.0-pre.12](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.11...v5.0.0-pre.12) (2021-10-12) +### Bug Fixes -**Note:** Version bump only for package @feathersjs/client +- **client:** Fix @feathersjs/client types field ([#2596](https://github.com/feathersjs/feathers/issues/2596)) ([d719f54](https://github.com/feathersjs/feathers/commit/d719f54daee63daf9ed5cc762626ca15131086de)) +### Features +- **typescript:** Improve adapter typings ([#2605](https://github.com/feathersjs/feathers/issues/2605)) ([3b2ca0a](https://github.com/feathersjs/feathers/commit/3b2ca0a6a8e03e8390272c4d7e930b4bffdaacf5)) +# [5.0.0-pre.18](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.17...v5.0.0-pre.18) (2022-04-11) +**Note:** Version bump only for package @feathersjs/client -# [5.0.0-pre.11](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.10...v5.0.0-pre.11) (2021-10-06) +# [5.0.0-pre.17](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.16...v5.0.0-pre.17) (2022-02-15) **Note:** Version bump only for package @feathersjs/client +# [5.0.0-pre.16](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.15...v5.0.0-pre.16) (2022-01-12) +### Features +- **express, koa:** make transports similar ([#2486](https://github.com/feathersjs/feathers/issues/2486)) ([26aa937](https://github.com/feathersjs/feathers/commit/26aa937c114fb8596dfefc599b1f53cead69c159)) - -# [5.0.0-pre.10](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.9...v5.0.0-pre.10) (2021-09-19) +# [5.0.0-pre.15](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.14...v5.0.0-pre.15) (2021-11-27) **Note:** Version bump only for package @feathersjs/client +# [5.0.0-pre.14](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.13...v5.0.0-pre.14) (2021-10-13) +**Note:** Version bump only for package @feathersjs/client - - -# [5.0.0-pre.9](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.8...v5.0.0-pre.9) (2021-08-09) +# [5.0.0-pre.13](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.12...v5.0.0-pre.13) (2021-10-13) **Note:** Version bump only for package @feathersjs/client +# [5.0.0-pre.12](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.11...v5.0.0-pre.12) (2021-10-12) +**Note:** Version bump only for package @feathersjs/client +# [5.0.0-pre.11](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.10...v5.0.0-pre.11) (2021-10-06) +**Note:** Version bump only for package @feathersjs/client -# [5.0.0-pre.8](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.7...v5.0.0-pre.8) (2021-08-09) +# [5.0.0-pre.10](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.9...v5.0.0-pre.10) (2021-09-19) **Note:** Version bump only for package @feathersjs/client +# [5.0.0-pre.9](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.8...v5.0.0-pre.9) (2021-08-09) +**Note:** Version bump only for package @feathersjs/client +# [5.0.0-pre.8](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.7...v5.0.0-pre.8) (2021-08-09) +**Note:** Version bump only for package @feathersjs/client # [5.0.0-pre.7](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.6...v5.0.0-pre.7) (2021-08-09) **Note:** Version bump only for package @feathersjs/client - - - - # [5.0.0-pre.6](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.5...v5.0.0-pre.6) (2021-08-08) **Note:** Version bump only for package @feathersjs/client - - - - # [5.0.0-pre.5](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.4...v5.0.0-pre.5) (2021-06-23) - ### Features -* **adapter-commons:** Add support for params.adapter option and move memory adapter to @feathersjs/memory ([#2367](https://github.com/feathersjs/feathers/issues/2367)) ([a43e7da](https://github.com/feathersjs/feathers/commit/a43e7da22b6b981a96d1321736ea9a0cb924fb4f)) - - - - +- **adapter-commons:** Add support for params.adapter option and move memory adapter to @feathersjs/memory ([#2367](https://github.com/feathersjs/feathers/issues/2367)) ([a43e7da](https://github.com/feathersjs/feathers/commit/a43e7da22b6b981a96d1321736ea9a0cb924fb4f)) # [5.0.0-pre.4](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.3...v5.0.0-pre.4) (2021-05-13) - ### Features -* **koa:** KoaJS transport adapter ([#2315](https://github.com/feathersjs/feathers/issues/2315)) ([2554b57](https://github.com/feathersjs/feathers/commit/2554b57cf05731df58feeba9c12faab18e442107)) - - - - +- **koa:** KoaJS transport adapter ([#2315](https://github.com/feathersjs/feathers/issues/2315)) ([2554b57](https://github.com/feathersjs/feathers/commit/2554b57cf05731df58feeba9c12faab18e442107)) # [5.0.0-pre.3](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.2...v5.0.0-pre.3) (2021-04-21) - ### Bug Fixes -* **typescript:** Improve TypeScript backwards compatibility ([#2310](https://github.com/feathersjs/feathers/issues/2310)) ([f33be73](https://github.com/feathersjs/feathers/commit/f33be73fc46a533efb15df9aab0658e3240d3897)) - - - - +- **typescript:** Improve TypeScript backwards compatibility ([#2310](https://github.com/feathersjs/feathers/issues/2310)) ([f33be73](https://github.com/feathersjs/feathers/commit/f33be73fc46a533efb15df9aab0658e3240d3897)) # [5.0.0-pre.2](https://github.com/feathersjs/feathers/compare/v5.0.0-beta.1...v5.0.0-pre.2) (2021-04-06) **Note:** Version bump only for package @feathersjs/client - - - - # [5.0.0-beta.1](https://github.com/feathersjs/feathers/compare/v5.0.0-beta.0...v5.0.0-beta.1) (2021-04-03) - ### Bug Fixes -* **dependencies:** Fix transport-commons dependency and update other dependencies ([#2284](https://github.com/feathersjs/feathers/issues/2284)) ([05b03b2](https://github.com/feathersjs/feathers/commit/05b03b27b40604d956047e3021d8053c3a137616)) - - - - +- **dependencies:** Fix transport-commons dependency and update other dependencies ([#2284](https://github.com/feathersjs/feathers/issues/2284)) ([05b03b2](https://github.com/feathersjs/feathers/commit/05b03b27b40604d956047e3021d8053c3a137616)) # [5.0.0-beta.0](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.1...v5.0.0-beta.0) (2021-03-28) - ### Bug Fixes -* Update Grant usage and other dependencies ([#2264](https://github.com/feathersjs/feathers/issues/2264)) ([7b0f8fa](https://github.com/feathersjs/feathers/commit/7b0f8fad252419ed0ad0bf259cdf3104d322ab60)) - +- Update Grant usage and other dependencies ([#2264](https://github.com/feathersjs/feathers/issues/2264)) ([7b0f8fa](https://github.com/feathersjs/feathers/commit/7b0f8fad252419ed0ad0bf259cdf3104d322ab60)) ### Features -* Feathers v5 core refactoring and features ([#2255](https://github.com/feathersjs/feathers/issues/2255)) ([2dafb7c](https://github.com/feathersjs/feathers/commit/2dafb7ce14ba57406aeec13d10ca45b1e709bee9)) - - - - +- Feathers v5 core refactoring and features ([#2255](https://github.com/feathersjs/feathers/issues/2255)) ([2dafb7c](https://github.com/feathersjs/feathers/commit/2dafb7ce14ba57406aeec13d10ca45b1e709bee9)) # [5.0.0-pre.1](https://github.com/feathersjs/feathers/compare/v4.5.11...v5.0.0-pre.1) (2020-12-17) - - # [5.0.0-pre.0](https://github.com/feathersjs/feathers/compare/v4.5.4...v5.0.0-pre.0) (2020-05-19) - ### chore -* **package:** Remove @feathersjs/primus packages from core ([#1919](https://github.com/feathersjs/feathers/issues/1919)) ([d20b7d5](https://github.com/feathersjs/feathers/commit/d20b7d5a70f4d3306e294696156e8aa0337c35e9)), closes [#1899](https://github.com/feathersjs/feathers/issues/1899) - +- **package:** Remove @feathersjs/primus packages from core ([#1919](https://github.com/feathersjs/feathers/issues/1919)) ([d20b7d5](https://github.com/feathersjs/feathers/commit/d20b7d5a70f4d3306e294696156e8aa0337c35e9)), closes [#1899](https://github.com/feathersjs/feathers/issues/1899) ### Features -* **core:** use @feathers/hooks and add async type ([#1929](https://github.com/feathersjs/feathers/issues/1929)) ([a5c4756](https://github.com/feathersjs/feathers/commit/a5c47562eae8410c82fe2f6308f26f8e78b6a3e8)) - +- **core:** use @feathers/hooks and add async type ([#1929](https://github.com/feathersjs/feathers/issues/1929)) ([a5c4756](https://github.com/feathersjs/feathers/commit/a5c47562eae8410c82fe2f6308f26f8e78b6a3e8)) ### BREAKING CHANGES -* **package:** Remove primus packages to be moved into the ecosystem. - - - - +- **package:** Remove primus packages to be moved into the ecosystem. # [5.0.0-pre.0](https://github.com/feathersjs/feathers/compare/v4.5.4...v5.0.0-pre.0) (2020-05-19) - ### chore -* **package:** Remove @feathersjs/primus packages from core ([#1919](https://github.com/feathersjs/feathers/issues/1919)) ([d20b7d5](https://github.com/feathersjs/feathers/commit/d20b7d5a70f4d3306e294696156e8aa0337c35e9)), closes [#1899](https://github.com/feathersjs/feathers/issues/1899) - +- **package:** Remove @feathersjs/primus packages from core ([#1919](https://github.com/feathersjs/feathers/issues/1919)) ([d20b7d5](https://github.com/feathersjs/feathers/commit/d20b7d5a70f4d3306e294696156e8aa0337c35e9)), closes [#1899](https://github.com/feathersjs/feathers/issues/1899) ### Features -* **core:** use @feathers/hooks and add async type ([#1929](https://github.com/feathersjs/feathers/issues/1929)) ([a5c4756](https://github.com/feathersjs/feathers/commit/a5c47562eae8410c82fe2f6308f26f8e78b6a3e8)) - +- **core:** use @feathers/hooks and add async type ([#1929](https://github.com/feathersjs/feathers/issues/1929)) ([a5c4756](https://github.com/feathersjs/feathers/commit/a5c47562eae8410c82fe2f6308f26f8e78b6a3e8)) ### BREAKING CHANGES -* **package:** Remove primus packages to be moved into the ecosystem. - +- **package:** Remove primus packages to be moved into the ecosystem. ## [4.5.11](https://github.com/feathersjs/feathers/compare/v4.5.10...v4.5.11) (2020-12-05) **Note:** Version bump only for package @feathersjs/client - - - - ## [4.5.10](https://github.com/feathersjs/feathers/compare/v4.5.9...v4.5.10) (2020-11-08) - ### Bug Fixes -* **package:** Fix clean script in non Unix environments ([#2110](https://github.com/feathersjs/feathers/issues/2110)) ([09b62c0](https://github.com/feathersjs/feathers/commit/09b62c0c7e636caf620904ba87d61f168a020f05)) - - - - +- **package:** Fix clean script in non Unix environments ([#2110](https://github.com/feathersjs/feathers/issues/2110)) ([09b62c0](https://github.com/feathersjs/feathers/commit/09b62c0c7e636caf620904ba87d61f168a020f05)) ## [4.5.9](https://github.com/feathersjs/feathers/compare/v4.5.8...v4.5.9) (2020-10-09) **Note:** Version bump only for package @feathersjs/client - - - - ## [4.5.8](https://github.com/feathersjs/feathers/compare/v4.5.7...v4.5.8) (2020-08-12) **Note:** Version bump only for package @feathersjs/client - - - - ## [4.5.7](https://github.com/feathersjs/feathers/compare/v4.5.6...v4.5.7) (2020-07-24) **Note:** Version bump only for package @feathersjs/client - - - - ## [4.5.6](https://github.com/feathersjs/feathers/compare/v4.5.5...v4.5.6) (2020-07-12) **Note:** Version bump only for package @feathersjs/client - - - - ## [4.5.5](https://github.com/feathersjs/feathers/compare/v4.5.4...v4.5.5) (2020-07-11) **Note:** Version bump only for package @feathersjs/client - - - - ## [4.5.4](https://github.com/feathersjs/feathers/compare/v4.5.3...v4.5.4) (2020-04-29) **Note:** Version bump only for package @feathersjs/client - - - - ## [4.5.3](https://github.com/feathersjs/feathers/compare/v4.5.2...v4.5.3) (2020-04-17) **Note:** Version bump only for package @feathersjs/client - - - - ## [4.5.2](https://github.com/feathersjs/feathers/compare/v4.5.1...v4.5.2) (2020-03-04) **Note:** Version bump only for package @feathersjs/client - - - - ## [4.5.1](https://github.com/feathersjs/feathers/compare/v4.5.0...v4.5.1) (2020-01-24) **Note:** Version bump only for package @feathersjs/client - - - - # [4.5.0](https://github.com/feathersjs/feathers/compare/v4.4.3...v4.5.0) (2020-01-18) **Note:** Version bump only for package @feathersjs/client - - - - ## [4.4.3](https://github.com/feathersjs/feathers/compare/v4.4.1...v4.4.3) (2019-12-06) **Note:** Version bump only for package @feathersjs/client - - - - ## [4.4.1](https://github.com/feathersjs/feathers/compare/v4.4.0...v4.4.1) (2019-11-27) **Note:** Version bump only for package @feathersjs/client - - - - # [4.4.0](https://github.com/feathersjs/feathers/compare/v4.3.11...v4.4.0) (2019-11-27) **Note:** Version bump only for package @feathersjs/client - - - - ## [4.3.11](https://github.com/feathersjs/feathers/compare/v4.3.10...v4.3.11) (2019-11-11) **Note:** Version bump only for package @feathersjs/client - - - - ## [4.3.10](https://github.com/feathersjs/feathers/compare/v4.3.9...v4.3.10) (2019-10-26) **Note:** Version bump only for package @feathersjs/client - - - - ## [4.3.9](https://github.com/feathersjs/feathers/compare/v4.3.8...v4.3.9) (2019-10-26) **Note:** Version bump only for package @feathersjs/client - - - - ## [4.3.7](https://github.com/feathersjs/feathers/compare/v4.3.6...v4.3.7) (2019-10-14) **Note:** Version bump only for package @feathersjs/client - - - - ## [4.3.5](https://github.com/feathersjs/feathers/compare/v4.3.4...v4.3.5) (2019-10-07) **Note:** Version bump only for package @feathersjs/client - - - - ## [4.3.4](https://github.com/feathersjs/feathers/compare/v4.3.3...v4.3.4) (2019-10-03) **Note:** Version bump only for package @feathersjs/client - - - - ## [4.3.3](https://github.com/feathersjs/feathers/compare/v4.3.2...v4.3.3) (2019-09-21) **Note:** Version bump only for package @feathersjs/client - - - - ## [4.3.2](https://github.com/feathersjs/feathers/compare/v4.3.1...v4.3.2) (2019-09-16) **Note:** Version bump only for package @feathersjs/client - - - - ## [4.3.1](https://github.com/feathersjs/feathers/compare/v4.3.0...v4.3.1) (2019-09-09) **Note:** Version bump only for package @feathersjs/client - - - - # [4.3.0](https://github.com/feathersjs/feathers/compare/v4.3.0-pre.4...v4.3.0) (2019-08-27) **Note:** Version bump only for package @feathersjs/client - - - - # [4.3.0-pre.4](https://github.com/feathersjs/feathers/compare/v4.3.0-pre.3...v4.3.0-pre.4) (2019-08-22) **Note:** Version bump only for package @feathersjs/client - - - - # [4.3.0-pre.3](https://github.com/feathersjs/feathers/compare/v4.3.0-pre.2...v4.3.0-pre.3) (2019-08-19) **Note:** Version bump only for package @feathersjs/client - - - - # [4.3.0-pre.2](https://github.com/feathersjs/feathers/compare/v4.3.0-pre.1...v4.3.0-pre.2) (2019-08-02) **Note:** Version bump only for package @feathersjs/client - - - - # [4.3.0-pre.1](https://github.com/feathersjs/feathers/compare/v4.0.0-pre.5...v4.3.0-pre.1) (2019-07-11) **Note:** Version bump only for package @feathersjs/client - - - - # [4.0.0-pre.5](https://github.com/feathersjs/feathers/compare/v4.0.0-pre.4...v4.0.0-pre.5) (2019-07-10) - ### Bug Fixes -* Fix feathers-memory dependency that did not get updated ([9422b13](https://github.com/feathersjs/feathers/commit/9422b13)) - - - - +- Fix feathers-memory dependency that did not get updated ([9422b13](https://github.com/feathersjs/feathers/commit/9422b13)) # [4.0.0-pre.4](https://github.com/feathersjs/feathers/compare/v4.0.0-pre.3...v4.0.0-pre.4) (2019-07-05) **Note:** Version bump only for package @feathersjs/client - - - - # [4.0.0-pre.3](https://github.com/feathersjs/feathers/compare/v4.0.0-pre.2...v4.0.0-pre.3) (2019-06-01) - ### Bug Fixes -* Update dependencies and fix tests ([#1373](https://github.com/feathersjs/feathers/issues/1373)) ([d743a7f](https://github.com/feathersjs/feathers/commit/d743a7f)) - - - - +- Update dependencies and fix tests ([#1373](https://github.com/feathersjs/feathers/issues/1373)) ([d743a7f](https://github.com/feathersjs/feathers/commit/d743a7f)) # [4.0.0-pre.2](https://github.com/feathersjs/feathers/compare/v4.0.0-pre.1...v4.0.0-pre.2) (2019-05-15) - ### Bug Fixes -* Use `export =` in TypeScript definitions ([#1285](https://github.com/feathersjs/feathers/issues/1285)) ([12d0f4b](https://github.com/feathersjs/feathers/commit/12d0f4b)) - - - - +- Use `export =` in TypeScript definitions ([#1285](https://github.com/feathersjs/feathers/issues/1285)) ([12d0f4b](https://github.com/feathersjs/feathers/commit/12d0f4b)) # [4.0.0-pre.1](https://github.com/feathersjs/feathers/compare/v4.0.0-pre.0...v4.0.0-pre.1) (2019-05-08) - ### Bug Fixes -* Improve authentication parameter handling ([#1333](https://github.com/feathersjs/feathers/issues/1333)) ([6e77204](https://github.com/feathersjs/feathers/commit/6e77204)) - - - - +- Improve authentication parameter handling ([#1333](https://github.com/feathersjs/feathers/issues/1333)) ([6e77204](https://github.com/feathersjs/feathers/commit/6e77204)) # [4.0.0-pre.0](https://github.com/feathersjs/feathers/compare/v3.2.0-pre.1...v4.0.0-pre.0) (2019-04-21) - ### Bug Fixes -* Make Mocha a proper devDependency for every repository ([#1053](https://github.com/feathersjs/feathers/issues/1053)) ([9974803](https://github.com/feathersjs/feathers/commit/9974803)) -* Update adapter common tests ([#1135](https://github.com/feathersjs/feathers/issues/1135)) ([8166dda](https://github.com/feathersjs/feathers/commit/8166dda)) -* Update all dependencies to latest ([#1206](https://github.com/feathersjs/feathers/issues/1206)) ([e51e0f6](https://github.com/feathersjs/feathers/commit/e51e0f6)) -* **chore:** Properly configure and run code linter ([#1092](https://github.com/feathersjs/feathers/issues/1092)) ([fd3fc34](https://github.com/feathersjs/feathers/commit/fd3fc34)) - +- Make Mocha a proper devDependency for every repository ([#1053](https://github.com/feathersjs/feathers/issues/1053)) ([9974803](https://github.com/feathersjs/feathers/commit/9974803)) +- Update adapter common tests ([#1135](https://github.com/feathersjs/feathers/issues/1135)) ([8166dda](https://github.com/feathersjs/feathers/commit/8166dda)) +- Update all dependencies to latest ([#1206](https://github.com/feathersjs/feathers/issues/1206)) ([e51e0f6](https://github.com/feathersjs/feathers/commit/e51e0f6)) +- **chore:** Properly configure and run code linter ([#1092](https://github.com/feathersjs/feathers/issues/1092)) ([fd3fc34](https://github.com/feathersjs/feathers/commit/fd3fc34)) ### Features -* Add TypeScript definitions ([#1275](https://github.com/feathersjs/feathers/issues/1275)) ([9dd6713](https://github.com/feathersjs/feathers/commit/9dd6713)) -* Authentication v3 core server implementation ([#1205](https://github.com/feathersjs/feathers/issues/1205)) ([1bd7591](https://github.com/feathersjs/feathers/commit/1bd7591)) - - - - +- Add TypeScript definitions ([#1275](https://github.com/feathersjs/feathers/issues/1275)) ([9dd6713](https://github.com/feathersjs/feathers/commit/9dd6713)) +- Authentication v3 core server implementation ([#1205](https://github.com/feathersjs/feathers/issues/1205)) ([1bd7591](https://github.com/feathersjs/feathers/commit/1bd7591)) ## [3.7.8](https://github.com/feathersjs/feathers/compare/@feathersjs/client@3.7.7...@feathersjs/client@3.7.8) (2019-01-26) **Note:** Version bump only for package @feathersjs/client - - - - ## [3.7.7](https://github.com/feathersjs/feathers/compare/@feathersjs/client@3.7.6...@feathersjs/client@3.7.7) (2019-01-02) - ### Bug Fixes -* Update adapter common tests ([#1135](https://github.com/feathersjs/feathers/issues/1135)) ([8166dda](https://github.com/feathersjs/feathers/commit/8166dda)) - - - - +- Update adapter common tests ([#1135](https://github.com/feathersjs/feathers/issues/1135)) ([8166dda](https://github.com/feathersjs/feathers/commit/8166dda)) -## [3.7.6](https://github.com/feathersjs/feathers/compare/@feathersjs/client@3.7.5...@feathersjs/client@3.7.6) (2018-12-16) +## [3.7.6](https://github.com/feathersjs/feathers/compare/@feathersjs/client@3.7.5...@feathersjs/client@3.7.6) (2018-12-16) ### Bug Fixes -* **chore:** Properly configure and run code linter ([#1092](https://github.com/feathersjs/feathers/issues/1092)) ([fd3fc34](https://github.com/feathersjs/feathers/commit/fd3fc34)) - - - - +- **chore:** Properly configure and run code linter ([#1092](https://github.com/feathersjs/feathers/issues/1092)) ([fd3fc34](https://github.com/feathersjs/feathers/commit/fd3fc34)) + ## [3.7.5](https://github.com/feathersjs/feathers/compare/@feathersjs/client@3.7.4...@feathersjs/client@3.7.5) (2018-10-26) **Note:** Version bump only for package @feathersjs/client - - - - -## [3.7.4](https://github.com/feathersjs/feathers/compare/@feathersjs/client@3.7.3...@feathersjs/client@3.7.4) (2018-10-25) +## [3.7.4](https://github.com/feathersjs/feathers/compare/@feathersjs/client@3.7.3...@feathersjs/client@3.7.4) (2018-10-25) ### Bug Fixes -* Make Mocha a proper devDependency for every repository ([#1053](https://github.com/feathersjs/feathers/issues/1053)) ([9974803](https://github.com/feathersjs/feathers/commit/9974803)) - - - - +- Make Mocha a proper devDependency for every repository ([#1053](https://github.com/feathersjs/feathers/issues/1053)) ([9974803](https://github.com/feathersjs/feathers/commit/9974803)) + ## [3.7.3](https://github.com/feathersjs/feathers/compare/@feathersjs/client@3.7.2...@feathersjs/client@3.7.3) (2018-09-24) **Note:** Version bump only for package @feathersjs/client - - - - + ## 3.7.2 (2018-09-21) **Note:** Version bump only for package @feathersjs/client - - - - # Change Log ## [v3.7.1](https://github.com/feathersjs/client/tree/v3.7.1) (2018-09-21) + [Full Changelog](https://github.com/feathersjs/client/compare/v3.7.0...v3.7.1) ## [v3.7.0](https://github.com/feathersjs/client/tree/v3.7.0) (2018-09-18) + [Full Changelog](https://github.com/feathersjs/client/compare/v3.6.0...v3.7.0) **Closed issues:** @@ -600,6 +411,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Update uglifyjs-webpack-plugin to the latest version 🚀 [\#287](https://github.com/feathersjs/client/pull/287) ([greenkeeper[bot]](https://github.com/marketplace/greenkeeper)) ## [v3.6.0](https://github.com/feathersjs/client/tree/v3.6.0) (2018-09-03) + [Full Changelog](https://github.com/feathersjs/client/compare/v3.5.6...v3.6.0) **Merged pull requests:** @@ -609,9 +421,11 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Update @feathersjs/errors to the latest version 🚀 [\#272](https://github.com/feathersjs/client/pull/272) ([greenkeeper[bot]](https://github.com/marketplace/greenkeeper)) ## [v3.5.6](https://github.com/feathersjs/client/tree/v3.5.6) (2018-08-13) + [Full Changelog](https://github.com/feathersjs/client/compare/v3.5.5...v3.5.6) ## [v3.5.5](https://github.com/feathersjs/client/tree/v3.5.5) (2018-08-02) + [Full Changelog](https://github.com/feathersjs/client/compare/v3.5.4...v3.5.5) **Closed issues:** @@ -623,6 +437,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Update ws to the latest version 🚀 [\#269](https://github.com/feathersjs/client/pull/269) ([greenkeeper[bot]](https://github.com/marketplace/greenkeeper)) ## [v3.5.4](https://github.com/feathersjs/client/tree/v3.5.4) (2018-07-19) + [Full Changelog](https://github.com/feathersjs/client/compare/v3.5.3...v3.5.4) **Merged pull requests:** @@ -630,6 +445,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Update all dependencies to latest [\#268](https://github.com/feathersjs/client/pull/268) ([daffl](https://github.com/daffl)) ## [v3.5.3](https://github.com/feathersjs/client/tree/v3.5.3) (2018-06-28) + [Full Changelog](https://github.com/feathersjs/client/compare/v3.5.2...v3.5.3) **Merged pull requests:** @@ -637,6 +453,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Update @feathersjs/rest-client to the latest version 🚀 [\#266](https://github.com/feathersjs/client/pull/266) ([greenkeeper[bot]](https://github.com/marketplace/greenkeeper)) ## [v3.5.2](https://github.com/feathersjs/client/tree/v3.5.2) (2018-06-16) + [Full Changelog](https://github.com/feathersjs/client/compare/v3.5.1...v3.5.2) **Closed issues:** @@ -649,11 +466,12 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Update shx to the latest version 🚀 [\#263](https://github.com/feathersjs/client/pull/263) ([greenkeeper[bot]](https://github.com/marketplace/greenkeeper)) ## [v3.5.1](https://github.com/feathersjs/client/tree/v3.5.1) (2018-06-03) + [Full Changelog](https://github.com/feathersjs/client/compare/v3.5.0...v3.5.1) **Closed issues:** -- 'exports' is undefined [\#261](https://github.com/feathersjs/client/issues/261) +- 'exports' is undefined [\#261](https://github.com/feathersjs/client/issues/261) - I got error from NuxtJS when I use FeathersJS client V3 [\#260](https://github.com/feathersjs/client/issues/260) **Merged pull requests:** @@ -661,6 +479,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Update @feathersjs/feathers to the latest version 🚀 [\#262](https://github.com/feathersjs/client/pull/262) ([greenkeeper[bot]](https://github.com/marketplace/greenkeeper)) ## [v3.5.0](https://github.com/feathersjs/client/tree/v3.5.0) (2018-05-17) + [Full Changelog](https://github.com/feathersjs/client/compare/v3.4.5...v3.5.0) **Merged pull requests:** @@ -668,6 +487,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Update @feathersjs/rest-client to the latest version 🚀 [\#259](https://github.com/feathersjs/client/pull/259) ([greenkeeper[bot]](https://github.com/marketplace/greenkeeper)) ## [v3.4.5](https://github.com/feathersjs/client/tree/v3.4.5) (2018-05-04) + [Full Changelog](https://github.com/feathersjs/client/compare/v3.4.4...v3.4.5) **Merged pull requests:** @@ -675,6 +495,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Update @feathersjs/feathers to the latest version 🚀 [\#258](https://github.com/feathersjs/client/pull/258) ([greenkeeper[bot]](https://github.com/marketplace/greenkeeper)) ## [v3.4.4](https://github.com/feathersjs/client/tree/v3.4.4) (2018-03-27) + [Full Changelog](https://github.com/feathersjs/client/compare/v3.4.3...v3.4.4) **Merged pull requests:** @@ -683,6 +504,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Update @feathersjs/rest-client to the latest version 🚀 [\#256](https://github.com/feathersjs/client/pull/256) ([greenkeeper[bot]](https://github.com/marketplace/greenkeeper)) ## [v3.4.3](https://github.com/feathersjs/client/tree/v3.4.3) (2018-03-07) + [Full Changelog](https://github.com/feathersjs/client/compare/v3.4.2...v3.4.3) **Closed issues:** @@ -695,6 +517,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Update webpack to the latest version 🚀 [\#254](https://github.com/feathersjs/client/pull/254) ([greenkeeper[bot]](https://github.com/marketplace/greenkeeper)) ## [v3.4.2](https://github.com/feathersjs/client/tree/v3.4.2) (2018-02-16) + [Full Changelog](https://github.com/feathersjs/client/compare/v3.4.1...v3.4.2) **Closed issues:** @@ -707,6 +530,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Update @feathersjs/errors to the latest version 🚀 [\#251](https://github.com/feathersjs/client/pull/251) ([greenkeeper[bot]](https://github.com/marketplace/greenkeeper)) ## [v3.4.1](https://github.com/feathersjs/client/tree/v3.4.1) (2018-02-10) + [Full Changelog](https://github.com/feathersjs/client/compare/v3.4.0...v3.4.1) **Merged pull requests:** @@ -714,6 +538,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Update @feathersjs/feathers to the latest version 🚀 [\#249](https://github.com/feathersjs/client/pull/249) ([greenkeeper[bot]](https://github.com/marketplace/greenkeeper)) ## [v3.4.0](https://github.com/feathersjs/client/tree/v3.4.0) (2018-02-09) + [Full Changelog](https://github.com/feathersjs/client/compare/v3.3.2...v3.4.0) **Merged pull requests:** @@ -722,6 +547,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Update @feathersjs/socketio-client to the latest version 🚀 [\#247](https://github.com/feathersjs/client/pull/247) ([greenkeeper[bot]](https://github.com/marketplace/greenkeeper)) ## [v3.3.2](https://github.com/feathersjs/client/tree/v3.3.2) (2018-02-09) + [Full Changelog](https://github.com/feathersjs/client/compare/v3.3.1...v3.3.2) **Merged pull requests:** @@ -730,6 +556,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - delete slack link [\#245](https://github.com/feathersjs/client/pull/245) ([vodniciarv](https://github.com/vodniciarv)) ## [v3.3.1](https://github.com/feathersjs/client/tree/v3.3.1) (2018-02-05) + [Full Changelog](https://github.com/feathersjs/client/compare/v3.3.0...v3.3.1) **Merged pull requests:** @@ -739,6 +566,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Update node-fetch to the latest version 🚀 [\#242](https://github.com/feathersjs/client/pull/242) ([greenkeeper[bot]](https://github.com/marketplace/greenkeeper)) ## [v3.3.0](https://github.com/feathersjs/client/tree/v3.3.0) (2018-01-26) + [Full Changelog](https://github.com/feathersjs/client/compare/v3.2.0...v3.3.0) **Merged pull requests:** @@ -746,6 +574,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Update @feathersjs/feathers to the latest version 🚀 [\#241](https://github.com/feathersjs/client/pull/241) ([greenkeeper[bot]](https://github.com/marketplace/greenkeeper)) ## [v3.2.0](https://github.com/feathersjs/client/tree/v3.2.0) (2018-01-24) + [Full Changelog](https://github.com/feathersjs/client/compare/v3.1.2...v3.2.0) **Closed issues:** @@ -768,6 +597,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Update @feathersjs/errors to the latest version 🚀 [\#228](https://github.com/feathersjs/client/pull/228) ([greenkeeper[bot]](https://github.com/marketplace/greenkeeper)) ## [v3.1.2](https://github.com/feathersjs/client/tree/v3.1.2) (2018-01-02) + [Full Changelog](https://github.com/feathersjs/client/compare/v3.1.1...v3.1.2) **Closed issues:** @@ -780,6 +610,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Update semistandard to the latest version 🚀 [\#226](https://github.com/feathersjs/client/pull/226) ([greenkeeper[bot]](https://github.com/marketplace/greenkeeper)) ## [v3.1.1](https://github.com/feathersjs/client/tree/v3.1.1) (2017-12-05) + [Full Changelog](https://github.com/feathersjs/client/compare/v3.1.0...v3.1.1) **Merged pull requests:** @@ -790,6 +621,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Update @feathersjs/errors to the latest version 🚀 [\#221](https://github.com/feathersjs/client/pull/221) ([greenkeeper[bot]](https://github.com/marketplace/greenkeeper)) ## [v3.1.0](https://github.com/feathersjs/client/tree/v3.1.0) (2017-11-16) + [Full Changelog](https://github.com/feathersjs/client/compare/v3.0.0...v3.1.0) **Merged pull requests:** @@ -799,6 +631,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Update package.json [\#215](https://github.com/feathersjs/client/pull/215) ([frank-dspeed](https://github.com/frank-dspeed)) ## [v3.0.0](https://github.com/feathersjs/client/tree/v3.0.0) (2017-11-01) + [Full Changelog](https://github.com/feathersjs/client/compare/v3.0.0-pre.1...v3.0.0) **Merged pull requests:** @@ -806,6 +639,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Update dependencies for release [\#214](https://github.com/feathersjs/client/pull/214) ([daffl](https://github.com/daffl)) ## [v3.0.0-pre.1](https://github.com/feathersjs/client/tree/v3.0.0-pre.1) (2017-10-30) + [Full Changelog](https://github.com/feathersjs/client/compare/v2.4.0...v3.0.0-pre.1) **Closed issues:** @@ -832,6 +666,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Update feathers-errors to the latest version 🚀 [\#197](https://github.com/feathersjs/client/pull/197) ([greenkeeper[bot]](https://github.com/marketplace/greenkeeper)) ## [v2.4.0](https://github.com/feathersjs/client/tree/v2.4.0) (2017-09-02) + [Full Changelog](https://github.com/feathersjs/client/compare/v2.3.0...v2.4.0) **Closed issues:** @@ -851,6 +686,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Update feathers-errors to the latest version 🚀 [\#186](https://github.com/feathersjs/client/pull/186) ([greenkeeper[bot]](https://github.com/marketplace/greenkeeper)) ## [v2.3.0](https://github.com/feathersjs/client/tree/v2.3.0) (2017-07-04) + [Full Changelog](https://github.com/feathersjs/client/compare/v2.2.0...v2.3.0) **Closed issues:** @@ -879,6 +715,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Add IE Edge instead of IE 9 [\#166](https://github.com/feathersjs/client/pull/166) ([daffl](https://github.com/daffl)) ## [v2.2.0](https://github.com/feathersjs/client/tree/v2.2.0) (2017-04-25) + [Full Changelog](https://github.com/feathersjs/client/compare/v2.1.0...v2.2.0) **Merged pull requests:** @@ -888,6 +725,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Update semistandard to the latest version 🚀 [\#163](https://github.com/feathersjs/client/pull/163) ([greenkeeper[bot]](https://github.com/marketplace/greenkeeper)) ## [v2.1.0](https://github.com/feathersjs/client/tree/v2.1.0) (2017-04-18) + [Full Changelog](https://github.com/feathersjs/client/compare/v2.0.0...v2.1.0) **Closed issues:** @@ -901,6 +739,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Added generics to typescript definition. [\#158](https://github.com/feathersjs/client/pull/158) ([noah79](https://github.com/noah79)) ## [v2.0.0](https://github.com/feathersjs/client/tree/v2.0.0) (2017-04-11) + [Full Changelog](https://github.com/feathersjs/client/compare/v2.0.0-pre.2...v2.0.0) **Closed issues:** @@ -912,6 +751,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Update feathers-rest to version 1.7.2 🚀 [\#160](https://github.com/feathersjs/client/pull/160) ([greenkeeperio-bot](https://github.com/greenkeeperio-bot)) ## [v2.0.0-pre.2](https://github.com/feathersjs/client/tree/v2.0.0-pre.2) (2017-03-08) + [Full Changelog](https://github.com/feathersjs/client/compare/v2.0.0-pre.1...v2.0.0-pre.2) **Closed issues:** @@ -937,6 +777,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Update ws to version 2.0.0 🚀 [\#139](https://github.com/feathersjs/client/pull/139) ([greenkeeperio-bot](https://github.com/greenkeeperio-bot)) ## [v2.0.0-pre.1](https://github.com/feathersjs/client/tree/v2.0.0-pre.1) (2017-01-11) + [Full Changelog](https://github.com/feathersjs/client/compare/v1.9.0...v2.0.0-pre.1) **Closed issues:** @@ -948,6 +789,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Feathers Auth Update [\#131](https://github.com/feathersjs/client/pull/131) ([flyboarder](https://github.com/flyboarder)) ## [v1.9.0](https://github.com/feathersjs/client/tree/v1.9.0) (2016-12-31) + [Full Changelog](https://github.com/feathersjs/client/compare/v1.8.0...v1.9.0) **Closed issues:** @@ -968,6 +810,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - superagent@3.1.0 breaks build 🚨 [\#121](https://github.com/feathersjs/client/pull/121) ([greenkeeperio-bot](https://github.com/greenkeeperio-bot)) ## [v1.8.0](https://github.com/feathersjs/client/tree/v1.8.0) (2016-11-26) + [Full Changelog](https://github.com/feathersjs/client/compare/v1.7.2...v1.8.0) **Closed issues:** @@ -986,6 +829,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Update feathers-commons to version 0.8.0 🚀 [\#111](https://github.com/feathersjs/client/pull/111) ([greenkeeperio-bot](https://github.com/greenkeeperio-bot)) ## [v1.7.2](https://github.com/feathersjs/client/tree/v1.7.2) (2016-11-08) + [Full Changelog](https://github.com/feathersjs/client/compare/v1.7.1...v1.7.2) **Merged pull requests:** @@ -994,6 +838,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Update feathers-socketio to version 1.4.2 🚀 [\#109](https://github.com/feathersjs/client/pull/109) ([greenkeeperio-bot](https://github.com/greenkeeperio-bot)) ## [v1.7.1](https://github.com/feathersjs/client/tree/v1.7.1) (2016-11-02) + [Full Changelog](https://github.com/feathersjs/client/compare/v1.7.0...v1.7.1) **Closed issues:** @@ -1006,6 +851,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Make sure Bower and NPM version are in sync [\#107](https://github.com/feathersjs/client/pull/107) ([daffl](https://github.com/daffl)) ## [v1.7.0](https://github.com/feathersjs/client/tree/v1.7.0) (2016-11-02) + [Full Changelog](https://github.com/feathersjs/client/compare/v1.6.2...v1.7.0) **Closed issues:** @@ -1022,6 +868,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Cross browser testing in Saucelabs [\#100](https://github.com/feathersjs/client/pull/100) ([daffl](https://github.com/daffl)) ## [v1.6.2](https://github.com/feathersjs/client/tree/v1.6.2) (2016-10-22) + [Full Changelog](https://github.com/feathersjs/client/compare/v1.6.1...v1.6.2) **Closed issues:** @@ -1038,6 +885,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Update feathers-hooks to version 1.5.8 🚀 [\#91](https://github.com/feathersjs/client/pull/91) ([greenkeeperio-bot](https://github.com/greenkeeperio-bot)) ## [v1.6.1](https://github.com/feathersjs/client/tree/v1.6.1) (2016-09-15) + [Full Changelog](https://github.com/feathersjs/client/compare/v1.6.0...v1.6.1) **Closed issues:** @@ -1049,6 +897,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Update feathers to version 2.0.2 🚀 [\#90](https://github.com/feathersjs/client/pull/90) ([greenkeeperio-bot](https://github.com/greenkeeperio-bot)) ## [v1.6.0](https://github.com/feathersjs/client/tree/v1.6.0) (2016-09-09) + [Full Changelog](https://github.com/feathersjs/client/compare/v1.5.3...v1.6.0) **Closed issues:** @@ -1063,6 +912,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Update feathers-memory to version 0.8.0 🚀 [\#88](https://github.com/feathersjs/client/pull/88) ([greenkeeperio-bot](https://github.com/greenkeeperio-bot)) ## [v1.5.3](https://github.com/feathersjs/client/tree/v1.5.3) (2016-08-31) + [Full Changelog](https://github.com/feathersjs/client/compare/v1.5.2...v1.5.3) **Closed issues:** @@ -1077,6 +927,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Update feathers-hooks to version 1.5.6 🚀 [\#75](https://github.com/feathersjs/client/pull/75) ([greenkeeperio-bot](https://github.com/greenkeeperio-bot)) ## [v1.5.2](https://github.com/feathersjs/client/tree/v1.5.2) (2016-08-12) + [Full Changelog](https://github.com/feathersjs/client/compare/v1.5.1...v1.5.2) **Closed issues:** @@ -1089,6 +940,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Update mocha to version 3.0.0 🚀 [\#72](https://github.com/feathersjs/client/pull/72) ([greenkeeperio-bot](https://github.com/greenkeeperio-bot)) ## [v1.5.1](https://github.com/feathersjs/client/tree/v1.5.1) (2016-07-14) + [Full Changelog](https://github.com/feathersjs/client/compare/v1.5.0...v1.5.1) **Merged pull requests:** @@ -1096,6 +948,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Update feathers-rest to version 1.4.3 🚀 [\#70](https://github.com/feathersjs/client/pull/70) ([greenkeeperio-bot](https://github.com/greenkeeperio-bot)) ## [v1.5.0](https://github.com/feathersjs/client/tree/v1.5.0) (2016-07-05) + [Full Changelog](https://github.com/feathersjs/client/compare/v1.4.1...v1.5.0) **Closed issues:** @@ -1103,9 +956,11 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Refresh browser [\#68](https://github.com/feathersjs/client/issues/68) ## [v1.4.1](https://github.com/feathersjs/client/tree/v1.4.1) (2016-06-27) + [Full Changelog](https://github.com/feathersjs/client/compare/v1.4.0...v1.4.1) ## [v1.4.0](https://github.com/feathersjs/client/tree/v1.4.0) (2016-06-24) + [Full Changelog](https://github.com/feathersjs/client/compare/v1.3.2...v1.4.0) **Closed issues:** @@ -1119,6 +974,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Update feathers-authentication to version 0.7.9 🚀 [\#63](https://github.com/feathersjs/client/pull/63) ([greenkeeperio-bot](https://github.com/greenkeeperio-bot)) ## [v1.3.2](https://github.com/feathersjs/client/tree/v1.3.2) (2016-06-09) + [Full Changelog](https://github.com/feathersjs/client/compare/v1.3.1...v1.3.2) **Merged pull requests:** @@ -1126,6 +982,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Update feathers-authentication to version 0.7.8 🚀 [\#61](https://github.com/feathersjs/client/pull/61) ([greenkeeperio-bot](https://github.com/greenkeeperio-bot)) ## [v1.3.1](https://github.com/feathersjs/client/tree/v1.3.1) (2016-06-04) + [Full Changelog](https://github.com/feathersjs/client/compare/v1.3.0...v1.3.1) **Merged pull requests:** @@ -1133,6 +990,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Update feathers-rest to version 1.4.2 🚀 [\#60](https://github.com/feathersjs/client/pull/60) ([greenkeeperio-bot](https://github.com/greenkeeperio-bot)) ## [v1.3.0](https://github.com/feathersjs/client/tree/v1.3.0) (2016-05-30) + [Full Changelog](https://github.com/feathersjs/client/compare/v1.2.1...v1.3.0) **Merged pull requests:** @@ -1144,6 +1002,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Update feathers-primus to version 1.4.1 🚀 [\#52](https://github.com/feathersjs/client/pull/52) ([greenkeeperio-bot](https://github.com/greenkeeperio-bot)) ## [v1.2.1](https://github.com/feathersjs/client/tree/v1.2.1) (2016-05-19) + [Full Changelog](https://github.com/feathersjs/client/compare/v1.2.0...v1.2.1) **Closed issues:** @@ -1156,6 +1015,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Update babel-plugin-add-module-exports to version 0.2.0 🚀 [\#46](https://github.com/feathersjs/client/pull/46) ([greenkeeperio-bot](https://github.com/greenkeeperio-bot)) ## [v1.2.0](https://github.com/feathersjs/client/tree/v1.2.0) (2016-04-29) + [Full Changelog](https://github.com/feathersjs/client/compare/v1.1.0...v1.2.0) **Closed issues:** @@ -1172,6 +1032,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Update feathers-memory to version 0.7.0 🚀 [\#33](https://github.com/feathersjs/client/pull/33) ([greenkeeperio-bot](https://github.com/greenkeeperio-bot)) ## [v1.1.0](https://github.com/feathersjs/client/tree/v1.1.0) (2016-04-03) + [Full Changelog](https://github.com/feathersjs/client/compare/v1.0.0...v1.1.0) **Merged pull requests:** @@ -1179,6 +1040,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Update all dependencies 🌴 [\#31](https://github.com/feathersjs/client/pull/31) ([greenkeeperio-bot](https://github.com/greenkeeperio-bot)) ## [v1.0.0](https://github.com/feathersjs/client/tree/v1.0.0) (2016-03-14) + [Full Changelog](https://github.com/feathersjs/client/compare/v1.0.0-pre.3...v1.0.0) **Merged pull requests:** @@ -1186,9 +1048,11 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Use a gcc version that can build bcrypt [\#30](https://github.com/feathersjs/client/pull/30) ([daffl](https://github.com/daffl)) ## [v1.0.0-pre.3](https://github.com/feathersjs/client/tree/v1.0.0-pre.3) (2016-03-14) + [Full Changelog](https://github.com/feathersjs/client/compare/v1.0.0-pre.2...v1.0.0-pre.3) ## [v1.0.0-pre.2](https://github.com/feathersjs/client/tree/v1.0.0-pre.2) (2016-03-04) + [Full Changelog](https://github.com/feathersjs/client/compare/v0.5.3...v1.0.0-pre.2) **Closed issues:** @@ -1198,12 +1062,15 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Add documentation for using in React Native [\#10](https://github.com/feathersjs/client/issues/10) ## [v0.5.3](https://github.com/feathersjs/client/tree/v0.5.3) (2016-02-12) + [Full Changelog](https://github.com/feathersjs/client/compare/v1.0.0-pre.1...v0.5.3) ## [v1.0.0-pre.1](https://github.com/feathersjs/client/tree/v1.0.0-pre.1) (2016-02-11) + [Full Changelog](https://github.com/feathersjs/client/compare/v0.5.2...v1.0.0-pre.1) ## [v0.5.2](https://github.com/feathersjs/client/tree/v0.5.2) (2016-02-09) + [Full Changelog](https://github.com/feathersjs/client/compare/v0.5.1...v0.5.2) **Merged pull requests:** @@ -1212,6 +1079,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Adding nsp check [\#24](https://github.com/feathersjs/client/pull/24) ([marshallswain](https://github.com/marshallswain)) ## [v0.5.1](https://github.com/feathersjs/client/tree/v0.5.1) (2016-01-15) + [Full Changelog](https://github.com/feathersjs/client/compare/v0.5.0...v0.5.1) **Closed issues:** @@ -1225,6 +1093,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - fix issue \#21 [\#22](https://github.com/feathersjs/client/pull/22) ([wuyuanyi135](https://github.com/wuyuanyi135)) ## [v0.5.0](https://github.com/feathersjs/client/tree/v0.5.0) (2016-01-05) + [Full Changelog](https://github.com/feathersjs/client/compare/v0.4.0...v0.5.0) **Closed issues:** @@ -1237,6 +1106,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Adding events and querystring dependencies. [\#16](https://github.com/feathersjs/client/pull/16) ([marshallswain](https://github.com/marshallswain)) ## [v0.4.0](https://github.com/feathersjs/client/tree/v0.4.0) (2015-12-11) + [Full Changelog](https://github.com/feathersjs/client/compare/v0.3.3...v0.4.0) **Fixed bugs:** @@ -1248,6 +1118,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - .babelrc messes with react-native [\#15](https://github.com/feathersjs/client/issues/15) ## [v0.3.3](https://github.com/feathersjs/client/tree/v0.3.3) (2015-11-27) + [Full Changelog](https://github.com/feathersjs/client/compare/v0.3.2...v0.3.3) **Closed issues:** @@ -1259,6 +1130,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Fix es6 build and add Steal compatibility. [\#13](https://github.com/feathersjs/client/pull/13) ([marshallswain](https://github.com/marshallswain)) ## [v0.3.2](https://github.com/feathersjs/client/tree/v0.3.2) (2015-11-26) + [Full Changelog](https://github.com/feathersjs/client/compare/v0.3.1...v0.3.2) **Closed issues:** @@ -1266,6 +1138,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Update lodash [\#11](https://github.com/feathersjs/client/issues/11) ## [v0.3.1](https://github.com/feathersjs/client/tree/v0.3.1) (2015-11-26) + [Full Changelog](https://github.com/feathersjs/client/compare/v0.3.0...v0.3.1) **Closed issues:** @@ -1273,6 +1146,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Working with can-connect [\#8](https://github.com/feathersjs/client/issues/8) ## [v0.3.0](https://github.com/feathersjs/client/tree/v0.3.0) (2015-11-15) + [Full Changelog](https://github.com/feathersjs/client/compare/v0.2.1...v0.3.0) **Closed issues:** @@ -1284,6 +1158,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Migration to ES6 and using Promises [\#9](https://github.com/feathersjs/client/pull/9) ([daffl](https://github.com/daffl)) ## [v0.2.1](https://github.com/feathersjs/client/tree/v0.2.1) (2015-10-06) + [Full Changelog](https://github.com/feathersjs/client/compare/v0.2.0...v0.2.1) **Merged pull requests:** @@ -1291,9 +1166,11 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Make client depend on feathers-commons, remove arguments.js [\#6](https://github.com/feathersjs/client/pull/6) ([daffl](https://github.com/daffl)) ## [v0.2.0](https://github.com/feathersjs/client/tree/v0.2.0) (2015-07-18) + [Full Changelog](https://github.com/feathersjs/client/compare/v0.1.3...v0.2.0) ## [v0.1.3](https://github.com/feathersjs/client/tree/v0.1.3) (2015-07-06) + [Full Changelog](https://github.com/feathersjs/client/compare/v0.1.2...v0.1.3) **Merged pull requests:** @@ -1301,6 +1178,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Fixing requires and missing deps. [\#5](https://github.com/feathersjs/client/pull/5) ([marshallswain](https://github.com/marshallswain)) ## [v0.1.2](https://github.com/feathersjs/client/tree/v0.1.2) (2015-06-22) + [Full Changelog](https://github.com/feathersjs/client/compare/v0.1.1...v0.1.2) **Closed issues:** @@ -1308,12 +1186,13 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Publish to NPM and Bower [\#1](https://github.com/feathersjs/client/issues/1) ## [v0.1.1](https://github.com/feathersjs/client/tree/v0.1.1) (2015-06-21) + [Full Changelog](https://github.com/feathersjs/client/compare/v0.0.1...v0.1.1) ## [v0.0.1](https://github.com/feathersjs/client/tree/v0.0.1) (2015-06-21) + [Full Changelog](https://github.com/feathersjs/client/compare/v0.1.0...v0.0.1) ## [v0.1.0](https://github.com/feathersjs/client/tree/v0.1.0) (2015-06-06) - -\* *This Change Log was automatically generated by [github_changelog_generator](https://github.com/skywinder/Github-Changelog-Generator)* +\* _This Change Log was automatically generated by [github_changelog_generator](https://github.com/skywinder/Github-Changelog-Generator)_ diff --git a/packages/client/README.md b/packages/client/README.md index 6cd96aeff9..f4a96f2833 100644 --- a/packages/client/README.md +++ b/packages/client/README.md @@ -1,8 +1,8 @@ # @feathersjs/client [![CI](https://github.com/feathersjs/feathers/workflows/CI/badge.svg)](https://github.com/feathersjs/feathers/actions?query=workflow%3ACI) -[![Dependency Status](https://img.shields.io/david/feathersjs/client.svg?style=flat-square)](https://david-dm.org/feathersjs/client) [![Download Status](https://img.shields.io/npm/dm/@feathersjs/client.svg?style=flat-square)](https://www.npmjs.com/package/@feathersjs/client) +[![Discord](https://badgen.net/badge/icon/discord?icon=discord&label)](https://discord.gg/qa8kez8QBx) > A client build for FeathersJS @@ -18,6 +18,6 @@ Refer to the [Feathers client API documentation](https://docs.feathersjs.com/api ## License -Copyright (c) 2021 [Feathers contributors](https://github.com/feathersjs/feathers/graphs/contributors) +Copyright (c) 2022 [Feathers contributors](https://github.com/feathersjs/feathers/graphs/contributors) Licensed under the [MIT license](LICENSE). diff --git a/packages/client/package.json b/packages/client/package.json index 64fb12d405..cbd19745ae 100644 --- a/packages/client/package.json +++ b/packages/client/package.json @@ -1,10 +1,11 @@ { "name": "@feathersjs/client", "description": "A module that consolidates Feathers client modules for REST (jQuery, Request, Superagent) and Websocket (Socket.io, Primus) connections", - "version": "5.0.0-pre.16", + "version": "5.0.0-pre.31", "repository": { "type": "git", - "url": "https://github.com/feathersjs/feathers.git" + "url": "https://github.com/feathersjs/feathers.git", + "directory": "packages/client" }, "license": "MIT", "funding": { @@ -24,7 +25,7 @@ "node": ">= 12" }, "main": "dist/feathers", - "types": "dist/", + "types": "dist/feathers", "files": [ "CHANGELOG.md", "LICENSE", @@ -48,31 +49,31 @@ "IE 11" ], "dependencies": { - "@feathersjs/authentication-client": "^5.0.0-pre.16", - "@feathersjs/errors": "^5.0.0-pre.16", - "@feathersjs/feathers": "^5.0.0-pre.16", - "@feathersjs/rest-client": "^5.0.0-pre.16", - "@feathersjs/socketio-client": "^5.0.0-pre.16" + "@feathersjs/authentication-client": "^5.0.0-pre.31", + "@feathersjs/errors": "^5.0.0-pre.31", + "@feathersjs/feathers": "^5.0.0-pre.31", + "@feathersjs/rest-client": "^5.0.0-pre.31", + "@feathersjs/socketio-client": "^5.0.0-pre.31" }, "devDependencies": { - "@babel/core": "^7.16.7", - "@babel/preset-env": "^7.16.7", - "@feathersjs/express": "^5.0.0-pre.16", - "@feathersjs/memory": "^5.0.0-pre.16", - "@feathersjs/socketio": "^5.0.0-pre.16", - "@feathersjs/tests": "^5.0.0-pre.16", - "babel-loader": "^8.2.3", - "mocha": "^9.1.3", + "@babel/core": "^7.19.3", + "@babel/preset-env": "^7.19.3", + "@feathersjs/express": "^5.0.0-pre.31", + "@feathersjs/memory": "^5.0.0-pre.31", + "@feathersjs/socketio": "^5.0.0-pre.31", + "@feathersjs/tests": "^5.0.0-pre.31", + "babel-loader": "^8.2.5", + "mocha": "^10.0.0", "mocha-puppeteer": "^0.14.0", "node-fetch": "^2.6.1", - "shx": "^0.3.3", - "socket.io-client": "^4.4.0", - "superagent": "^6.1.0", - "ts-loader": "^9.2.6", - "typescript": "^4.5.4", - "webpack": "^5.65.0", - "webpack-cli": "^4.9.1", + "shx": "^0.3.4", + "socket.io-client": "^4.5.2", + "superagent": "^8.0.0", + "ts-loader": "^9.4.1", + "typescript": "^4.8.4", + "webpack": "^5.74.0", + "webpack-cli": "^4.10.0", "webpack-merge": "^5.8.0" }, - "gitHead": "f0cd227a82d159b528193bd33747c97684a48773" + "gitHead": "4500dbeb8cea566678cf88b3313a88efd93a2ed9" } diff --git a/packages/client/src/core.ts b/packages/client/src/core.ts index 325f8d781e..1138c62281 100644 --- a/packages/client/src/core.ts +++ b/packages/client/src/core.ts @@ -1 +1 @@ -export * from '@feathersjs/feathers'; +export * from '@feathersjs/feathers' diff --git a/packages/client/src/feathers.ts b/packages/client/src/feathers.ts index 313f3e732c..e3522cb374 100644 --- a/packages/client/src/feathers.ts +++ b/packages/client/src/feathers.ts @@ -1,13 +1,13 @@ -import { feathers } from '@feathersjs/feathers'; -import authentication from '@feathersjs/authentication-client'; -import rest from '@feathersjs/rest-client'; -import socketio from '@feathersjs/socketio-client'; +import { feathers } from '@feathersjs/feathers' +import authentication from '@feathersjs/authentication-client' +import rest from '@feathersjs/rest-client' +import socketio from '@feathersjs/socketio-client' -export * from '@feathersjs/feathers'; -export * as errors from '@feathersjs/errors'; -export { authentication, rest, socketio }; -export default feathers; +export * from '@feathersjs/feathers' +export * as errors from '@feathersjs/errors' +export { authentication, rest, socketio } +export default feathers if (typeof module !== 'undefined') { - module.exports = Object.assign(feathers, module.exports); + module.exports = Object.assign(feathers, module.exports) } diff --git a/packages/client/test/fetch.test.ts b/packages/client/test/fetch.test.ts index 3a0c49bdb1..22f626a4a6 100644 --- a/packages/client/test/fetch.test.ts +++ b/packages/client/test/fetch.test.ts @@ -1,24 +1,24 @@ -//@ts-ignore -import fetch from 'node-fetch'; -import { Server } from 'http'; -import { clientTests } from '@feathersjs/tests'; +/* eslint-disable @typescript-eslint/ban-ts-comment */ +// @ts-ignore +import fetch from 'node-fetch' +import { Server } from 'http' +import { clientTests } from '@feathersjs/tests' -import * as feathers from '../dist/feathers'; -import app from './fixture'; +import * as feathers from '../dist/feathers' +import app from './fixture' describe('fetch REST connector', function () { - let server: Server; - const rest = feathers.rest('http://localhost:8889'); - const client = feathers.default() - .configure(rest.fetch(fetch)); + let server: Server + const rest = feathers.rest('http://localhost:8889') + const client = feathers.default().configure(rest.fetch(fetch)) before(async () => { - server = await app().listen(8889); - }); + server = await app().listen(8889) + }) after(function (done) { - server.close(done); - }); + server.close(done) + }) - clientTests(client, 'todos'); -}); + clientTests(client, 'todos') +}) diff --git a/packages/client/test/fixture.ts b/packages/client/test/fixture.ts index c286bc1a8f..de42f60d65 100644 --- a/packages/client/test/fixture.ts +++ b/packages/client/test/fixture.ts @@ -1,80 +1,79 @@ -import { feathers, Application, HookContext, Id, Params } from '@feathersjs/feathers'; -import * as express from '@feathersjs/express'; -import { Service } from '@feathersjs/memory'; +import { feathers, Application, HookContext, Id, Params } from '@feathersjs/feathers' +import * as express from '@feathersjs/express' +import { MemoryService } from '@feathersjs/memory' // eslint-disable-next-line no-extend-native Object.defineProperty(Error.prototype, 'toJSON', { - value () { - const alt: any = {}; + value() { + const alt: any = {} Object.getOwnPropertyNames(this).forEach((key: string) => { - alt[key] = this[key]; - }); + alt[key] = this[key] + }) - return alt; + return alt }, configurable: true -}); +}) // Create an in-memory CRUD service for our Todos -class TodoService extends Service { - async get (id: Id, params: Params) { +class TodoService extends MemoryService { + async get(id: Id, params: Params) { if (params.query.error) { - throw new Error('Something went wrong'); + throw new Error('Something went wrong') } - return super.get(id).then(data => - Object.assign({ query: params.query }, data) - ); + return super.get(id).then((data) => Object.assign({ query: params.query }, data)) } } export default (configurer?: (app: Application) => void) => { - const app = express.default(feathers()) + const app = express + .default(feathers()) // Parse HTTP bodies .use(express.json()) .use(express.urlencoded({ extended: true })) // Host the current directory (for index.html) .use(express.static(process.cwd())) - .configure(express.rest()); + .configure(express.rest()) if (typeof configurer === 'function') { - configurer.call(app, app); + configurer.call(app, app) } app // Host our Todos service on the /todos path - .use('/todos', new TodoService({ - multi: true - })) - .use(express.errorHandler()); + .use( + '/todos', + new TodoService({ + multi: true + }) + ) + .use(express.errorHandler()) const testTodo = { text: 'some todo', complete: false - }; - const service: any = app.service('todos'); + } + const service: any = app.service('todos') - service.create(testTodo); + service.create(testTodo) service.hooks({ after: { - remove (hook: HookContext) { + remove(hook: HookContext) { if (hook.id === null) { - service._uId = 0; - return service.create(testTodo) - .then(() => hook); + service._uId = 0 + return service.create(testTodo).then(() => hook) } } } - }); + }) - app.on('connection', connection => - (app as any).channel('general').join(connection) - ); + app.on('connection', (connection) => (app as any).channel('general').join(connection)) if (service.publish) { - service.publish(() => app.channel('general')); + service.publish(() => app.channel('general')) } - return app; -}; + return app +} diff --git a/packages/client/test/socketio.test.ts b/packages/client/test/socketio.test.ts index 8438bbf870..74a86cd73e 100644 --- a/packages/client/test/socketio.test.ts +++ b/packages/client/test/socketio.test.ts @@ -1,28 +1,27 @@ -import { io } from 'socket.io-client'; -import socketio from '@feathersjs/socketio'; -import { Server } from 'http'; -import { clientTests } from '@feathersjs/tests'; +import { io } from 'socket.io-client' +import socketio from '@feathersjs/socketio' +import { Server } from 'http' +import { clientTests } from '@feathersjs/tests' -import * as feathers from '../dist/feathers'; -import app from './fixture'; +import * as feathers from '../dist/feathers' +import app from './fixture' describe('Socket.io connector', function () { - let server: Server; - const socket = io('http://localhost:9988'); - const client = feathers.default() - .configure(feathers.socketio(socket)); + let server: Server + const socket = io('http://localhost:9988') + const client = feathers.default().configure(feathers.socketio(socket)) before(async () => { - server = await app(app => app.configure(socketio())).listen(9988); - }); + server = await app((app) => app.configure(socketio())).listen(9988) + }) after(function (done) { socket.once('disconnect', () => { - server.close(); - done(); - }); - socket.disconnect(); - }); + server.close() + done() + }) + socket.disconnect() + }) - clientTests(client, 'todos'); -}); + clientTests(client, 'todos') +}) diff --git a/packages/client/test/superagent.test.ts b/packages/client/test/superagent.test.ts index 567d1a9be2..ea158b9747 100644 --- a/packages/client/test/superagent.test.ts +++ b/packages/client/test/superagent.test.ts @@ -1,23 +1,22 @@ -import superagent from 'superagent'; -import { clientTests } from '@feathersjs/tests'; -import { Server } from 'http'; +import superagent from 'superagent' +import { clientTests } from '@feathersjs/tests' +import { Server } from 'http' -import * as feathers from '../dist/feathers'; -import app from './fixture'; +import * as feathers from '../dist/feathers' +import app from './fixture' describe('Superagent REST connector', function () { - let server: Server; - const rest = feathers.rest('http://localhost:8889'); - const client = feathers.default() - .configure(rest.superagent(superagent)); + let server: Server + const rest = feathers.rest('http://localhost:8889') + const client = feathers.default().configure(rest.superagent(superagent)) before(async () => { - server = await app().listen(8889); - }); + server = await app().listen(8889) + }) after(function (done) { - server.close(done); - }); + server.close(done) + }) - clientTests(client, 'todos'); -}); + clientTests(client, 'todos') +}) diff --git a/packages/commons/CHANGELOG.md b/packages/commons/CHANGELOG.md index 6368017ea9..63da543445 100644 --- a/packages/commons/CHANGELOG.md +++ b/packages/commons/CHANGELOG.md @@ -3,418 +3,294 @@ All notable changes to this project will be documented in this file. See [Conventional Commits](https://conventionalcommits.org) for commit guidelines. -# [5.0.0-pre.16](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.15...v5.0.0-pre.16) (2022-01-12) +# [5.0.0-pre.31](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.30...v5.0.0-pre.31) (2022-10-12) **Note:** Version bump only for package @feathersjs/commons +# [5.0.0-pre.30](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.29...v5.0.0-pre.30) (2022-10-07) +### Features +- **core:** Allow to unregister services at runtime ([#2756](https://github.com/feathersjs/feathers/issues/2756)) ([d16601f](https://github.com/feathersjs/feathers/commit/d16601f2277dca5357866ffdefba2a611f6dc7fa)) - -# [5.0.0-pre.15](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.14...v5.0.0-pre.15) (2021-11-27) +# [5.0.0-pre.29](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.28...v5.0.0-pre.29) (2022-09-16) **Note:** Version bump only for package @feathersjs/commons +# [5.0.0-pre.28](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.27...v5.0.0-pre.28) (2022-08-03) +### Bug Fixes +- **cli:** Improve generated application and client ([#2701](https://github.com/feathersjs/feathers/issues/2701)) ([bd55ffb](https://github.com/feathersjs/feathers/commit/bd55ffb812e89bf215f4515e7f137656ea888c3f)) - -# [5.0.0-pre.14](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.13...v5.0.0-pre.14) (2021-10-13) +# [5.0.0-pre.27](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.26...v5.0.0-pre.27) (2022-07-13) **Note:** Version bump only for package @feathersjs/commons +# [5.0.0-pre.26](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.25...v5.0.0-pre.26) (2022-06-22) +**Note:** Version bump only for package @feathersjs/commons +# [5.0.0-pre.25](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.24...v5.0.0-pre.25) (2022-06-22) +**Note:** Version bump only for package @feathersjs/commons -# [5.0.0-pre.13](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.12...v5.0.0-pre.13) (2021-10-13) +# [5.0.0-pre.24](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.23...v5.0.0-pre.24) (2022-06-21) **Note:** Version bump only for package @feathersjs/commons +# [5.0.0-pre.23](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.22...v5.0.0-pre.23) (2022-06-06) +**Note:** Version bump only for package @feathersjs/commons +# [5.0.0-pre.22](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.21...v5.0.0-pre.22) (2022-05-24) +**Note:** Version bump only for package @feathersjs/commons -# [5.0.0-pre.12](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.11...v5.0.0-pre.12) (2021-10-12) +# [5.0.0-pre.20](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.19...v5.0.0-pre.20) (2022-05-04) **Note:** Version bump only for package @feathersjs/commons +# [5.0.0-pre.19](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.18...v5.0.0-pre.19) (2022-05-01) +**Note:** Version bump only for package @feathersjs/commons +# [5.0.0-pre.18](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.17...v5.0.0-pre.18) (2022-04-11) +**Note:** Version bump only for package @feathersjs/commons -# [5.0.0-pre.11](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.10...v5.0.0-pre.11) (2021-10-06) +# [5.0.0-pre.17](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.16...v5.0.0-pre.17) (2022-02-15) **Note:** Version bump only for package @feathersjs/commons +# [5.0.0-pre.16](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.15...v5.0.0-pre.16) (2022-01-12) +**Note:** Version bump only for package @feathersjs/commons +# [5.0.0-pre.15](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.14...v5.0.0-pre.15) (2021-11-27) +**Note:** Version bump only for package @feathersjs/commons -# [5.0.0-pre.10](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.9...v5.0.0-pre.10) (2021-09-19) +# [5.0.0-pre.14](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.13...v5.0.0-pre.14) (2021-10-13) **Note:** Version bump only for package @feathersjs/commons +# [5.0.0-pre.13](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.12...v5.0.0-pre.13) (2021-10-13) +**Note:** Version bump only for package @feathersjs/commons +# [5.0.0-pre.12](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.11...v5.0.0-pre.12) (2021-10-12) +**Note:** Version bump only for package @feathersjs/commons -# [5.0.0-pre.9](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.8...v5.0.0-pre.9) (2021-08-09) +# [5.0.0-pre.11](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.10...v5.0.0-pre.11) (2021-10-06) **Note:** Version bump only for package @feathersjs/commons +# [5.0.0-pre.10](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.9...v5.0.0-pre.10) (2021-09-19) +**Note:** Version bump only for package @feathersjs/commons +# [5.0.0-pre.9](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.8...v5.0.0-pre.9) (2021-08-09) +**Note:** Version bump only for package @feathersjs/commons # [5.0.0-pre.8](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.7...v5.0.0-pre.8) (2021-08-09) **Note:** Version bump only for package @feathersjs/commons - - - - # [5.0.0-pre.7](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.6...v5.0.0-pre.7) (2021-08-09) **Note:** Version bump only for package @feathersjs/commons - - - - # [5.0.0-pre.6](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.5...v5.0.0-pre.6) (2021-08-08) **Note:** Version bump only for package @feathersjs/commons - - - - # [5.0.0-pre.5](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.4...v5.0.0-pre.5) (2021-06-23) **Note:** Version bump only for package @feathersjs/commons - - - - # [5.0.0-pre.4](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.3...v5.0.0-pre.4) (2021-05-13) **Note:** Version bump only for package @feathersjs/commons - - - - # [5.0.0-pre.3](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.2...v5.0.0-pre.3) (2021-04-21) - ### Bug Fixes -* **typescript:** Improve TypeScript backwards compatibility ([#2310](https://github.com/feathersjs/feathers/issues/2310)) ([f33be73](https://github.com/feathersjs/feathers/commit/f33be73fc46a533efb15df9aab0658e3240d3897)) - +- **typescript:** Improve TypeScript backwards compatibility ([#2310](https://github.com/feathersjs/feathers/issues/2310)) ([f33be73](https://github.com/feathersjs/feathers/commit/f33be73fc46a533efb15df9aab0658e3240d3897)) ### Features -* **dependencies:** Remove direct debug dependency ([#2296](https://github.com/feathersjs/feathers/issues/2296)) ([501d416](https://github.com/feathersjs/feathers/commit/501d4164d30c6a126906dc640cdfdc82207ba34a)) - - - - +- **dependencies:** Remove direct debug dependency ([#2296](https://github.com/feathersjs/feathers/issues/2296)) ([501d416](https://github.com/feathersjs/feathers/commit/501d4164d30c6a126906dc640cdfdc82207ba34a)) # [5.0.0-pre.2](https://github.com/feathersjs/feathers/compare/v5.0.0-beta.1...v5.0.0-pre.2) (2021-04-06) **Note:** Version bump only for package @feathersjs/commons - - - - # [5.0.0-beta.1](https://github.com/feathersjs/feathers/compare/v5.0.0-beta.0...v5.0.0-beta.1) (2021-04-03) **Note:** Version bump only for package @feathersjs/commons - - - - # [5.0.0-beta.0](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.1...v5.0.0-beta.0) (2021-03-28) - ### Bug Fixes -* Update Grant usage and other dependencies ([#2264](https://github.com/feathersjs/feathers/issues/2264)) ([7b0f8fa](https://github.com/feathersjs/feathers/commit/7b0f8fad252419ed0ad0bf259cdf3104d322ab60)) - - - - +- Update Grant usage and other dependencies ([#2264](https://github.com/feathersjs/feathers/issues/2264)) ([7b0f8fa](https://github.com/feathersjs/feathers/commit/7b0f8fad252419ed0ad0bf259cdf3104d322ab60)) # [5.0.0-pre.1](https://github.com/feathersjs/feathers/compare/v4.5.11...v5.0.0-pre.1) (2020-12-17) - - # [5.0.0-pre.0](https://github.com/feathersjs/feathers/compare/v4.5.4...v5.0.0-pre.0) (2020-05-19) - ### Features -* **core:** Migrate @feathersjs/feathers to TypeScript ([#1963](https://github.com/feathersjs/feathers/issues/1963)) ([7812529](https://github.com/feathersjs/feathers/commit/7812529ff0f1008e21211f1d01efbc49795dbe55)) -* **core:** use @feathers/hooks and add async type ([#1929](https://github.com/feathersjs/feathers/issues/1929)) ([a5c4756](https://github.com/feathersjs/feathers/commit/a5c47562eae8410c82fe2f6308f26f8e78b6a3e8)) - - - - +- **core:** Migrate @feathersjs/feathers to TypeScript ([#1963](https://github.com/feathersjs/feathers/issues/1963)) ([7812529](https://github.com/feathersjs/feathers/commit/7812529ff0f1008e21211f1d01efbc49795dbe55)) +- **core:** use @feathers/hooks and add async type ([#1929](https://github.com/feathersjs/feathers/issues/1929)) ([a5c4756](https://github.com/feathersjs/feathers/commit/a5c47562eae8410c82fe2f6308f26f8e78b6a3e8)) # [5.0.0-pre.0](https://github.com/feathersjs/feathers/compare/v4.5.4...v5.0.0-pre.0) (2020-05-19) - ### Features -* **core:** Migrate @feathersjs/feathers to TypeScript ([#1963](https://github.com/feathersjs/feathers/issues/1963)) ([7812529](https://github.com/feathersjs/feathers/commit/7812529ff0f1008e21211f1d01efbc49795dbe55)) -* **core:** use @feathers/hooks and add async type ([#1929](https://github.com/feathersjs/feathers/issues/1929)) ([a5c4756](https://github.com/feathersjs/feathers/commit/a5c47562eae8410c82fe2f6308f26f8e78b6a3e8)) - - +- **core:** Migrate @feathersjs/feathers to TypeScript ([#1963](https://github.com/feathersjs/feathers/issues/1963)) ([7812529](https://github.com/feathersjs/feathers/commit/7812529ff0f1008e21211f1d01efbc49795dbe55)) +- **core:** use @feathers/hooks and add async type ([#1929](https://github.com/feathersjs/feathers/issues/1929)) ([a5c4756](https://github.com/feathersjs/feathers/commit/a5c47562eae8410c82fe2f6308f26f8e78b6a3e8)) ## [4.5.11](https://github.com/feathersjs/feathers/compare/v4.5.10...v4.5.11) (2020-12-05) **Note:** Version bump only for package @feathersjs/commons - - - - ## [4.5.10](https://github.com/feathersjs/feathers/compare/v4.5.9...v4.5.10) (2020-11-08) **Note:** Version bump only for package @feathersjs/commons - - - - ## [4.5.9](https://github.com/feathersjs/feathers/compare/v4.5.8...v4.5.9) (2020-10-09) **Note:** Version bump only for package @feathersjs/commons - - - - ## [4.5.8](https://github.com/feathersjs/feathers/compare/v4.5.7...v4.5.8) (2020-08-12) **Note:** Version bump only for package @feathersjs/commons - - - - ## [4.5.7](https://github.com/feathersjs/feathers/compare/v4.5.6...v4.5.7) (2020-07-24) **Note:** Version bump only for package @feathersjs/commons - - - - ## [4.5.5](https://github.com/feathersjs/feathers/compare/v4.5.4...v4.5.5) (2020-07-11) **Note:** Version bump only for package @feathersjs/commons - - - - ## [4.5.3](https://github.com/feathersjs/feathers/compare/v4.5.2...v4.5.3) (2020-04-17) **Note:** Version bump only for package @feathersjs/commons - - - - ## [4.5.2](https://github.com/feathersjs/feathers/compare/v4.5.1...v4.5.2) (2020-03-04) **Note:** Version bump only for package @feathersjs/commons - - - - ## [4.5.1](https://github.com/feathersjs/feathers/compare/v4.5.0...v4.5.1) (2020-01-24) **Note:** Version bump only for package @feathersjs/commons - - - - # [4.5.0](https://github.com/feathersjs/feathers/compare/v4.4.3...v4.5.0) (2020-01-18) **Note:** Version bump only for package @feathersjs/commons - - - - ## [4.4.3](https://github.com/feathersjs/feathers/compare/v4.4.1...v4.4.3) (2019-12-06) **Note:** Version bump only for package @feathersjs/commons - - - - ## [4.4.1](https://github.com/feathersjs/feathers/compare/v4.4.0...v4.4.1) (2019-11-27) **Note:** Version bump only for package @feathersjs/commons - - - - ## [4.3.7](https://github.com/feathersjs/feathers/compare/v4.3.6...v4.3.7) (2019-10-14) - ### Bug Fixes -* make __hooks writable and configurable ([#1520](https://github.com/feathersjs/feathers/issues/1520)) ([1c6c374](https://github.com/feathersjs/feathers/commit/1c6c3742ecf1cb813be56074da89e6736d03ffe8)) - - - - +- make \_\_hooks writable and configurable ([#1520](https://github.com/feathersjs/feathers/issues/1520)) ([1c6c374](https://github.com/feathersjs/feathers/commit/1c6c3742ecf1cb813be56074da89e6736d03ffe8)) # [4.3.0](https://github.com/feathersjs/feathers/compare/v4.3.0-pre.4...v4.3.0) (2019-08-27) **Note:** Version bump only for package @feathersjs/commons - - - - # [4.3.0-pre.4](https://github.com/feathersjs/feathers/compare/v4.3.0-pre.3...v4.3.0-pre.4) (2019-08-22) **Note:** Version bump only for package @feathersjs/commons - - - - # [4.3.0-pre.3](https://github.com/feathersjs/feathers/compare/v4.3.0-pre.2...v4.3.0-pre.3) (2019-08-19) - ### Bug Fixes -* Update all dependencies ([7d53a00](https://github.com/feathersjs/feathers/commit/7d53a00)) - - - - +- Update all dependencies ([7d53a00](https://github.com/feathersjs/feathers/commit/7d53a00)) # [4.3.0-pre.2](https://github.com/feathersjs/feathers/compare/v4.3.0-pre.1...v4.3.0-pre.2) (2019-08-02) **Note:** Version bump only for package @feathersjs/commons - - - - # [4.3.0-pre.1](https://github.com/feathersjs/feathers/compare/v4.0.0-pre.5...v4.3.0-pre.1) (2019-07-11) **Note:** Version bump only for package @feathersjs/commons - - - - # [4.0.0-pre.5](https://github.com/feathersjs/feathers/compare/v4.0.0-pre.4...v4.0.0-pre.5) (2019-07-10) **Note:** Version bump only for package @feathersjs/commons - - - - # [4.0.0-pre.4](https://github.com/feathersjs/feathers/compare/v4.0.0-pre.3...v4.0.0-pre.4) (2019-07-05) **Note:** Version bump only for package @feathersjs/commons - - - - # [4.0.0-pre.3](https://github.com/feathersjs/feathers/compare/v4.0.0-pre.2...v4.0.0-pre.3) (2019-06-01) - ### Bug Fixes -* Update dependencies and fix tests ([#1373](https://github.com/feathersjs/feathers/issues/1373)) ([d743a7f](https://github.com/feathersjs/feathers/commit/d743a7f)) - - - - +- Update dependencies and fix tests ([#1373](https://github.com/feathersjs/feathers/issues/1373)) ([d743a7f](https://github.com/feathersjs/feathers/commit/d743a7f)) # [4.0.0-pre.0](https://github.com/feathersjs/feathers/compare/v3.2.0-pre.1...v4.0.0-pre.0) (2019-04-21) - ### Bug Fixes -* Make Mocha a proper devDependency for every repository ([#1053](https://github.com/feathersjs/feathers/issues/1053)) ([9974803](https://github.com/feathersjs/feathers/commit/9974803)) -* Update all dependencies to latest ([#1206](https://github.com/feathersjs/feathers/issues/1206)) ([e51e0f6](https://github.com/feathersjs/feathers/commit/e51e0f6)) -* use minimal RegExp matching for better performance ([#977](https://github.com/feathersjs/feathers/issues/977)) ([3ca7e97](https://github.com/feathersjs/feathers/commit/3ca7e97)) - +- Make Mocha a proper devDependency for every repository ([#1053](https://github.com/feathersjs/feathers/issues/1053)) ([9974803](https://github.com/feathersjs/feathers/commit/9974803)) +- Update all dependencies to latest ([#1206](https://github.com/feathersjs/feathers/issues/1206)) ([e51e0f6](https://github.com/feathersjs/feathers/commit/e51e0f6)) +- use minimal RegExp matching for better performance ([#977](https://github.com/feathersjs/feathers/issues/977)) ([3ca7e97](https://github.com/feathersjs/feathers/commit/3ca7e97)) ### Features -* Add TypeScript definitions ([#1275](https://github.com/feathersjs/feathers/issues/1275)) ([9dd6713](https://github.com/feathersjs/feathers/commit/9dd6713)) -* Common database adapter utilities and test suite ([#1130](https://github.com/feathersjs/feathers/issues/1130)) ([17b3dc8](https://github.com/feathersjs/feathers/commit/17b3dc8)) -* Remove (hook, next) signature and SKIP support ([#1269](https://github.com/feathersjs/feathers/issues/1269)) ([211c0f8](https://github.com/feathersjs/feathers/commit/211c0f8)) - +- Add TypeScript definitions ([#1275](https://github.com/feathersjs/feathers/issues/1275)) ([9dd6713](https://github.com/feathersjs/feathers/commit/9dd6713)) +- Common database adapter utilities and test suite ([#1130](https://github.com/feathersjs/feathers/issues/1130)) ([17b3dc8](https://github.com/feathersjs/feathers/commit/17b3dc8)) +- Remove (hook, next) signature and SKIP support ([#1269](https://github.com/feathersjs/feathers/issues/1269)) ([211c0f8](https://github.com/feathersjs/feathers/commit/211c0f8)) ### BREAKING CHANGES -* Move database adapter utilities from @feathersjs/commons into its own module - - - - +- Move database adapter utilities from @feathersjs/commons into its own module -# [4.0.0](https://github.com/feathersjs/feathers/compare/@feathersjs/commons@3.0.1...@feathersjs/commons@4.0.0) (2018-12-16) +# [4.0.0](https://github.com/feathersjs/feathers/compare/@feathersjs/commons@3.0.1...@feathersjs/commons@4.0.0) (2018-12-16) ### Bug Fixes -* Make Mocha a proper devDependency for every repository ([#1053](https://github.com/feathersjs/feathers/issues/1053)) ([9974803](https://github.com/feathersjs/feathers/commit/9974803)) - +- Make Mocha a proper devDependency for every repository ([#1053](https://github.com/feathersjs/feathers/issues/1053)) ([9974803](https://github.com/feathersjs/feathers/commit/9974803)) ### Features -* Common database adapter utilities and test suite ([#1130](https://github.com/feathersjs/feathers/issues/1130)) ([17b3dc8](https://github.com/feathersjs/feathers/commit/17b3dc8)) - +- Common database adapter utilities and test suite ([#1130](https://github.com/feathersjs/feathers/issues/1130)) ([17b3dc8](https://github.com/feathersjs/feathers/commit/17b3dc8)) ### BREAKING CHANGES -* Move database adapter utilities from @feathersjs/commons into its own module - - - - +- Move database adapter utilities from @feathersjs/commons into its own module -## [3.0.1](https://github.com/feathersjs/feathers/compare/@feathersjs/commons@3.0.0...@feathersjs/commons@3.0.1) (2018-09-17) +## [3.0.1](https://github.com/feathersjs/feathers/compare/@feathersjs/commons@3.0.0...@feathersjs/commons@3.0.1) (2018-09-17) ### Bug Fixes -* use minimal RegExp matching for better performance ([#977](https://github.com/feathersjs/feathers/issues/977)) ([3ca7e97](https://github.com/feathersjs/feathers/commit/3ca7e97)) - - - - +- use minimal RegExp matching for better performance ([#977](https://github.com/feathersjs/feathers/issues/977)) ([3ca7e97](https://github.com/feathersjs/feathers/commit/3ca7e97)) # Change Log ## [v3.0.0-pre.1](https://github.com/feathersjs/commons/tree/v3.0.0-pre.1) (2018-08-13) + [Full Changelog](https://github.com/feathersjs/commons/compare/v2.0.0...v3.0.0-pre.1) **Merged pull requests:** @@ -422,6 +298,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Remove argument verification and add further utilities [\#81](https://github.com/feathersjs/commons/pull/81) ([daffl](https://github.com/daffl)) ## [v2.0.0](https://github.com/feathersjs/commons/tree/v2.0.0) (2018-08-03) + [Full Changelog](https://github.com/feathersjs/commons/compare/v1.4.4...v2.0.0) **Merged pull requests:** @@ -430,9 +307,11 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Ability to specify custom filters in filterQuery [\#73](https://github.com/feathersjs/commons/pull/73) ([vonagam](https://github.com/vonagam)) ## [v1.4.4](https://github.com/feathersjs/commons/tree/v1.4.4) (2018-08-01) + [Full Changelog](https://github.com/feathersjs/commons/compare/v1.4.3...v1.4.4) ## [v1.4.3](https://github.com/feathersjs/commons/tree/v1.4.3) (2018-07-25) + [Full Changelog](https://github.com/feathersjs/commons/compare/v1.4.2...v1.4.3) **Merged pull requests:** @@ -440,6 +319,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Revert breaking change from 78d780de91ae8333f3843be153beb5deea55c792 [\#78](https://github.com/feathersjs/commons/pull/78) ([daffl](https://github.com/daffl)) ## [v1.4.2](https://github.com/feathersjs/commons/tree/v1.4.2) (2018-07-25) + [Full Changelog](https://github.com/feathersjs/commons/compare/v1.4.1...v1.4.2) **Closed issues:** @@ -454,6 +334,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Open hook workflow to custom methods [\#72](https://github.com/feathersjs/commons/pull/72) ([bertho-zero](https://github.com/bertho-zero)) ## [v1.4.1](https://github.com/feathersjs/commons/tree/v1.4.1) (2018-04-12) + [Full Changelog](https://github.com/feathersjs/commons/compare/v1.4.0...v1.4.1) **Closed issues:** @@ -467,6 +348,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Update mocha to the latest version 🚀 [\#67](https://github.com/feathersjs/commons/pull/67) ([greenkeeper[bot]](https://github.com/apps/greenkeeper)) ## [v1.4.0](https://github.com/feathersjs/commons/tree/v1.4.0) (2018-01-17) + [Full Changelog](https://github.com/feathersjs/commons/compare/v1.3.1...v1.4.0) **Merged pull requests:** @@ -474,6 +356,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Add ability to skip all following hooks [\#65](https://github.com/feathersjs/commons/pull/65) ([sylvainlap](https://github.com/sylvainlap)) ## [v1.3.1](https://github.com/feathersjs/commons/tree/v1.3.1) (2018-01-12) + [Full Changelog](https://github.com/feathersjs/commons/compare/v1.3.0...v1.3.1) **Merged pull requests:** @@ -482,6 +365,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Update semistandard to the latest version 🚀 [\#64](https://github.com/feathersjs/commons/pull/64) ([greenkeeper[bot]](https://github.com/apps/greenkeeper)) ## [v1.3.0](https://github.com/feathersjs/commons/tree/v1.3.0) (2017-11-20) + [Full Changelog](https://github.com/feathersjs/commons/compare/v1.2.0...v1.3.0) **Merged pull requests:** @@ -490,6 +374,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - updating contributing guide and issue template [\#61](https://github.com/feathersjs/commons/pull/61) ([ekryski](https://github.com/ekryski)) ## [v1.2.0](https://github.com/feathersjs/commons/tree/v1.2.0) (2017-10-25) + [Full Changelog](https://github.com/feathersjs/commons/compare/v1.1.0...v1.2.0) **Merged pull requests:** @@ -498,6 +383,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - adding codeclimate config [\#60](https://github.com/feathersjs/commons/pull/60) ([ekryski](https://github.com/ekryski)) ## [v1.1.0](https://github.com/feathersjs/commons/tree/v1.1.0) (2017-10-23) + [Full Changelog](https://github.com/feathersjs/commons/compare/v1.0.0...v1.1.0) **Merged pull requests:** @@ -506,6 +392,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Add feathers-query-filters [\#58](https://github.com/feathersjs/commons/pull/58) ([daffl](https://github.com/daffl)) ## [v1.0.0](https://github.com/feathersjs/commons/tree/v1.0.0) (2017-10-19) + [Full Changelog](https://github.com/feathersjs/commons/compare/v1.0.0-pre.3...v1.0.0) **Merged pull requests:** @@ -514,6 +401,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Updates for Feathers v3 \(Buzzard\) [\#56](https://github.com/feathersjs/commons/pull/56) ([daffl](https://github.com/daffl)) ## [v1.0.0-pre.3](https://github.com/feathersjs/commons/tree/v1.0.0-pre.3) (2017-10-18) + [Full Changelog](https://github.com/feathersjs/commons/compare/v1.0.0-pre.2...v1.0.0-pre.3) **Merged pull requests:** @@ -522,6 +410,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Update mocha to the latest version 🚀 [\#54](https://github.com/feathersjs/commons/pull/54) ([greenkeeper[bot]](https://github.com/apps/greenkeeper)) ## [v1.0.0-pre.2](https://github.com/feathersjs/commons/tree/v1.0.0-pre.2) (2017-07-11) + [Full Changelog](https://github.com/feathersjs/commons/compare/v1.0.0-pre.1...v1.0.0-pre.2) **Merged pull requests:** @@ -529,6 +418,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Update to new plugin infrastructure [\#53](https://github.com/feathersjs/commons/pull/53) ([daffl](https://github.com/daffl)) ## [v1.0.0-pre.1](https://github.com/feathersjs/commons/tree/v1.0.0-pre.1) (2017-06-28) + [Full Changelog](https://github.com/feathersjs/commons/compare/v0.8.7...v1.0.0-pre.1) **Merged pull requests:** @@ -539,6 +429,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Update dependencies to enable Greenkeeper 🌴 [\#49](https://github.com/feathersjs/commons/pull/49) ([greenkeeper[bot]](https://github.com/apps/greenkeeper)) ## [v0.8.7](https://github.com/feathersjs/commons/tree/v0.8.7) (2016-11-30) + [Full Changelog](https://github.com/feathersjs/commons/compare/v0.8.6...v0.8.7) **Closed issues:** @@ -550,6 +441,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - matcher now doesn't blow up with null values. Closes \#46 [\#47](https://github.com/feathersjs/commons/pull/47) ([ekryski](https://github.com/ekryski)) ## [v0.8.6](https://github.com/feathersjs/commons/tree/v0.8.6) (2016-11-25) + [Full Changelog](https://github.com/feathersjs/commons/compare/v0.8.5...v0.8.6) **Merged pull requests:** @@ -557,6 +449,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Allow to pass an object to hook object [\#45](https://github.com/feathersjs/commons/pull/45) ([daffl](https://github.com/daffl)) ## [v0.8.5](https://github.com/feathersjs/commons/tree/v0.8.5) (2016-11-19) + [Full Changelog](https://github.com/feathersjs/commons/compare/v0.8.4...v0.8.5) **Merged pull requests:** @@ -567,12 +460,15 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Expect syntax [\#41](https://github.com/feathersjs/commons/pull/41) ([ekryski](https://github.com/ekryski)) ## [v0.8.4](https://github.com/feathersjs/commons/tree/v0.8.4) (2016-11-11) + [Full Changelog](https://github.com/feathersjs/commons/compare/v0.8.3...v0.8.4) ## [v0.8.3](https://github.com/feathersjs/commons/tree/v0.8.3) (2016-11-11) + [Full Changelog](https://github.com/feathersjs/commons/compare/v0.8.2...v0.8.3) ## [v0.8.2](https://github.com/feathersjs/commons/tree/v0.8.2) (2016-11-11) + [Full Changelog](https://github.com/feathersjs/commons/compare/v0.8.1...v0.8.2) **Merged pull requests:** @@ -580,6 +476,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - One more fix for select on arrays [\#40](https://github.com/feathersjs/commons/pull/40) ([daffl](https://github.com/daffl)) ## [v0.8.1](https://github.com/feathersjs/commons/tree/v0.8.1) (2016-11-11) + [Full Changelog](https://github.com/feathersjs/commons/compare/v0.8.0...v0.8.1) **Merged pull requests:** @@ -587,6 +484,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Fixing select utility methods to work with query selector [\#39](https://github.com/feathersjs/commons/pull/39) ([daffl](https://github.com/daffl)) ## [v0.8.0](https://github.com/feathersjs/commons/tree/v0.8.0) (2016-11-09) + [Full Changelog](https://github.com/feathersjs/commons/compare/v0.7.8...v0.8.0) **Merged pull requests:** @@ -595,6 +493,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - jshint —\> semistandard [\#37](https://github.com/feathersjs/commons/pull/37) ([corymsmith](https://github.com/corymsmith)) ## [v0.7.8](https://github.com/feathersjs/commons/tree/v0.7.8) (2016-10-21) + [Full Changelog](https://github.com/feathersjs/commons/compare/v0.7.7...v0.7.8) **Merged pull requests:** @@ -602,6 +501,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Make getting the service in base test dynamic [\#36](https://github.com/feathersjs/commons/pull/36) ([daffl](https://github.com/daffl)) ## [v0.7.7](https://github.com/feathersjs/commons/tree/v0.7.7) (2016-10-21) + [Full Changelog](https://github.com/feathersjs/commons/compare/v0.7.6...v0.7.7) **Merged pull requests:** @@ -609,15 +509,17 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Allow app in hookObject [\#35](https://github.com/feathersjs/commons/pull/35) ([daffl](https://github.com/daffl)) ## [v0.7.6](https://github.com/feathersjs/commons/tree/v0.7.6) (2016-10-20) + [Full Changelog](https://github.com/feathersjs/commons/compare/v0.7.5...v0.7.6) **Merged pull requests:** -- Add test for matching and increase code coverage [\#34](https://github.com/feathersjs/commons/pull/34) ([daffl](https://github.com/daffl)) +- Add test for matching and increase code coverage [\#34](https://github.com/feathersjs/commons/pull/34) ([daffl](https://github.com/daffl)) - omit '$select' in matcher [\#33](https://github.com/feathersjs/commons/pull/33) ([beeplin](https://github.com/beeplin)) - adding code coverage [\#32](https://github.com/feathersjs/commons/pull/32) ([ekryski](https://github.com/ekryski)) ## [v0.7.5](https://github.com/feathersjs/commons/tree/v0.7.5) (2016-09-05) + [Full Changelog](https://github.com/feathersjs/commons/compare/v0.7.4...v0.7.5) **Closed issues:** @@ -632,6 +534,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Update mocha to version 3.0.0 🚀 [\#27](https://github.com/feathersjs/commons/pull/27) ([greenkeeperio-bot](https://github.com/greenkeeperio-bot)) ## [v0.7.4](https://github.com/feathersjs/commons/tree/v0.7.4) (2016-05-29) + [Full Changelog](https://github.com/feathersjs/commons/compare/v0.7.3...v0.7.4) **Merged pull requests:** @@ -641,6 +544,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Update babel-plugin-add-module-exports to version 0.2.0 🚀 [\#23](https://github.com/feathersjs/commons/pull/23) ([greenkeeperio-bot](https://github.com/greenkeeperio-bot)) ## [v0.7.3](https://github.com/feathersjs/commons/tree/v0.7.3) (2016-05-05) + [Full Changelog](https://github.com/feathersjs/commons/compare/v0.7.2...v0.7.3) **Merged pull requests:** @@ -648,6 +552,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Make sure arguments from hook objects are created properly for known … [\#22](https://github.com/feathersjs/commons/pull/22) ([daffl](https://github.com/daffl)) ## [v0.7.2](https://github.com/feathersjs/commons/tree/v0.7.2) (2016-04-26) + [Full Changelog](https://github.com/feathersjs/commons/compare/v0.7.1...v0.7.2) **Merged pull requests:** @@ -655,6 +560,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Update test fixture to use promises and add error cases [\#19](https://github.com/feathersjs/commons/pull/19) ([daffl](https://github.com/daffl)) ## [v0.7.1](https://github.com/feathersjs/commons/tree/v0.7.1) (2016-04-04) + [Full Changelog](https://github.com/feathersjs/commons/compare/v0.6.2...v0.7.1) **Merged pull requests:** @@ -662,12 +568,15 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Adding functionality and tests for shared query and list handling [\#17](https://github.com/feathersjs/commons/pull/17) ([daffl](https://github.com/daffl)) ## [v0.6.2](https://github.com/feathersjs/commons/tree/v0.6.2) (2016-02-09) + [Full Changelog](https://github.com/feathersjs/commons/compare/v0.7.0...v0.6.2) ## [v0.7.0](https://github.com/feathersjs/commons/tree/v0.7.0) (2016-02-08) + [Full Changelog](https://github.com/feathersjs/commons/compare/v0.6.1...v0.7.0) ## [v0.6.1](https://github.com/feathersjs/commons/tree/v0.6.1) (2016-02-08) + [Full Changelog](https://github.com/feathersjs/commons/compare/v0.6.0...v0.6.1) **Merged pull requests:** @@ -675,6 +584,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Add NSP check to test script. [\#16](https://github.com/feathersjs/commons/pull/16) ([marshallswain](https://github.com/marshallswain)) ## [v0.6.0](https://github.com/feathersjs/commons/tree/v0.6.0) (2016-01-21) + [Full Changelog](https://github.com/feathersjs/commons/compare/v0.5.0...v0.6.0) **Closed issues:** @@ -687,12 +597,15 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Support socket routes with apps mounted on a path [\#14](https://github.com/feathersjs/commons/pull/14) ([daffl](https://github.com/daffl)) ## [v0.5.0](https://github.com/feathersjs/commons/tree/v0.5.0) (2016-01-10) + [Full Changelog](https://github.com/feathersjs/commons/compare/v0.4.0...v0.5.0) ## [v0.4.0](https://github.com/feathersjs/commons/tree/v0.4.0) (2016-01-10) + [Full Changelog](https://github.com/feathersjs/commons/compare/v0.3.4...v0.4.0) ## [v0.3.4](https://github.com/feathersjs/commons/tree/v0.3.4) (2016-01-06) + [Full Changelog](https://github.com/feathersjs/commons/compare/v0.3.3...v0.3.4) **Merged pull requests:** @@ -700,6 +613,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Fix SocketIO client iteration for all cases [\#11](https://github.com/feathersjs/commons/pull/11) ([daffl](https://github.com/daffl)) ## [v0.3.3](https://github.com/feathersjs/commons/tree/v0.3.3) (2016-01-06) + [Full Changelog](https://github.com/feathersjs/commons/compare/v0.3.2...v0.3.3) **Closed issues:** @@ -707,12 +621,15 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Socket.io 1.4.0 broke feathers [\#10](https://github.com/feathersjs/commons/issues/10) ## [v0.3.2](https://github.com/feathersjs/commons/tree/v0.3.2) (2016-01-06) + [Full Changelog](https://github.com/feathersjs/commons/compare/v0.3.1...v0.3.2) ## [v0.3.1](https://github.com/feathersjs/commons/tree/v0.3.1) (2016-01-06) + [Full Changelog](https://github.com/feathersjs/commons/compare/v0.3.0...v0.3.1) ## [v0.3.0](https://github.com/feathersjs/commons/tree/v0.3.0) (2015-12-11) + [Full Changelog](https://github.com/feathersjs/commons/compare/v0.2.11...v0.3.0) **Closed issues:** @@ -720,6 +637,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - babel inside package.json breaks react-native [\#9](https://github.com/feathersjs/commons/issues/9) ## [v0.2.11](https://github.com/feathersjs/commons/tree/v0.2.11) (2015-11-30) + [Full Changelog](https://github.com/feathersjs/commons/compare/v0.2.10...v0.2.11) **Merged pull requests:** @@ -727,6 +645,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - getOrRemove did not check id property type [\#8](https://github.com/feathersjs/commons/pull/8) ([daffl](https://github.com/daffl)) ## [v0.2.10](https://github.com/feathersjs/commons/tree/v0.2.10) (2015-11-28) + [Full Changelog](https://github.com/feathersjs/commons/compare/v0.2.9...v0.2.10) **Closed issues:** @@ -738,6 +657,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Migrate to Babel 6 and remove Lodash dependency [\#7](https://github.com/feathersjs/commons/pull/7) ([daffl](https://github.com/daffl)) ## [v0.2.9](https://github.com/feathersjs/commons/tree/v0.2.9) (2015-11-17) + [Full Changelog](https://github.com/feathersjs/commons/compare/v0.2.8...v0.2.9) **Closed issues:** @@ -746,6 +666,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - .create with no callback throws error [\#4](https://github.com/feathersjs/commons/issues/4) ## [v0.2.8](https://github.com/feathersjs/commons/tree/v0.2.8) (2015-10-06) + [Full Changelog](https://github.com/feathersjs/commons/compare/v0.2.7...v0.2.8) **Closed issues:** @@ -757,27 +678,33 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Add hookObject utilities and remove Lodash dependency from arguments.js [\#3](https://github.com/feathersjs/commons/pull/3) ([daffl](https://github.com/daffl)) ## [v0.2.7](https://github.com/feathersjs/commons/tree/v0.2.7) (2015-03-07) + [Full Changelog](https://github.com/feathersjs/commons/compare/v0.2.6...v0.2.7) ## [v0.2.6](https://github.com/feathersjs/commons/tree/v0.2.6) (2015-03-06) + [Full Changelog](https://github.com/feathersjs/commons/compare/v0.2.5...v0.2.6) ## [v0.2.5](https://github.com/feathersjs/commons/tree/v0.2.5) (2015-03-06) + [Full Changelog](https://github.com/feathersjs/commons/compare/0.2.3...v0.2.5) ## [0.2.3](https://github.com/feathersjs/commons/tree/0.2.3) (2015-03-06) + [Full Changelog](https://github.com/feathersjs/commons/compare/0.2.2...0.2.3) ## [0.2.2](https://github.com/feathersjs/commons/tree/0.2.2) (2015-03-06) + [Full Changelog](https://github.com/feathersjs/commons/compare/0.2.1...0.2.2) ## [0.2.1](https://github.com/feathersjs/commons/tree/0.2.1) (2015-03-06) + [Full Changelog](https://github.com/feathersjs/commons/compare/0.2.0...0.2.1) ## [0.2.0](https://github.com/feathersjs/commons/tree/0.2.0) (2015-03-06) + [Full Changelog](https://github.com/feathersjs/commons/compare/0.1.0...0.2.0) ## [0.1.0](https://github.com/feathersjs/commons/tree/0.1.0) (2015-03-06) - -\* *This Change Log was automatically generated by [github_changelog_generator](https://github.com/skywinder/Github-Changelog-Generator)* +\* _This Change Log was automatically generated by [github_changelog_generator](https://github.com/skywinder/Github-Changelog-Generator)_ diff --git a/packages/commons/LICENSE b/packages/commons/LICENSE index 3f395cc665..59604f46f3 100644 --- a/packages/commons/LICENSE +++ b/packages/commons/LICENSE @@ -1,6 +1,6 @@ The MIT License (MIT) -Copyright (c) 2021 Feathers +Copyright (c) 2022 Feathers Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated documentation files (the "Software"), to deal diff --git a/packages/commons/README.md b/packages/commons/README.md index f5e068413d..1ce2fa97d7 100644 --- a/packages/commons/README.md +++ b/packages/commons/README.md @@ -1,8 +1,8 @@ # Feathers Commons [![CI](https://github.com/feathersjs/feathers/workflows/CI/badge.svg)](https://github.com/feathersjs/feathers/actions?query=workflow%3ACI) -[![Dependency Status](https://img.shields.io/david/feathersjs/feathers.svg?style=flat-square&path=packages/commons)](https://david-dm.org/feathersjs/feathers?path=packages/commons) [![Download Status](https://img.shields.io/npm/dm/@feathersjs/commons.svg?style=flat-square)](https://www.npmjs.com/package/@feathersjs/commons) +[![Discord](https://badgen.net/badge/icon/discord?icon=discord&label)](https://discord.gg/qa8kez8QBx) > Shared Feathers utility functions @@ -12,6 +12,6 @@ This is a repository for utility functionality that is shared between different ## License -Copyright (c) 2021 [Feathers contributors](https://github.com/feathersjs/feathers/graphs/contributors) +Copyright (c) 2022 [Feathers contributors](https://github.com/feathersjs/feathers/graphs/contributors) Licensed under the [MIT license](LICENSE). diff --git a/packages/commons/package.json b/packages/commons/package.json index 2543fb7b64..0c8fc2392a 100644 --- a/packages/commons/package.json +++ b/packages/commons/package.json @@ -1,6 +1,6 @@ { "name": "@feathersjs/commons", - "version": "5.0.0-pre.16", + "version": "5.0.0-pre.31", "description": "Shared Feathers utility functions", "homepage": "https://feathersjs.com", "keywords": [ @@ -13,7 +13,8 @@ }, "repository": { "type": "git", - "url": "git://github.com/feathersjs/feathers.git" + "url": "git://github.com/feathersjs/feathers.git", + "directory": "packages/commons" }, "author": { "name": "Feathers contributor", @@ -40,7 +41,8 @@ ], "scripts": { "prepublish": "npm run compile", - "compile": "shx rm -rf lib/ && tsc", + "pack": "npm pack --pack-destination ../cli/test/build", + "compile": "shx rm -rf lib/ && tsc && npm run pack", "test": "mocha --config ../../.mocharc.json --recursive test/**.test.ts test/**/*.test.ts" }, "directories": { @@ -50,12 +52,12 @@ "access": "public" }, "devDependencies": { - "@types/mocha": "^9.0.0", - "@types/node": "^17.0.5", - "mocha": "^9.1.3", - "shx": "^0.3.3", - "ts-node": "^10.4.0", - "typescript": "^4.5.4" - }, - "gitHead": "f0cd227a82d159b528193bd33747c97684a48773" + "@types/mocha": "^10.0.0", + "@types/node": "^18.8.2", + "mocha": "^10.0.0", + "shx": "^0.3.4", + "ts-node": "^10.9.1", + "typescript": "^4.8.4" + }, + "gitHead": "4500dbeb8cea566678cf88b3313a88efd93a2ed9" } diff --git a/packages/commons/src/debug.ts b/packages/commons/src/debug.ts index 48f5d23298..5c15e62cf7 100644 --- a/packages/commons/src/debug.ts +++ b/packages/commons/src/debug.ts @@ -1,26 +1,27 @@ -export type DebugFunction = (...args: any[]) => void; -export type DebugInitializer = (name: string) => DebugFunction; +/* eslint-disable @typescript-eslint/no-empty-function */ +export type DebugFunction = (...args: any[]) => void +export type DebugInitializer = (name: string) => DebugFunction -const debuggers: { [key: string]: DebugFunction } = {}; +const debuggers: { [key: string]: DebugFunction } = {} -export function noopDebug (): DebugFunction { - return () => {} +export function noopDebug(): DebugFunction { + return function () {} } -let defaultInitializer: DebugInitializer = noopDebug; +let defaultInitializer: DebugInitializer = noopDebug -export function setDebug (debug: DebugInitializer) { - defaultInitializer = debug; +export function setDebug(debug: DebugInitializer) { + defaultInitializer = debug - Object.keys(debuggers).forEach(name => { - debuggers[name] = debug(name); - }); + Object.keys(debuggers).forEach((name) => { + debuggers[name] = debug(name) + }) } -export function createDebug (name: string) { +export function createDebug(name: string) { if (!debuggers[name]) { - debuggers[name] = defaultInitializer(name); + debuggers[name] = defaultInitializer(name) } - return (...args: any[]) => debuggers[name](...args); + return (...args: any[]) => debuggers[name](...args) } diff --git a/packages/commons/src/index.ts b/packages/commons/src/index.ts index ba30dafaeb..c13b82adac 100644 --- a/packages/commons/src/index.ts +++ b/packages/commons/src/index.ts @@ -1,103 +1,102 @@ // Removes all leading and trailing slashes from a path -export function stripSlashes (name: string) { - return name.replace(/^(\/+)|(\/+)$/g, ''); +export function stripSlashes(name: string) { + return name.replace(/^(\/+)|(\/+)$/g, '') } -export type KeyValueCallback = (value: any, key: string) => T; +export type KeyValueCallback = (value: any, key: string) => T // A set of lodash-y utility functions that use ES6 export const _ = { - each (obj: any, callback: KeyValueCallback) { + each(obj: any, callback: KeyValueCallback) { if (obj && typeof obj.forEach === 'function') { - obj.forEach(callback); + obj.forEach(callback) } else if (_.isObject(obj)) { - Object.keys(obj).forEach(key => callback(obj[key], key)); + Object.keys(obj).forEach((key) => callback(obj[key], key)) } }, - some (value: any, callback: KeyValueCallback) { + some(value: any, callback: KeyValueCallback) { return Object.keys(value) - .map(key => [ value[key], key ]) - .some(([val, key]) => callback(val, key)); + .map((key) => [value[key], key]) + .some(([val, key]) => callback(val, key)) }, - every (value: any, callback: KeyValueCallback) { + every(value: any, callback: KeyValueCallback) { return Object.keys(value) - .map(key => [ value[key], key ]) - .every(([val, key]) => callback(val, key)); + .map((key) => [value[key], key]) + .every(([val, key]) => callback(val, key)) }, - keys (obj: any) { - return Object.keys(obj); + keys(obj: any) { + return Object.keys(obj) }, - values (obj: any) { - return _.keys(obj).map(key => obj[key]); + values(obj: any) { + return _.keys(obj).map((key) => obj[key]) }, - isMatch (obj: any, item: any) { - return _.keys(item).every(key => obj[key] === item[key]); + isMatch(obj: any, item: any) { + return _.keys(item).every((key) => obj[key] === item[key]) }, - isEmpty (obj: any) { - return _.keys(obj).length === 0; + isEmpty(obj: any) { + return _.keys(obj).length === 0 }, - isObject (item: any) { - return (typeof item === 'object' && !Array.isArray(item) && item !== null); + isObject(item: any) { + return typeof item === 'object' && !Array.isArray(item) && item !== null }, - isObjectOrArray (value: any) { - return typeof value === 'object' && value !== null; + isObjectOrArray(value: any) { + return typeof value === 'object' && value !== null }, - extend (first: any, ...rest: any[]) { - return Object.assign(first, ...rest); + extend(first: any, ...rest: any[]) { + return Object.assign(first, ...rest) }, - omit (obj: any, ...keys: string[]) { - const result = _.extend({}, obj); - keys.forEach(key => delete result[key]); - return result; + omit(obj: any, ...keys: string[]) { + const result = _.extend({}, obj) + keys.forEach((key) => delete result[key]) + return result }, - pick (source: any, ...keys: string[]) { + pick(source: any, ...keys: string[]) { return keys.reduce((result: { [key: string]: any }, key) => { if (source[key] !== undefined) { - result[key] = source[key]; + result[key] = source[key] } - return result; - }, {}); + return result + }, {}) }, // Recursively merge the source object into the target object - merge (target: any, source: any) { + merge(target: any, source: any) { if (_.isObject(target) && _.isObject(source)) { - Object.keys(source).forEach(key => { + Object.keys(source).forEach((key) => { if (_.isObject(source[key])) { if (!target[key]) { - Object.assign(target, { [key]: {} }); + Object.assign(target, { [key]: {} }) } - _.merge(target[key], source[key]); + _.merge(target[key], source[key]) } else { - Object.assign(target, { [key]: source[key] }); + Object.assign(target, { [key]: source[key] }) } - }); + }) } - return target; + return target } -}; +} // Duck-checks if an object looks like a promise -export function isPromise (result: any) { - return _.isObject(result) && - typeof result.then === 'function'; +export function isPromise(result: any) { + return _.isObject(result) && typeof result.then === 'function' } -export function createSymbol (name: string) { - return typeof Symbol !== 'undefined' ? Symbol(name) : name; +export function createSymbol(name: string) { + return typeof Symbol !== 'undefined' ? Symbol(name) : name } -export * from './debug'; +export * from './debug' diff --git a/packages/commons/test/debug.test.ts b/packages/commons/test/debug.test.ts index f299521349..2089af9b0c 100644 --- a/packages/commons/test/debug.test.ts +++ b/packages/commons/test/debug.test.ts @@ -1,30 +1,32 @@ -import { strict as assert } from 'assert'; -import { createDebug, setDebug, noopDebug } from '../src'; +import { strict as assert } from 'assert' +import { createDebug, setDebug, noopDebug } from '../src' -const myDebug = createDebug('hello test'); +const myDebug = createDebug('hello test') describe('debug', () => { it('default debug does nothing', () => { - assert.equal(myDebug('hi', 'there'), undefined); - }); + assert.equal(myDebug('hi', 'there'), undefined) + }) it('can set custom debug later', () => { - let call; + let call - const customDebug = (name: string) => (...args: any[]) => { - call = [ name ].concat(args); - } + const customDebug = + (name: string) => + (...args: any[]) => { + call = [name].concat(args) + } - setDebug(customDebug); + setDebug(customDebug) - assert.equal(myDebug('hi', 'there'), undefined); - assert.deepEqual(call, [ 'hello test', 'hi', 'there' ]); + assert.equal(myDebug('hi', 'there'), undefined) + assert.deepEqual(call, ['hello test', 'hi', 'there']) - const newDebug = createDebug('other test'); + const newDebug = createDebug('other test') - assert.equal(newDebug('other', 'there'), undefined); - assert.deepEqual(call, [ 'other test', 'other', 'there' ]); + assert.equal(newDebug('other', 'there'), undefined) + assert.deepEqual(call, ['other test', 'other', 'there']) - setDebug(noopDebug); - }); -}); + setDebug(noopDebug) + }) +}) diff --git a/packages/commons/test/module.test.ts b/packages/commons/test/module.test.ts index 7ab2acebbd..06198d039e 100644 --- a/packages/commons/test/module.test.ts +++ b/packages/commons/test/module.test.ts @@ -1,28 +1,28 @@ -import { strict as assert } from 'assert'; -import { _ } from '../src'; +import { strict as assert } from 'assert' +import { _ } from '../src' describe('module', () => { it('is commonjs compatible', () => { // eslint-disable-next-line - const commons = require('../lib'); + const commons = require('../lib') - assert.equal(typeof commons, 'object'); - assert.equal(typeof commons.stripSlashes, 'function'); - assert.equal(typeof commons._, 'object'); - }); + assert.equal(typeof commons, 'object') + assert.equal(typeof commons.stripSlashes, 'function') + assert.equal(typeof commons._, 'object') + }) it('exposes lodash methods under _', () => { - assert.equal(typeof _.each, 'function'); - assert.equal(typeof _.some, 'function'); - assert.equal(typeof _.every, 'function'); - assert.equal(typeof _.keys, 'function'); - assert.equal(typeof _.values, 'function'); - assert.equal(typeof _.isMatch, 'function'); - assert.equal(typeof _.isEmpty, 'function'); - assert.equal(typeof _.isObject, 'function'); - assert.equal(typeof _.extend, 'function'); - assert.equal(typeof _.omit, 'function'); - assert.equal(typeof _.pick, 'function'); - assert.equal(typeof _.merge, 'function'); - }); -}); + assert.equal(typeof _.each, 'function') + assert.equal(typeof _.some, 'function') + assert.equal(typeof _.every, 'function') + assert.equal(typeof _.keys, 'function') + assert.equal(typeof _.values, 'function') + assert.equal(typeof _.isMatch, 'function') + assert.equal(typeof _.isEmpty, 'function') + assert.equal(typeof _.isObject, 'function') + assert.equal(typeof _.extend, 'function') + assert.equal(typeof _.omit, 'function') + assert.equal(typeof _.pick, 'function') + assert.equal(typeof _.merge, 'function') + }) +}) diff --git a/packages/commons/test/utils.test.ts b/packages/commons/test/utils.test.ts index fb7eafc9c5..53d51978ab 100644 --- a/packages/commons/test/utils.test.ts +++ b/packages/commons/test/utils.test.ts @@ -1,163 +1,216 @@ /* tslint:disable:no-unused-expression */ -import { strict as assert } from 'assert'; -import { _, stripSlashes, isPromise, createSymbol } from '../src'; +import { strict as assert } from 'assert' +import { _, stripSlashes, isPromise, createSymbol } from '../src' describe('@feathersjs/commons utils', () => { it('stripSlashes', () => { - assert.equal(stripSlashes('some/thing'), 'some/thing'); - assert.equal(stripSlashes('/some/thing'), 'some/thing'); - assert.equal(stripSlashes('some/thing/'), 'some/thing'); - assert.equal(stripSlashes('/some/thing/'), 'some/thing'); - assert.equal(stripSlashes('//some/thing/'), 'some/thing'); - assert.equal(stripSlashes('//some//thing////'), 'some//thing'); - }); + assert.equal(stripSlashes('some/thing'), 'some/thing') + assert.equal(stripSlashes('/some/thing'), 'some/thing') + assert.equal(stripSlashes('some/thing/'), 'some/thing') + assert.equal(stripSlashes('/some/thing/'), 'some/thing') + assert.equal(stripSlashes('//some/thing/'), 'some/thing') + assert.equal(stripSlashes('//some//thing////'), 'some//thing') + }) it('isPromise', () => { - assert.equal(isPromise(Promise.resolve()), true); - assert.ok(isPromise({ - then () {} - })); - assert.equal(isPromise(null), false); - }); + assert.equal(isPromise(Promise.resolve()), true) + assert.ok( + isPromise({ + then() { + return true + } + }) + ) + assert.equal(isPromise(null), false) + }) it('createSymbol', () => { - assert.equal(typeof createSymbol('a test'), 'symbol'); - }); + assert.equal(typeof createSymbol('a test'), 'symbol') + }) describe('_', () => { it('isObject', () => { - assert.equal(_.isObject({}), true); - assert.equal(_.isObject([]), false); - assert.equal(_.isObject(null), false); - }); + assert.equal(_.isObject({}), true) + assert.equal(_.isObject([]), false) + assert.equal(_.isObject(null), false) + }) it('isObjectOrArray', () => { - assert.equal(_.isObjectOrArray({}), true); - assert.equal(_.isObjectOrArray([]), true); - assert.equal(_.isObjectOrArray(null), false); - }); + assert.equal(_.isObjectOrArray({}), true) + assert.equal(_.isObjectOrArray([]), true) + assert.equal(_.isObjectOrArray(null), false) + }) it('each', () => { _.each({ hi: 'there' }, (value, key) => { - assert.equal(key, 'hi'); - assert.equal(value, 'there'); - }); + assert.equal(key, 'hi') + assert.equal(value, 'there') + }) - _.each([ 'hi' ], (value, key) => { - assert.equal(key, 0); - assert.equal(value, 'hi'); - }); + _.each(['hi'], (value, key) => { + assert.equal(key, 0) + assert.equal(value, 'hi') + }) - _.each('moo', () => assert.fail('Should never get here')); - }); + _.each('moo', () => assert.fail('Should never get here')) + }) it('some', () => { - assert.ok(_.some([ 'a', 'b' ], current => current === 'a')); - assert.ok(!_.some([ 'a', 'b' ], current => current === 'c')); - }); + assert.ok(_.some(['a', 'b'], (current) => current === 'a')) + assert.ok(!_.some(['a', 'b'], (current) => current === 'c')) + }) it('every', () => { - assert.ok(_.every([ 'a', 'a' ], current => current === 'a')); - assert.ok(!_.every([ 'a', 'b' ], current => current === 'a')); - }); + assert.ok(_.every(['a', 'a'], (current) => current === 'a')) + assert.ok(!_.every(['a', 'b'], (current) => current === 'a')) + }) it('keys', () => { - const data = { hi: 'there', name: 'David' }; - assert.deepEqual(_.keys(data), [ 'hi', 'name' ]); - }); + const data = { hi: 'there', name: 'David' } + assert.deepEqual(_.keys(data), ['hi', 'name']) + }) it('values', () => { - const data = { hi: 'there', name: 'David' }; - assert.deepEqual(_.values(data), [ 'there', 'David' ]); - }); + const data = { hi: 'there', name: 'David' } + assert.deepEqual(_.values(data), ['there', 'David']) + }) it('isMatch', () => { - assert.ok(_.isMatch({ - test: 'me', hi: 'you', more: true - }, { - test: 'me', hi: 'you' - })); - - assert.ok(!_.isMatch({ - test: 'me', hi: 'you', more: true - }, { - test: 'me', hi: 'there' - })); - }); + assert.ok( + _.isMatch( + { + test: 'me', + hi: 'you', + more: true + }, + { + test: 'me', + hi: 'you' + } + ) + ) + + assert.ok( + !_.isMatch( + { + test: 'me', + hi: 'you', + more: true + }, + { + test: 'me', + hi: 'there' + } + ) + ) + }) it('isEmpty', () => { - assert.ok(_.isEmpty({})); - assert.ok(!_.isEmpty({ name: 'David' })); - }); + assert.ok(_.isEmpty({})) + assert.ok(!_.isEmpty({ name: 'David' })) + }) it('extend', () => { assert.deepEqual(_.extend({ hi: 'there' }, { name: 'david' }), { hi: 'there', name: 'david' - }); - }); + }) + }) it('omit', () => { - assert.deepEqual(_.omit({ - name: 'David', - first: 1, - second: 2 - }, 'first', 'second'), { - name: 'David' - }); - }); + assert.deepEqual( + _.omit( + { + name: 'David', + first: 1, + second: 2 + }, + 'first', + 'second' + ), + { + name: 'David' + } + ) + }) it('pick', () => { - assert.deepEqual(_.pick({ - name: 'David', - first: 1, - second: 2 - }, 'first', 'second'), { - first: 1, - second: 2 - }); - - assert.deepEqual(_.pick({ - name: 'David', - first: 1 - }, 'first', 'second'), { - first: 1 - }); - }); + assert.deepEqual( + _.pick( + { + name: 'David', + first: 1, + second: 2 + }, + 'first', + 'second' + ), + { + first: 1, + second: 2 + } + ) + + assert.deepEqual( + _.pick( + { + name: 'David', + first: 1 + }, + 'first', + 'second' + ), + { + first: 1 + } + ) + }) it('merge', () => { assert.deepEqual(_.merge({ hi: 'there' }, { name: 'david' }), { hi: 'there', name: 'david' - }); - - assert.deepEqual(_.merge({}, { - name: 'david', - nested: { obj: true } - }), { - name: 'david', - nested: { obj: true } - }); + }) + + assert.deepEqual( + _.merge( + {}, + { + name: 'david', + nested: { obj: true } + } + ), + { + name: 'david', + nested: { obj: true } + } + ) assert.deepEqual(_.merge({ name: 'david' }, {}), { name: 'david' - }); - - assert.deepEqual(_.merge({ - hi: 'there', - my: { - name: { is: 'david' }, - number: { is: 1 } - } - }, { my: { name: { is: 'eric' } } }), { - hi: 'there', - my: { - number: { is: 1 }, - name: { is: 'eric' } + }) + + assert.deepEqual( + _.merge( + { + hi: 'there', + my: { + name: { is: 'david' }, + number: { is: 1 } + } + }, + { my: { name: { is: 'eric' } } } + ), + { + hi: 'there', + my: { + number: { is: 1 }, + name: { is: 'eric' } + } } - }); + ) - assert.equal(_.merge('hello', {}), 'hello'); - }); - }); -}); + assert.equal(_.merge('hello', {}), 'hello') + }) + }) +}) diff --git a/packages/configuration/CHANGELOG.md b/packages/configuration/CHANGELOG.md index 6de7d1a09b..075ea929be 100644 --- a/packages/configuration/CHANGELOG.md +++ b/packages/configuration/CHANGELOG.md @@ -3,512 +3,359 @@ All notable changes to this project will be documented in this file. See [Conventional Commits](https://conventionalcommits.org) for commit guidelines. -# [5.0.0-pre.16](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.15...v5.0.0-pre.16) (2022-01-12) +# [5.0.0-pre.31](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.30...v5.0.0-pre.31) (2022-10-12) **Note:** Version bump only for package @feathersjs/configuration +# [5.0.0-pre.30](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.29...v5.0.0-pre.30) (2022-10-07) +### Features +- **core:** Allow to unregister services at runtime ([#2756](https://github.com/feathersjs/feathers/issues/2756)) ([d16601f](https://github.com/feathersjs/feathers/commit/d16601f2277dca5357866ffdefba2a611f6dc7fa)) +- **schema:** Make schemas validation library independent and add TypeBox support ([#2772](https://github.com/feathersjs/feathers/issues/2772)) ([44172d9](https://github.com/feathersjs/feathers/commit/44172d99b566d11d9ceda04f1d0bf72b6d05ce76)) - -# [5.0.0-pre.15](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.14...v5.0.0-pre.15) (2021-11-27) +# [5.0.0-pre.29](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.28...v5.0.0-pre.29) (2022-09-16) **Note:** Version bump only for package @feathersjs/configuration +# [5.0.0-pre.28](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.27...v5.0.0-pre.28) (2022-08-03) +### Bug Fixes +- **cli:** Improve generated application and client ([#2701](https://github.com/feathersjs/feathers/issues/2701)) ([bd55ffb](https://github.com/feathersjs/feathers/commit/bd55ffb812e89bf215f4515e7f137656ea888c3f)) - -# [5.0.0-pre.14](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.13...v5.0.0-pre.14) (2021-10-13) +# [5.0.0-pre.27](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.26...v5.0.0-pre.27) (2022-07-13) **Note:** Version bump only for package @feathersjs/configuration +# [5.0.0-pre.26](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.25...v5.0.0-pre.26) (2022-06-22) +**Note:** Version bump only for package @feathersjs/configuration +# [5.0.0-pre.25](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.24...v5.0.0-pre.25) (2022-06-22) +**Note:** Version bump only for package @feathersjs/configuration -# [5.0.0-pre.13](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.12...v5.0.0-pre.13) (2021-10-13) +# [5.0.0-pre.24](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.23...v5.0.0-pre.24) (2022-06-21) **Note:** Version bump only for package @feathersjs/configuration +# [5.0.0-pre.23](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.22...v5.0.0-pre.23) (2022-06-06) +**Note:** Version bump only for package @feathersjs/configuration +# [5.0.0-pre.22](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.21...v5.0.0-pre.22) (2022-05-24) +**Note:** Version bump only for package @feathersjs/configuration -# [5.0.0-pre.12](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.11...v5.0.0-pre.12) (2021-10-12) +# [5.0.0-pre.21](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.20...v5.0.0-pre.21) (2022-05-23) **Note:** Version bump only for package @feathersjs/configuration +# [5.0.0-pre.20](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.19...v5.0.0-pre.20) (2022-05-04) +### Bug Fixes +- **configuration:** Only validate the initial configuration against the schema ([#2622](https://github.com/feathersjs/feathers/issues/2622)) ([386c5e2](https://github.com/feathersjs/feathers/commit/386c5e2e67bfad4fb4333f2e3e17f7d7e09ac27e)) +- **dependencies:** Lock monorepo package version numbers ([#2623](https://github.com/feathersjs/feathers/issues/2623)) ([5640c10](https://github.com/feathersjs/feathers/commit/5640c1020cc139994e695d658c08bad3494db507)) - -# [5.0.0-pre.11](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.10...v5.0.0-pre.11) (2021-10-06) +# [5.0.0-pre.19](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.18...v5.0.0-pre.19) (2022-05-01) **Note:** Version bump only for package @feathersjs/configuration +# [5.0.0-pre.18](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.17...v5.0.0-pre.18) (2022-04-11) +### Features +- **configuration:** Allow app configuration to be validated against a schema ([#2590](https://github.com/feathersjs/feathers/issues/2590)) ([a268f86](https://github.com/feathersjs/feathers/commit/a268f86da92a8ada14ed11ab456aac0a4bba5bb0)) - -# [5.0.0-pre.10](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.9...v5.0.0-pre.10) (2021-09-19) +# [5.0.0-pre.17](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.16...v5.0.0-pre.17) (2022-02-15) **Note:** Version bump only for package @feathersjs/configuration +# [5.0.0-pre.16](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.15...v5.0.0-pre.16) (2022-01-12) +**Note:** Version bump only for package @feathersjs/configuration - - -# [5.0.0-pre.9](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.8...v5.0.0-pre.9) (2021-08-09) +# [5.0.0-pre.15](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.14...v5.0.0-pre.15) (2021-11-27) **Note:** Version bump only for package @feathersjs/configuration +# [5.0.0-pre.14](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.13...v5.0.0-pre.14) (2021-10-13) +**Note:** Version bump only for package @feathersjs/configuration +# [5.0.0-pre.13](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.12...v5.0.0-pre.13) (2021-10-13) +**Note:** Version bump only for package @feathersjs/configuration -# [5.0.0-pre.8](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.7...v5.0.0-pre.8) (2021-08-09) +# [5.0.0-pre.12](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.11...v5.0.0-pre.12) (2021-10-12) **Note:** Version bump only for package @feathersjs/configuration +# [5.0.0-pre.11](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.10...v5.0.0-pre.11) (2021-10-06) +**Note:** Version bump only for package @feathersjs/configuration +# [5.0.0-pre.10](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.9...v5.0.0-pre.10) (2021-09-19) +**Note:** Version bump only for package @feathersjs/configuration -# [5.0.0-pre.7](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.6...v5.0.0-pre.7) (2021-08-09) +# [5.0.0-pre.9](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.8...v5.0.0-pre.9) (2021-08-09) **Note:** Version bump only for package @feathersjs/configuration +# [5.0.0-pre.8](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.7...v5.0.0-pre.8) (2021-08-09) +**Note:** Version bump only for package @feathersjs/configuration +# [5.0.0-pre.7](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.6...v5.0.0-pre.7) (2021-08-09) +**Note:** Version bump only for package @feathersjs/configuration # [5.0.0-pre.6](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.5...v5.0.0-pre.6) (2021-08-08) **Note:** Version bump only for package @feathersjs/configuration - - - - # [5.0.0-pre.5](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.4...v5.0.0-pre.5) (2021-06-23) - ### Bug Fixes -* **koa:** Use extended query parser for compatibility ([#2397](https://github.com/feathersjs/feathers/issues/2397)) ([b2944ba](https://github.com/feathersjs/feathers/commit/b2944bac3ec6d5ecc80dc518cd4e58093692db74)) - - - - +- **koa:** Use extended query parser for compatibility ([#2397](https://github.com/feathersjs/feathers/issues/2397)) ([b2944ba](https://github.com/feathersjs/feathers/commit/b2944bac3ec6d5ecc80dc518cd4e58093692db74)) # [5.0.0-pre.4](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.3...v5.0.0-pre.4) (2021-05-13) **Note:** Version bump only for package @feathersjs/configuration - - - - # [5.0.0-pre.3](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.2...v5.0.0-pre.3) (2021-04-21) - ### Bug Fixes -* **typescript:** Improve TypeScript backwards compatibility ([#2310](https://github.com/feathersjs/feathers/issues/2310)) ([f33be73](https://github.com/feathersjs/feathers/commit/f33be73fc46a533efb15df9aab0658e3240d3897)) - +- **typescript:** Improve TypeScript backwards compatibility ([#2310](https://github.com/feathersjs/feathers/issues/2310)) ([f33be73](https://github.com/feathersjs/feathers/commit/f33be73fc46a533efb15df9aab0658e3240d3897)) ### Features -* **dependencies:** Remove direct debug dependency ([#2296](https://github.com/feathersjs/feathers/issues/2296)) ([501d416](https://github.com/feathersjs/feathers/commit/501d4164d30c6a126906dc640cdfdc82207ba34a)) - - - - +- **dependencies:** Remove direct debug dependency ([#2296](https://github.com/feathersjs/feathers/issues/2296)) ([501d416](https://github.com/feathersjs/feathers/commit/501d4164d30c6a126906dc640cdfdc82207ba34a)) # [5.0.0-pre.2](https://github.com/feathersjs/feathers/compare/v5.0.0-beta.1...v5.0.0-pre.2) (2021-04-06) **Note:** Version bump only for package @feathersjs/configuration - - - - # [5.0.0-beta.1](https://github.com/feathersjs/feathers/compare/v5.0.0-beta.0...v5.0.0-beta.1) (2021-04-03) **Note:** Version bump only for package @feathersjs/configuration - - - - # [5.0.0-beta.0](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.1...v5.0.0-beta.0) (2021-03-28) - ### Bug Fixes -* Update Grant usage and other dependencies ([#2264](https://github.com/feathersjs/feathers/issues/2264)) ([7b0f8fa](https://github.com/feathersjs/feathers/commit/7b0f8fad252419ed0ad0bf259cdf3104d322ab60)) - +- Update Grant usage and other dependencies ([#2264](https://github.com/feathersjs/feathers/issues/2264)) ([7b0f8fa](https://github.com/feathersjs/feathers/commit/7b0f8fad252419ed0ad0bf259cdf3104d322ab60)) ### Features -* Feathers v5 core refactoring and features ([#2255](https://github.com/feathersjs/feathers/issues/2255)) ([2dafb7c](https://github.com/feathersjs/feathers/commit/2dafb7ce14ba57406aeec13d10ca45b1e709bee9)) - - - - +- Feathers v5 core refactoring and features ([#2255](https://github.com/feathersjs/feathers/issues/2255)) ([2dafb7c](https://github.com/feathersjs/feathers/commit/2dafb7ce14ba57406aeec13d10ca45b1e709bee9)) # [5.0.0-pre.1](https://github.com/feathersjs/feathers/compare/v4.5.11...v5.0.0-pre.1) (2020-12-17) - - # [5.0.0-pre.0](https://github.com/feathersjs/feathers/compare/v4.5.4...v5.0.0-pre.0) (2020-05-19) - ### chore -* **configuration:** Remove environment variable substitution ([#1942](https://github.com/feathersjs/feathers/issues/1942)) ([caaa21f](https://github.com/feathersjs/feathers/commit/caaa21ffdc6a8dcac82fb403c91d9d4b781a6c0a)) - +- **configuration:** Remove environment variable substitution ([#1942](https://github.com/feathersjs/feathers/issues/1942)) ([caaa21f](https://github.com/feathersjs/feathers/commit/caaa21ffdc6a8dcac82fb403c91d9d4b781a6c0a)) ### BREAKING CHANGES -* **configuration:** Falls back to node-config instead of adding additional -functionality like path replacements and automatic environment variable insertion. - - - - +- **configuration:** Falls back to node-config instead of adding additional + functionality like path replacements and automatic environment variable insertion. # [5.0.0-pre.0](https://github.com/feathersjs/feathers/compare/v4.5.4...v5.0.0-pre.0) (2020-05-19) - ### chore -* **configuration:** Remove environment variable substitution ([#1942](https://github.com/feathersjs/feathers/issues/1942)) ([caaa21f](https://github.com/feathersjs/feathers/commit/caaa21ffdc6a8dcac82fb403c91d9d4b781a6c0a)) - +- **configuration:** Remove environment variable substitution ([#1942](https://github.com/feathersjs/feathers/issues/1942)) ([caaa21f](https://github.com/feathersjs/feathers/commit/caaa21ffdc6a8dcac82fb403c91d9d4b781a6c0a)) ### BREAKING CHANGES -* **configuration:** Falls back to node-config instead of adding additional -functionality like path replacements and automatic environment variable insertion. - - - +- **configuration:** Falls back to node-config instead of adding additional + functionality like path replacements and automatic environment variable insertion. ## [4.5.9](https://github.com/feathersjs/feathers/compare/v4.5.8...v4.5.9) (2020-10-09) - ### Bug Fixes -* **configuration:** Fix handling of config values that start with . or .. but are not actually relative paths; e.g. ".foo" or "..bar" ([#2065](https://github.com/feathersjs/feathers/issues/2065)) ([d07bf59](https://github.com/feathersjs/feathers/commit/d07bf5902e9c8c606f16b9523472972d3d2e9b49)) - - - - +- **configuration:** Fix handling of config values that start with . or .. but are not actually relative paths; e.g. ".foo" or "..bar" ([#2065](https://github.com/feathersjs/feathers/issues/2065)) ([d07bf59](https://github.com/feathersjs/feathers/commit/d07bf5902e9c8c606f16b9523472972d3d2e9b49)) ## [4.5.8](https://github.com/feathersjs/feathers/compare/v4.5.7...v4.5.8) (2020-08-12) **Note:** Version bump only for package @feathersjs/configuration - - - - ## [4.5.7](https://github.com/feathersjs/feathers/compare/v4.5.6...v4.5.7) (2020-07-24) **Note:** Version bump only for package @feathersjs/configuration - - - - ## [4.5.5](https://github.com/feathersjs/feathers/compare/v4.5.4...v4.5.5) (2020-07-11) **Note:** Version bump only for package @feathersjs/configuration - - - - ## [4.5.3](https://github.com/feathersjs/feathers/compare/v4.5.2...v4.5.3) (2020-04-17) **Note:** Version bump only for package @feathersjs/configuration - - - - ## [4.5.2](https://github.com/feathersjs/feathers/compare/v4.5.1...v4.5.2) (2020-03-04) **Note:** Version bump only for package @feathersjs/configuration - - - - ## [4.5.1](https://github.com/feathersjs/feathers/compare/v4.5.0...v4.5.1) (2020-01-24) **Note:** Version bump only for package @feathersjs/configuration - - - - # [4.5.0](https://github.com/feathersjs/feathers/compare/v4.4.3...v4.5.0) (2020-01-18) **Note:** Version bump only for package @feathersjs/configuration - - - - ## [4.4.3](https://github.com/feathersjs/feathers/compare/v4.4.1...v4.4.3) (2019-12-06) **Note:** Version bump only for package @feathersjs/configuration - - - - ## [4.4.1](https://github.com/feathersjs/feathers/compare/v4.4.0...v4.4.1) (2019-11-27) **Note:** Version bump only for package @feathersjs/configuration - - - - # [4.4.0](https://github.com/feathersjs/feathers/compare/v4.3.11...v4.4.0) (2019-11-27) **Note:** Version bump only for package @feathersjs/configuration - - - - ## [4.3.11](https://github.com/feathersjs/feathers/compare/v4.3.10...v4.3.11) (2019-11-11) **Note:** Version bump only for package @feathersjs/configuration - - - - ## [4.3.10](https://github.com/feathersjs/feathers/compare/v4.3.9...v4.3.10) (2019-10-26) **Note:** Version bump only for package @feathersjs/configuration - - - - ## [4.3.9](https://github.com/feathersjs/feathers/compare/v4.3.8...v4.3.9) (2019-10-26) **Note:** Version bump only for package @feathersjs/configuration - - - - ## [4.3.7](https://github.com/feathersjs/feathers/compare/v4.3.6...v4.3.7) (2019-10-14) **Note:** Version bump only for package @feathersjs/configuration - - - - ## [4.3.4](https://github.com/feathersjs/feathers/compare/v4.3.3...v4.3.4) (2019-10-03) **Note:** Version bump only for package @feathersjs/configuration - - - - ## [4.3.3](https://github.com/feathersjs/feathers/compare/v4.3.2...v4.3.3) (2019-09-21) - ### Bug Fixes -* Small improvements in dependencies and code sturcture ([#1562](https://github.com/feathersjs/feathers/issues/1562)) ([42c13e2](https://github.com/feathersjs/feathers/commit/42c13e2)) - - - - +- Small improvements in dependencies and code sturcture ([#1562](https://github.com/feathersjs/feathers/issues/1562)) ([42c13e2](https://github.com/feathersjs/feathers/commit/42c13e2)) ## [4.3.2](https://github.com/feathersjs/feathers/compare/v4.3.1...v4.3.2) (2019-09-16) **Note:** Version bump only for package @feathersjs/configuration - - - - ## [4.3.1](https://github.com/feathersjs/feathers/compare/v4.3.0...v4.3.1) (2019-09-09) **Note:** Version bump only for package @feathersjs/configuration - - - - # [4.3.0](https://github.com/feathersjs/feathers/compare/v4.3.0-pre.4...v4.3.0) (2019-08-27) **Note:** Version bump only for package @feathersjs/configuration - - - - # [4.3.0-pre.4](https://github.com/feathersjs/feathers/compare/v4.3.0-pre.3...v4.3.0-pre.4) (2019-08-22) **Note:** Version bump only for package @feathersjs/configuration - - - - # [4.3.0-pre.3](https://github.com/feathersjs/feathers/compare/v4.3.0-pre.2...v4.3.0-pre.3) (2019-08-19) - ### Bug Fixes -* Update all dependencies ([7d53a00](https://github.com/feathersjs/feathers/commit/7d53a00)) - - - - +- Update all dependencies ([7d53a00](https://github.com/feathersjs/feathers/commit/7d53a00)) # [4.3.0-pre.2](https://github.com/feathersjs/feathers/compare/v4.3.0-pre.1...v4.3.0-pre.2) (2019-08-02) **Note:** Version bump only for package @feathersjs/configuration - - - - # [4.3.0-pre.1](https://github.com/feathersjs/feathers/compare/v4.0.0-pre.5...v4.3.0-pre.1) (2019-07-11) **Note:** Version bump only for package @feathersjs/configuration - - - - # [4.0.0-pre.5](https://github.com/feathersjs/feathers/compare/v4.0.0-pre.4...v4.0.0-pre.5) (2019-07-10) **Note:** Version bump only for package @feathersjs/configuration - - - - # [4.0.0-pre.4](https://github.com/feathersjs/feathers/compare/v4.0.0-pre.3...v4.0.0-pre.4) (2019-07-05) **Note:** Version bump only for package @feathersjs/configuration - - - - # [4.0.0-pre.3](https://github.com/feathersjs/feathers/compare/v4.0.0-pre.2...v4.0.0-pre.3) (2019-06-01) - ### Bug Fixes -* Update dependencies and fix tests ([#1373](https://github.com/feathersjs/feathers/issues/1373)) ([d743a7f](https://github.com/feathersjs/feathers/commit/d743a7f)) - - - - +- Update dependencies and fix tests ([#1373](https://github.com/feathersjs/feathers/issues/1373)) ([d743a7f](https://github.com/feathersjs/feathers/commit/d743a7f)) # [4.0.0-pre.2](https://github.com/feathersjs/feathers/compare/v4.0.0-pre.1...v4.0.0-pre.2) (2019-05-15) **Note:** Version bump only for package @feathersjs/configuration - - - - # [4.0.0-pre.1](https://github.com/feathersjs/feathers/compare/v4.0.0-pre.0...v4.0.0-pre.1) (2019-05-08) **Note:** Version bump only for package @feathersjs/configuration - - - - # [4.0.0-pre.0](https://github.com/feathersjs/feathers/compare/v3.2.0-pre.1...v4.0.0-pre.0) (2019-04-21) - ### Bug Fixes -* Update all dependencies to latest ([#1206](https://github.com/feathersjs/feathers/issues/1206)) ([e51e0f6](https://github.com/feathersjs/feathers/commit/e51e0f6)) -* **package:** update config to version 3.0.0 ([#1100](https://github.com/feathersjs/feathers/issues/1100)) ([c9f4b42](https://github.com/feathersjs/feathers/commit/c9f4b42)) -* Make Mocha a proper devDependency for every repository ([#1053](https://github.com/feathersjs/feathers/issues/1053)) ([9974803](https://github.com/feathersjs/feathers/commit/9974803)) -* **package:** update debug to version 3.0.0 ([#45](https://github.com/feathersjs/feathers/issues/45)) ([2391434](https://github.com/feathersjs/feathers/commit/2391434)) -* **package:** update debug to version 3.0.1 ([#46](https://github.com/feathersjs/feathers/issues/46)) ([f8ada69](https://github.com/feathersjs/feathers/commit/f8ada69)) - +- Update all dependencies to latest ([#1206](https://github.com/feathersjs/feathers/issues/1206)) ([e51e0f6](https://github.com/feathersjs/feathers/commit/e51e0f6)) +- **package:** update config to version 3.0.0 ([#1100](https://github.com/feathersjs/feathers/issues/1100)) ([c9f4b42](https://github.com/feathersjs/feathers/commit/c9f4b42)) +- Make Mocha a proper devDependency for every repository ([#1053](https://github.com/feathersjs/feathers/issues/1053)) ([9974803](https://github.com/feathersjs/feathers/commit/9974803)) +- **package:** update debug to version 3.0.0 ([#45](https://github.com/feathersjs/feathers/issues/45)) ([2391434](https://github.com/feathersjs/feathers/commit/2391434)) +- **package:** update debug to version 3.0.1 ([#46](https://github.com/feathersjs/feathers/issues/46)) ([f8ada69](https://github.com/feathersjs/feathers/commit/f8ada69)) ### Features -* Add TypeScript definitions ([#1275](https://github.com/feathersjs/feathers/issues/1275)) ([9dd6713](https://github.com/feathersjs/feathers/commit/9dd6713)) - - - - +- Add TypeScript definitions ([#1275](https://github.com/feathersjs/feathers/issues/1275)) ([9dd6713](https://github.com/feathersjs/feathers/commit/9dd6713)) ## [2.0.6](https://github.com/feathersjs/feathers/compare/@feathersjs/configuration@2.0.5...@feathersjs/configuration@2.0.6) (2019-01-02) **Note:** Version bump only for package @feathersjs/configuration - - - - -## [2.0.5](https://github.com/feathersjs/feathers/compare/@feathersjs/configuration@2.0.4...@feathersjs/configuration@2.0.5) (2018-12-16) +## [2.0.5](https://github.com/feathersjs/feathers/compare/@feathersjs/configuration@2.0.4...@feathersjs/configuration@2.0.5) (2018-12-16) ### Bug Fixes -* Make Mocha a proper devDependency for every repository ([#1053](https://github.com/feathersjs/feathers/issues/1053)) ([9974803](https://github.com/feathersjs/feathers/commit/9974803)) -* **package:** update config to version 3.0.0 ([#1100](https://github.com/feathersjs/feathers/issues/1100)) ([c9f4b42](https://github.com/feathersjs/feathers/commit/c9f4b42)) - - - - +- Make Mocha a proper devDependency for every repository ([#1053](https://github.com/feathersjs/feathers/issues/1053)) ([9974803](https://github.com/feathersjs/feathers/commit/9974803)) +- **package:** update config to version 3.0.0 ([#1100](https://github.com/feathersjs/feathers/issues/1100)) ([c9f4b42](https://github.com/feathersjs/feathers/commit/c9f4b42)) + ## [2.0.4](https://github.com/feathersjs/feathers/compare/@feathersjs/configuration@2.0.3...@feathersjs/configuration@2.0.4) (2018-09-21) **Note:** Version bump only for package @feathersjs/configuration - - - - + ## [2.0.3](https://github.com/feathersjs/feathers/compare/@feathersjs/configuration@2.0.2...@feathersjs/configuration@2.0.3) (2018-09-17) **Note:** Version bump only for package @feathersjs/configuration - - - - + ## [2.0.2](https://github.com/feathersjs/feathers/compare/@feathersjs/configuration@2.0.1...@feathersjs/configuration@2.0.2) (2018-09-02) **Note:** Version bump only for package @feathersjs/configuration + ## 2.0.1 - Migrate to Monorepo ([feathers#462](https://github.com/feathersjs/feathers/issues/462)) ## [v2.0.0](https://github.com/feathersjs/configuration/tree/v2.0.0) (2018-07-30) + [Full Changelog](https://github.com/feathersjs/configuration/compare/v1.0.2...v2.0.0) **Closed issues:** @@ -523,13 +370,15 @@ functionality like path replacements and automatic environment variable insertio - Update mocha to the latest version 🚀 [\#56](https://github.com/feathersjs/configuration/pull/56) ([greenkeeper[bot]](https://github.com/apps/greenkeeper)) ## [v1.0.2](https://github.com/feathersjs/configuration/tree/v1.0.2) (2018-01-02) + [Full Changelog](https://github.com/feathersjs/configuration/compare/v1.0.1...v1.0.2) **Merged pull requests:** -- Remove example and update Readme to point directly to the Feathers docs [\#55](https://github.com/feathersjs/configuration/pull/55) ([daffl](https://github.com/daffl)) +- Remove example and update Readme to point directly to the Feathers docs [\#55](https://github.com/feathersjs/configuration/pull/55) ([daffl](https://github.com/daffl)) ## [v1.0.1](https://github.com/feathersjs/configuration/tree/v1.0.1) (2017-11-16) + [Full Changelog](https://github.com/feathersjs/configuration/compare/v1.0.0...v1.0.1) **Merged pull requests:** @@ -538,9 +387,11 @@ functionality like path replacements and automatic environment variable insertio - Update nsp to the latest version 🚀 [\#52](https://github.com/feathersjs/configuration/pull/52) ([greenkeeper[bot]](https://github.com/apps/greenkeeper)) ## [v1.0.0](https://github.com/feathersjs/configuration/tree/v1.0.0) (2017-11-01) + [Full Changelog](https://github.com/feathersjs/configuration/compare/v1.0.0-pre.1...v1.0.0) ## [v1.0.0-pre.1](https://github.com/feathersjs/configuration/tree/v1.0.0-pre.1) (2017-10-23) + [Full Changelog](https://github.com/feathersjs/configuration/compare/v0.4.2...v1.0.0-pre.1) **Closed issues:** @@ -552,6 +403,7 @@ functionality like path replacements and automatic environment variable insertio - Update to new plugin infrastructure and npm scopes [\#51](https://github.com/feathersjs/configuration/pull/51) ([daffl](https://github.com/daffl)) ## [v0.4.2](https://github.com/feathersjs/configuration/tree/v0.4.2) (2017-10-15) + [Full Changelog](https://github.com/feathersjs/configuration/compare/v0.4.1...v0.4.2) **Closed issues:** @@ -563,7 +415,7 @@ functionality like path replacements and automatic environment variable insertio - Nested configuration [\#38](https://github.com/feathersjs/configuration/issues/38) - Stuck in configuration loophole... [\#37](https://github.com/feathersjs/configuration/issues/37) - Docs are wrong [\#36](https://github.com/feathersjs/configuration/issues/36) -- Why use "NODE\_ENV=development" with default.json? [\#33](https://github.com/feathersjs/configuration/issues/33) +- Why use "NODE_ENV=development" with default.json? [\#33](https://github.com/feathersjs/configuration/issues/33) **Merged pull requests:** @@ -579,6 +431,7 @@ functionality like path replacements and automatic environment variable insertio - 👻😱 Node.js 0.10 is unmaintained 😱👻 [\#30](https://github.com/feathersjs/configuration/pull/30) ([greenkeeperio-bot](https://github.com/greenkeeperio-bot)) ## [v0.4.1](https://github.com/feathersjs/configuration/tree/v0.4.1) (2016-10-24) + [Full Changelog](https://github.com/feathersjs/configuration/compare/v0.4.0...v0.4.1) **Closed issues:** @@ -591,6 +444,7 @@ functionality like path replacements and automatic environment variable insertio - jshint —\> semistandard [\#28](https://github.com/feathersjs/configuration/pull/28) ([corymsmith](https://github.com/corymsmith)) ## [v0.4.0](https://github.com/feathersjs/configuration/tree/v0.4.0) (2016-10-22) + [Full Changelog](https://github.com/feathersjs/configuration/compare/v0.3.3...v0.4.0) **Implemented enhancements:** @@ -603,9 +457,11 @@ functionality like path replacements and automatic environment variable insertio - Make this repo more about managing configuration [\#24](https://github.com/feathersjs/configuration/issues/24) ## [v0.3.3](https://github.com/feathersjs/configuration/tree/v0.3.3) (2016-09-12) + [Full Changelog](https://github.com/feathersjs/configuration/compare/v0.3.2...v0.3.3) ## [v0.3.2](https://github.com/feathersjs/configuration/tree/v0.3.2) (2016-09-12) + [Full Changelog](https://github.com/feathersjs/configuration/compare/v0.3.1...v0.3.2) **Closed issues:** @@ -617,6 +473,7 @@ functionality like path replacements and automatic environment variable insertio - Remove check for development mode [\#21](https://github.com/feathersjs/configuration/pull/21) ([daffl](https://github.com/daffl)) ## [v0.3.1](https://github.com/feathersjs/configuration/tree/v0.3.1) (2016-08-15) + [Full Changelog](https://github.com/feathersjs/configuration/compare/v0.3.0...v0.3.1) **Merged pull requests:** @@ -625,17 +482,19 @@ functionality like path replacements and automatic environment variable insertio - Update mocha to version 3.0.0 🚀 [\#18](https://github.com/feathersjs/configuration/pull/18) ([greenkeeperio-bot](https://github.com/greenkeeperio-bot)) ## [v0.3.0](https://github.com/feathersjs/configuration/tree/v0.3.0) (2016-05-22) + [Full Changelog](https://github.com/feathersjs/configuration/compare/v0.2.3...v0.3.0) **Closed issues:** -- \.json config need deep merge options [\#16](https://github.com/feathersjs/configuration/issues/16) +- \.json config need deep merge options [\#16](https://github.com/feathersjs/configuration/issues/16) **Merged pull requests:** - Add functionality for deeply extending configuration [\#17](https://github.com/feathersjs/configuration/pull/17) ([daffl](https://github.com/daffl)) ## [v0.2.3](https://github.com/feathersjs/configuration/tree/v0.2.3) (2016-04-24) + [Full Changelog](https://github.com/feathersjs/configuration/compare/v0.2.2...v0.2.3) **Closed issues:** @@ -648,6 +507,7 @@ functionality like path replacements and automatic environment variable insertio - Update all dependencies 🌴 [\#10](https://github.com/feathersjs/configuration/pull/10) ([greenkeeperio-bot](https://github.com/greenkeeperio-bot)) ## [v0.2.2](https://github.com/feathersjs/configuration/tree/v0.2.2) (2016-03-27) + [Full Changelog](https://github.com/feathersjs/configuration/compare/v0.2.1...v0.2.2) **Merged pull requests:** @@ -655,6 +515,7 @@ functionality like path replacements and automatic environment variable insertio - Expanding environment variables in \.json [\#9](https://github.com/feathersjs/configuration/pull/9) ([derek-watson](https://github.com/derek-watson)) ## [v0.2.1](https://github.com/feathersjs/configuration/tree/v0.2.1) (2016-03-12) + [Full Changelog](https://github.com/feathersjs/configuration/compare/v0.2.0...v0.2.1) **Merged pull requests:** @@ -662,6 +523,7 @@ functionality like path replacements and automatic environment variable insertio - Makes sure that arrays get converted properly [\#7](https://github.com/feathersjs/configuration/pull/7) ([daffl](https://github.com/daffl)) ## [v0.2.0](https://github.com/feathersjs/configuration/tree/v0.2.0) (2016-03-09) + [Full Changelog](https://github.com/feathersjs/configuration/compare/v0.1.1...v0.2.0) **Closed issues:** @@ -673,11 +535,12 @@ functionality like path replacements and automatic environment variable insertio - Implement an escape character [\#6](https://github.com/feathersjs/configuration/pull/6) ([daffl](https://github.com/daffl)) ## [v0.1.1](https://github.com/feathersjs/configuration/tree/v0.1.1) (2016-03-09) + [Full Changelog](https://github.com/feathersjs/configuration/compare/v0.1.0...v0.1.1) **Closed issues:** -- Configuration should recursively go through the values [\#2](https://github.com/feathersjs/configuration/issues/2) +- Configuration should recursively go through the values [\#2](https://github.com/feathersjs/configuration/issues/2) **Merged pull requests:** @@ -687,5 +550,4 @@ functionality like path replacements and automatic environment variable insertio ## [v0.1.0](https://github.com/feathersjs/configuration/tree/v0.1.0) (2015-11-14) - -\* *This Change Log was automatically generated by [github_changelog_generator](https://github.com/skywinder/Github-Changelog-Generator)* +\* _This Change Log was automatically generated by [github_changelog_generator](https://github.com/skywinder/Github-Changelog-Generator)_ diff --git a/packages/configuration/LICENSE b/packages/configuration/LICENSE index 3f395cc665..59604f46f3 100644 --- a/packages/configuration/LICENSE +++ b/packages/configuration/LICENSE @@ -1,6 +1,6 @@ The MIT License (MIT) -Copyright (c) 2021 Feathers +Copyright (c) 2022 Feathers Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated documentation files (the "Software"), to deal diff --git a/packages/configuration/README.md b/packages/configuration/README.md index decded0f41..2e38b61efa 100644 --- a/packages/configuration/README.md +++ b/packages/configuration/README.md @@ -1,8 +1,8 @@ # @feathersjs/configuration [![CI](https://github.com/feathersjs/feathers/workflows/CI/badge.svg)](https://github.com/feathersjs/feathers/actions?query=workflow%3ACI) -[![Dependency Status](https://img.shields.io/david/feathersjs/feathers.svg?style=flat-square&path=packages/configuration)](https://david-dm.org/feathersjs/feathers?path=packages/configuration) [![Download Status](https://img.shields.io/npm/dm/@feathersjs/configuration.svg?style=flat-square)](https://www.npmjs.com/package/@feathersjs/configuration) +[![Discord](https://badgen.net/badge/icon/discord?icon=discord&label)](https://discord.gg/qa8kez8QBx) > A small configuration module for your Feathers application. @@ -18,6 +18,6 @@ Refer to the [Feathers configuration API documentation](https://docs.feathersjs. ## License -Copyright (c) 2021 [Feathers contributors](https://github.com/feathersjs/feathers/graphs/contributors) +Copyright (c) 2022 [Feathers contributors](https://github.com/feathersjs/feathers/graphs/contributors) Licensed under the [MIT license](LICENSE). diff --git a/packages/configuration/package.json b/packages/configuration/package.json index e80342df29..c903c66124 100644 --- a/packages/configuration/package.json +++ b/packages/configuration/package.json @@ -1,7 +1,7 @@ { "name": "@feathersjs/configuration", "description": "A small configuration module for your Feathers application.", - "version": "5.0.0-pre.16", + "version": "5.0.0-pre.31", "homepage": "https://feathersjs.com", "main": "lib/", "types": "lib/", @@ -16,7 +16,8 @@ }, "repository": { "type": "git", - "url": "git://github.com/feathersjs/feathers.git" + "url": "git://github.com/feathersjs/feathers.git", + "directory": "packages/configuration" }, "author": { "name": "Feathers contributors", @@ -41,9 +42,9 @@ ], "scripts": { "prepublish": "npm run compile", - "compile": "shx rm -rf lib/ && tsc", - "test": "npm run compile && npm run mocha", - "mocha": "NODE_CONFIG_DIR=./test/config mocha --config ../../.mocharc.json --recursive test/**.test.ts test/**/*.test.ts" + "pack": "npm pack --pack-destination ../cli/test/build", + "compile": "shx rm -rf lib/ && tsc && npm run pack", + "test": "NODE_CONFIG_DIR=./test/config mocha --config ../../.mocharc.json --recursive test/**.test.ts test/**/*.test.ts" }, "semistandard": { "env": [ @@ -57,18 +58,19 @@ "access": "public" }, "dependencies": { - "@feathersjs/commons": "^5.0.0-pre.16", - "@feathersjs/feathers": "^5.0.0-pre.16", - "@types/config": "^0.0.40", - "config": "^3.3.6" + "@feathersjs/commons": "^5.0.0-pre.31", + "@feathersjs/feathers": "^5.0.0-pre.31", + "@feathersjs/schema": "^5.0.0-pre.31", + "@types/config": "^3.3.0", + "config": "^3.3.8" }, "devDependencies": { - "@types/mocha": "^9.0.0", - "@types/node": "^17.0.5", - "mocha": "^9.1.3", - "shx": "^0.3.3", - "ts-node": "^10.4.0", - "typescript": "^4.5.4" + "@types/mocha": "^10.0.0", + "@types/node": "^18.8.2", + "mocha": "^10.0.0", + "shx": "^0.3.4", + "ts-node": "^10.9.1", + "typescript": "^4.8.4" }, - "gitHead": "f0cd227a82d159b528193bd33747c97684a48773" + "gitHead": "4500dbeb8cea566678cf88b3313a88efd93a2ed9" } diff --git a/packages/configuration/src/index.ts b/packages/configuration/src/index.ts index d425a7150f..a34606d679 100644 --- a/packages/configuration/src/index.ts +++ b/packages/configuration/src/index.ts @@ -1,23 +1,39 @@ -import { Application } from '@feathersjs/feathers'; -import { createDebug } from '@feathersjs/commons'; -import config from 'config'; +import { Application, ApplicationHookContext, NextFunction } from '@feathersjs/feathers' +import { createDebug } from '@feathersjs/commons' +import { Schema, Validator } from '@feathersjs/schema' +import config from 'config' -const debug = createDebug('@feathersjs/configuration'); +const debug = createDebug('@feathersjs/configuration') + +export = function init(schema?: Schema | Validator) { + const validator: Validator = typeof schema === 'function' ? schema : schema?.validate.bind(schema) -export = function init () { return (app?: Application) => { if (!app) { - return config; + return config } - debug(`Initializing configuration for ${config.util.getEnv('NODE_ENV')} environment`); + const configuration: { [key: string]: unknown } = { ...config } + + debug(`Initializing configuration for ${config.util.getEnv('NODE_ENV')} environment`) - Object.keys(config).forEach(name => { - const value = (config as any)[name]; - debug(`Setting ${name} configuration value to`, value); - app.set(name, value); - }); + Object.keys(configuration).forEach((name) => { + const value = configuration[name] + debug(`Setting ${name} configuration value to`, value) + app.set(name, value) + }) + + if (validator) { + app.hooks({ + setup: [ + async (_context: ApplicationHookContext, next: NextFunction) => { + await validator(configuration) + await next() + } + ] + }) + } - return config; - }; + return config + } } diff --git a/packages/configuration/test/index.test.ts b/packages/configuration/test/index.test.ts index 780c9c4421..65fc1c8d14 100644 --- a/packages/configuration/test/index.test.ts +++ b/packages/configuration/test/index.test.ts @@ -1,23 +1,67 @@ -import { strict as assert } from 'assert'; -import { feathers, Application } from '@feathersjs/feathers'; -import plugin from '../src'; +import { strict as assert } from 'assert' +import { feathers, Application } from '@feathersjs/feathers' +import { Ajv, schema } from '@feathersjs/schema' +import configuration from '../src' describe('@feathersjs/configuration', () => { - const app: Application = feathers().configure(plugin()); + const app: Application = feathers().configure(configuration()) it('initialized app with default.json', () => { - assert.equal(app.get('port'), 3030); - assert.deepEqual(app.get('array'), [ - 'one', 'two', 'three' - ]); - assert.deepEqual(app.get('deep'), { base: false }); - assert.deepEqual(app.get('nullish'), null); - }); + assert.equal(app.get('port'), 3030) + assert.deepEqual(app.get('array'), ['one', 'two', 'three']) + assert.deepEqual(app.get('deep'), { base: false }) + assert.deepEqual(app.get('nullish'), null) + }) it('works when called directly', () => { - const fn = plugin(); - const conf = fn() as any; + const fn = configuration() + const conf = fn() as any - assert.strictEqual(conf.port, 3030); - }); -}); + assert.strictEqual(conf.port, 3030) + }) + + it('errors on .setup when a schema is passed and the configuration is invalid', async () => { + const configurationSchema = schema( + { + $id: 'ConfigurationSchema', + additionalProperties: false, + type: 'object', + properties: { + port: { type: 'number' }, + deep: { + type: 'object', + properties: { + base: { + type: 'boolean' + } + } + }, + array: { + type: 'array', + items: { type: 'string' } + }, + nullish: { + type: 'string' + } + } + } as const, + new Ajv() + ) + + const schemaApp = feathers().configure(configuration(configurationSchema)) + + await assert.rejects(() => schemaApp.setup(), { + data: [ + { + instancePath: '/nullish', + keyword: 'type', + message: 'must be string', + params: { + type: 'string' + }, + schemaPath: '#/properties/nullish/type' + } + ] + }) + }) +}) diff --git a/packages/create-feathers/CHANGELOG.md b/packages/create-feathers/CHANGELOG.md new file mode 100644 index 0000000000..90a26baf37 --- /dev/null +++ b/packages/create-feathers/CHANGELOG.md @@ -0,0 +1,14 @@ +# Change Log + +All notable changes to this project will be documented in this file. +See [Conventional Commits](https://conventionalcommits.org) for commit guidelines. + +# [5.0.0-pre.31](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.30...v5.0.0-pre.31) (2022-10-12) + +**Note:** Version bump only for package create-feathers + +# [5.0.0-pre.30](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.29...v5.0.0-pre.30) (2022-10-07) + +### Features + +- **cli:** Add ability to `npm init feathers` ([#2755](https://github.com/feathersjs/feathers/issues/2755)) ([d734931](https://github.com/feathersjs/feathers/commit/d734931ffd4f983a05d9e771ce0e43b696c2bc0e)) diff --git a/packages/create-feathers/bin/create-feathers b/packages/create-feathers/bin/create-feathers new file mode 100755 index 0000000000..b9161e21ba --- /dev/null +++ b/packages/create-feathers/bin/create-feathers @@ -0,0 +1,50 @@ +#!/usr/bin/env node +'use strict'; + +const path = require('path') +const { existsSync } = require('fs') +const { mkdir } = require('fs/promises') +const { Command, commandRunner, chalk } = require('@feathersjs/cli') + +const program = new Command() +const generateApp = commandRunner('app') + +program + .name('npm init feathers') + .description(`Create a new Feathers application 🕊️ + +${chalk.grey('npm init feathers myapp')} +`) + .argument('', 'The name of your new application') + // .version(version) + .showHelpAfterError() + .action(async (name, options) => { + try { + const cwd = path.join(process.cwd(), name) + + if (existsSync(cwd)) { + throw new Error(`Can not create Feathers application, the folder "${name}" already exists`) + } + + await mkdir(cwd) + + await generateApp({ + name, + cwd, + ...options + }) + + console.log(` + +${chalk.green('Hooray')}! Your Feathers app is ready to go! 🚀 +Go to the ${chalk.grey(name)} folder to get started. + +To learn more visit ${chalk.grey('https://dove.feathersjs.com/guides')} +`) + } catch (error) { + console.error(`${chalk.red('Error')}: ${error.message}`) + process.exit(1) + } + }) + +program.parse() diff --git a/_templates/package/new/package.json.t b/packages/create-feathers/package.json similarity index 57% rename from _templates/package/new/package.json.t rename to packages/create-feathers/package.json index a9a0e96d66..c5470a0f6a 100644 --- a/_templates/package/new/package.json.t +++ b/packages/create-feathers/package.json @@ -1,13 +1,11 @@ ---- -to: packages/<%= name %>/package.json ---- - { - "name": "@feathersjs/<%= name %>", - "description": "<%= description %>", - "version": "0.0.0", + "name": "create-feathers", + "description": "Create a new Feathers application", + "version": "5.0.0-pre.31", "homepage": "https://feathersjs.com", - "main": "lib/", + "bin": { + "create-feathers": "./bin/create-feathers" + }, "keywords": [ "feathers", "feathers-plugin" @@ -31,35 +29,25 @@ to: packages/<%= name %>/package.json "url": "https://github.com/feathersjs/feathers/issues" }, "engines": { - "node": ">= 12" + "node": ">= 14" }, "files": [ "CHANGELOG.md", "LICENSE", "README.md", - "src/**", "lib/**", + "bin/**", "*.d.ts", "*.js" ], "scripts": { - "prepublish": "npm run compile", - "compile": "shx rm -rf lib/ && tsc", - "test": "mocha --config ../../.mocharc.json --recursive test/**.test.ts test/**/*.test.ts" - }, - "directories": { - "lib": "lib" + "test": "echo \"No tests necessary\"" }, "publishConfig": { "access": "public" }, "dependencies": { + "@feathersjs/cli": "^5.0.0-pre.31" }, - "devDependencies": { - "@types/mocha": "^8.2.2", - "@types/node": "^14.14.37", - "mocha": "^8.3.2", - "shx": "^0.3.3", - "typescript": "^4.2.3" - } + "gitHead": "4500dbeb8cea566678cf88b3313a88efd93a2ed9" } diff --git a/packages/errors/CHANGELOG.md b/packages/errors/CHANGELOG.md index 5f3febb0b6..52a07866a4 100644 --- a/packages/errors/CHANGELOG.md +++ b/packages/errors/CHANGELOG.md @@ -3,169 +3,160 @@ All notable changes to this project will be documented in this file. See [Conventional Commits](https://conventionalcommits.org) for commit guidelines. -# [5.0.0-pre.16](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.15...v5.0.0-pre.16) (2022-01-12) +# [5.0.0-pre.31](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.30...v5.0.0-pre.31) (2022-10-12) -**Note:** Version bump only for package @feathersjs/errors +### Bug Fixes +- **errors:** Allows to pass no error message ([#2794](https://github.com/feathersjs/feathers/issues/2794)) ([f3ddab6](https://github.com/feathersjs/feathers/commit/f3ddab637e269e67e852ffce07b060bab2b085c0)) +# [5.0.0-pre.30](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.29...v5.0.0-pre.30) (2022-10-07) +### Features +- **core:** Allow to unregister services at runtime ([#2756](https://github.com/feathersjs/feathers/issues/2756)) ([d16601f](https://github.com/feathersjs/feathers/commit/d16601f2277dca5357866ffdefba2a611f6dc7fa)) -# [5.0.0-pre.15](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.14...v5.0.0-pre.15) (2021-11-27) +# [5.0.0-pre.29](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.28...v5.0.0-pre.29) (2022-09-16) **Note:** Version bump only for package @feathersjs/errors +# [5.0.0-pre.28](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.27...v5.0.0-pre.28) (2022-08-03) +### Bug Fixes +- **cli:** Improve generated application and client ([#2701](https://github.com/feathersjs/feathers/issues/2701)) ([bd55ffb](https://github.com/feathersjs/feathers/commit/bd55ffb812e89bf215f4515e7f137656ea888c3f)) - -# [5.0.0-pre.14](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.13...v5.0.0-pre.14) (2021-10-13) +# [5.0.0-pre.27](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.26...v5.0.0-pre.27) (2022-07-13) **Note:** Version bump only for package @feathersjs/errors +# [5.0.0-pre.26](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.25...v5.0.0-pre.26) (2022-06-22) +**Note:** Version bump only for package @feathersjs/errors +# [5.0.0-pre.25](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.24...v5.0.0-pre.25) (2022-06-22) +**Note:** Version bump only for package @feathersjs/errors -# [5.0.0-pre.13](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.12...v5.0.0-pre.13) (2021-10-13) +# [5.0.0-pre.24](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.23...v5.0.0-pre.24) (2022-06-21) **Note:** Version bump only for package @feathersjs/errors +# [5.0.0-pre.23](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.22...v5.0.0-pre.23) (2022-06-06) +**Note:** Version bump only for package @feathersjs/errors +# [5.0.0-pre.22](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.21...v5.0.0-pre.22) (2022-05-24) +**Note:** Version bump only for package @feathersjs/errors -# [5.0.0-pre.12](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.11...v5.0.0-pre.12) (2021-10-12) +# [5.0.0-pre.21](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.20...v5.0.0-pre.21) (2022-05-23) **Note:** Version bump only for package @feathersjs/errors +# [5.0.0-pre.20](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.19...v5.0.0-pre.20) (2022-05-04) +### Bug Fixes +- **dependencies:** Lock monorepo package version numbers ([#2623](https://github.com/feathersjs/feathers/issues/2623)) ([5640c10](https://github.com/feathersjs/feathers/commit/5640c1020cc139994e695d658c08bad3494db507)) - -# [5.0.0-pre.11](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.10...v5.0.0-pre.11) (2021-10-06) +# [5.0.0-pre.19](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.18...v5.0.0-pre.19) (2022-05-01) **Note:** Version bump only for package @feathersjs/errors +# [5.0.0-pre.18](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.17...v5.0.0-pre.18) (2022-04-11) +**Note:** Version bump only for package @feathersjs/errors +# [5.0.0-pre.17](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.16...v5.0.0-pre.17) (2022-02-15) +**Note:** Version bump only for package @feathersjs/errors -# [5.0.0-pre.10](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.9...v5.0.0-pre.10) (2021-09-19) +# [5.0.0-pre.16](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.15...v5.0.0-pre.16) (2022-01-12) **Note:** Version bump only for package @feathersjs/errors +# [5.0.0-pre.15](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.14...v5.0.0-pre.15) (2021-11-27) +**Note:** Version bump only for package @feathersjs/errors +# [5.0.0-pre.14](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.13...v5.0.0-pre.14) (2021-10-13) +**Note:** Version bump only for package @feathersjs/errors -# [5.0.0-pre.9](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.8...v5.0.0-pre.9) (2021-08-09) +# [5.0.0-pre.13](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.12...v5.0.0-pre.13) (2021-10-13) **Note:** Version bump only for package @feathersjs/errors +# [5.0.0-pre.12](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.11...v5.0.0-pre.12) (2021-10-12) +**Note:** Version bump only for package @feathersjs/errors +# [5.0.0-pre.11](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.10...v5.0.0-pre.11) (2021-10-06) +**Note:** Version bump only for package @feathersjs/errors -# [5.0.0-pre.8](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.7...v5.0.0-pre.8) (2021-08-09) +# [5.0.0-pre.10](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.9...v5.0.0-pre.10) (2021-09-19) **Note:** Version bump only for package @feathersjs/errors +# [5.0.0-pre.9](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.8...v5.0.0-pre.9) (2021-08-09) +**Note:** Version bump only for package @feathersjs/errors +# [5.0.0-pre.8](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.7...v5.0.0-pre.8) (2021-08-09) +**Note:** Version bump only for package @feathersjs/errors # [5.0.0-pre.7](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.6...v5.0.0-pre.7) (2021-08-09) **Note:** Version bump only for package @feathersjs/errors - - - - # [5.0.0-pre.6](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.5...v5.0.0-pre.6) (2021-08-08) **Note:** Version bump only for package @feathersjs/errors - - - - # [5.0.0-pre.5](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.4...v5.0.0-pre.5) (2021-06-23) **Note:** Version bump only for package @feathersjs/errors - - - - # [5.0.0-pre.4](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.3...v5.0.0-pre.4) (2021-05-13) **Note:** Version bump only for package @feathersjs/errors - - - - # [5.0.0-pre.3](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.2...v5.0.0-pre.3) (2021-04-21) - ### Bug Fixes -* **typescript:** Improve TypeScript backwards compatibility ([#2310](https://github.com/feathersjs/feathers/issues/2310)) ([f33be73](https://github.com/feathersjs/feathers/commit/f33be73fc46a533efb15df9aab0658e3240d3897)) - - - - +- **typescript:** Improve TypeScript backwards compatibility ([#2310](https://github.com/feathersjs/feathers/issues/2310)) ([f33be73](https://github.com/feathersjs/feathers/commit/f33be73fc46a533efb15df9aab0658e3240d3897)) # [5.0.0-pre.2](https://github.com/feathersjs/feathers/compare/v5.0.0-beta.1...v5.0.0-pre.2) (2021-04-06) **Note:** Version bump only for package @feathersjs/errors - - - - # [5.0.0-beta.1](https://github.com/feathersjs/feathers/compare/v5.0.0-beta.0...v5.0.0-beta.1) (2021-04-03) **Note:** Version bump only for package @feathersjs/errors - - - - # [5.0.0-beta.0](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.1...v5.0.0-beta.0) (2021-03-28) - ### Bug Fixes -* Update Grant usage and other dependencies ([#2264](https://github.com/feathersjs/feathers/issues/2264)) ([7b0f8fa](https://github.com/feathersjs/feathers/commit/7b0f8fad252419ed0ad0bf259cdf3104d322ab60)) - - - - +- Update Grant usage and other dependencies ([#2264](https://github.com/feathersjs/feathers/issues/2264)) ([7b0f8fa](https://github.com/feathersjs/feathers/commit/7b0f8fad252419ed0ad0bf259cdf3104d322ab60)) # [5.0.0-pre.1](https://github.com/feathersjs/feathers/compare/v4.5.11...v5.0.0-pre.1) (2020-12-17) - - # [5.0.0-pre.0](https://github.com/feathersjs/feathers/compare/v4.5.4...v5.0.0-pre.0) (2020-05-19) - ### Bug Fixes -* **errors:** Format package.json with spaces ([cbd31c1](https://github.com/feathersjs/feathers/commit/cbd31c10c2c574de63d6ca5e55dbfb73a5fdd758)) - - - - +- **errors:** Format package.json with spaces ([cbd31c1](https://github.com/feathersjs/feathers/commit/cbd31c10c2c574de63d6ca5e55dbfb73a5fdd758)) # [5.0.0-pre.0](https://github.com/feathersjs/feathers/compare/v4.5.4...v5.0.0-pre.0) (2020-05-19) ### Bug Fixes -* **errors:** Format package.json with spaces ([cbd31c1](https://github.com/feathersjs/feathers/commit/cbd31c10c2c574de63d6ca5e55dbfb73a5fdd758)) -* **typescript:** Fix `data` property definition in @feathersjs/errors ([#2018](https://github.com/feathersjs/feathers/issues/2018)) ([ef1398c](https://github.com/feathersjs/feathers/commit/ef1398cd5b19efa50929e8c9511ca5684a18997f)) +- **errors:** Format package.json with spaces ([cbd31c1](https://github.com/feathersjs/feathers/commit/cbd31c10c2c574de63d6ca5e55dbfb73a5fdd758)) +- **typescript:** Fix `data` property definition in @feathersjs/errors ([#2018](https://github.com/feathersjs/feathers/issues/2018)) ([ef1398c](https://github.com/feathersjs/feathers/commit/ef1398cd5b19efa50929e8c9511ca5684a18997f)) ## [4.5.11](https://github.com/feathersjs/feathers/compare/v4.5.10...v4.5.11) (2020-12-05) @@ -175,336 +166,192 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline **Note:** Version bump only for package @feathersjs/errors - - - - ## [4.5.9](https://github.com/feathersjs/feathers/compare/v4.5.8...v4.5.9) (2020-10-09) **Note:** Version bump only for package @feathersjs/errors - - - - ## [4.5.8](https://github.com/feathersjs/feathers/compare/v4.5.7...v4.5.8) (2020-08-12) **Note:** Version bump only for package @feathersjs/errors - - - - ## [4.5.7](https://github.com/feathersjs/feathers/compare/v4.5.6...v4.5.7) (2020-07-24) **Note:** Version bump only for package @feathersjs/errors - - - - ## [4.5.5](https://github.com/feathersjs/feathers/compare/v4.5.4...v4.5.5) (2020-07-11) **Note:** Version bump only for package @feathersjs/errors - - - - ## [4.5.3](https://github.com/feathersjs/feathers/compare/v4.5.2...v4.5.3) (2020-04-17) - ### Bug Fixes -* **errors:** Add 410 Gone to errors ([#1849](https://github.com/feathersjs/feathers/issues/1849)) ([6801428](https://github.com/feathersjs/feathers/commit/6801428f8fd17dbfebcdb6f1b0cd01433a4033dc)) - - - - +- **errors:** Add 410 Gone to errors ([#1849](https://github.com/feathersjs/feathers/issues/1849)) ([6801428](https://github.com/feathersjs/feathers/commit/6801428f8fd17dbfebcdb6f1b0cd01433a4033dc)) ## [4.5.2](https://github.com/feathersjs/feathers/compare/v4.5.1...v4.5.2) (2020-03-04) **Note:** Version bump only for package @feathersjs/errors - - - - ## [4.5.1](https://github.com/feathersjs/feathers/compare/v4.5.0...v4.5.1) (2020-01-24) **Note:** Version bump only for package @feathersjs/errors - - - - # [4.5.0](https://github.com/feathersjs/feathers/compare/v4.4.3...v4.5.0) (2020-01-18) **Note:** Version bump only for package @feathersjs/errors - - - - ## [4.4.3](https://github.com/feathersjs/feathers/compare/v4.4.1...v4.4.3) (2019-12-06) **Note:** Version bump only for package @feathersjs/errors - - - - ## [4.4.1](https://github.com/feathersjs/feathers/compare/v4.4.0...v4.4.1) (2019-11-27) **Note:** Version bump only for package @feathersjs/errors - - - - # [4.4.0](https://github.com/feathersjs/feathers/compare/v4.3.11...v4.4.0) (2019-11-27) **Note:** Version bump only for package @feathersjs/errors - - - - ## [4.3.11](https://github.com/feathersjs/feathers/compare/v4.3.10...v4.3.11) (2019-11-11) **Note:** Version bump only for package @feathersjs/errors - - - - ## [4.3.10](https://github.com/feathersjs/feathers/compare/v4.3.9...v4.3.10) (2019-10-26) **Note:** Version bump only for package @feathersjs/errors - - - - ## [4.3.9](https://github.com/feathersjs/feathers/compare/v4.3.8...v4.3.9) (2019-10-26) - ### Bug Fixes -* Small type improvements ([#1624](https://github.com/feathersjs/feathers/issues/1624)) ([50162c6](https://github.com/feathersjs/feathers/commit/50162c6e562f0a47c6a280c4f01fff7c3afee293)) - - - - +- Small type improvements ([#1624](https://github.com/feathersjs/feathers/issues/1624)) ([50162c6](https://github.com/feathersjs/feathers/commit/50162c6e562f0a47c6a280c4f01fff7c3afee293)) ## [4.3.7](https://github.com/feathersjs/feathers/compare/v4.3.6...v4.3.7) (2019-10-14) **Note:** Version bump only for package @feathersjs/errors - - - - ## [4.3.4](https://github.com/feathersjs/feathers/compare/v4.3.3...v4.3.4) (2019-10-03) **Note:** Version bump only for package @feathersjs/errors - - - - ## [4.3.3](https://github.com/feathersjs/feathers/compare/v4.3.2...v4.3.3) (2019-09-21) **Note:** Version bump only for package @feathersjs/errors - - - - ## [4.3.2](https://github.com/feathersjs/feathers/compare/v4.3.1...v4.3.2) (2019-09-16) **Note:** Version bump only for package @feathersjs/errors - - - - ## [4.3.1](https://github.com/feathersjs/feathers/compare/v4.3.0...v4.3.1) (2019-09-09) **Note:** Version bump only for package @feathersjs/errors - - - - # [4.3.0](https://github.com/feathersjs/feathers/compare/v4.3.0-pre.4...v4.3.0) (2019-08-27) **Note:** Version bump only for package @feathersjs/errors - - - - # [4.3.0-pre.4](https://github.com/feathersjs/feathers/compare/v4.3.0-pre.3...v4.3.0-pre.4) (2019-08-22) **Note:** Version bump only for package @feathersjs/errors - - - - # [4.3.0-pre.3](https://github.com/feathersjs/feathers/compare/v4.3.0-pre.2...v4.3.0-pre.3) (2019-08-19) **Note:** Version bump only for package @feathersjs/errors - - - - # [4.3.0-pre.2](https://github.com/feathersjs/feathers/compare/v4.3.0-pre.1...v4.3.0-pre.2) (2019-08-02) **Note:** Version bump only for package @feathersjs/errors - - - - # [4.3.0-pre.1](https://github.com/feathersjs/feathers/compare/v4.0.0-pre.5...v4.3.0-pre.1) (2019-07-11) **Note:** Version bump only for package @feathersjs/errors - - - - # [4.0.0-pre.5](https://github.com/feathersjs/feathers/compare/v4.0.0-pre.4...v4.0.0-pre.5) (2019-07-10) **Note:** Version bump only for package @feathersjs/errors - - - - # [4.0.0-pre.4](https://github.com/feathersjs/feathers/compare/v4.0.0-pre.3...v4.0.0-pre.4) (2019-07-05) **Note:** Version bump only for package @feathersjs/errors - - - - # [4.0.0-pre.3](https://github.com/feathersjs/feathers/compare/v4.0.0-pre.2...v4.0.0-pre.3) (2019-06-01) - ### Bug Fixes -* Update dependencies and fix tests ([#1373](https://github.com/feathersjs/feathers/issues/1373)) ([d743a7f](https://github.com/feathersjs/feathers/commit/d743a7f)) - - - - +- Update dependencies and fix tests ([#1373](https://github.com/feathersjs/feathers/issues/1373)) ([d743a7f](https://github.com/feathersjs/feathers/commit/d743a7f)) # [4.0.0-pre.2](https://github.com/feathersjs/feathers/compare/v4.0.0-pre.1...v4.0.0-pre.2) (2019-05-15) - ### Bug Fixes -* Use `export =` in TypeScript definitions ([#1285](https://github.com/feathersjs/feathers/issues/1285)) ([12d0f4b](https://github.com/feathersjs/feathers/commit/12d0f4b)) - - - - +- Use `export =` in TypeScript definitions ([#1285](https://github.com/feathersjs/feathers/issues/1285)) ([12d0f4b](https://github.com/feathersjs/feathers/commit/12d0f4b)) # [4.0.0-pre.1](https://github.com/feathersjs/feathers/compare/v4.0.0-pre.0...v4.0.0-pre.1) (2019-05-08) - ### Bug Fixes -* Do not log as errors below a 500 response ([#1256](https://github.com/feathersjs/feathers/issues/1256)) ([33fd0e4](https://github.com/feathersjs/feathers/commit/33fd0e4)) - - - - +- Do not log as errors below a 500 response ([#1256](https://github.com/feathersjs/feathers/issues/1256)) ([33fd0e4](https://github.com/feathersjs/feathers/commit/33fd0e4)) # [4.0.0-pre.0](https://github.com/feathersjs/feathers/compare/v3.2.0-pre.1...v4.0.0-pre.0) (2019-04-21) - ### Bug Fixes -* Make Mocha a proper devDependency for every repository ([#1053](https://github.com/feathersjs/feathers/issues/1053)) ([9974803](https://github.com/feathersjs/feathers/commit/9974803)) -* Update 401.html ([#983](https://github.com/feathersjs/feathers/issues/983)) ([cec6bae](https://github.com/feathersjs/feathers/commit/cec6bae)) -* Update 404.html ([#984](https://github.com/feathersjs/feathers/issues/984)) ([72132d1](https://github.com/feathersjs/feathers/commit/72132d1)) -* Update adapter common tests ([#1135](https://github.com/feathersjs/feathers/issues/1135)) ([8166dda](https://github.com/feathersjs/feathers/commit/8166dda)) -* Update all dependencies to latest ([#1206](https://github.com/feathersjs/feathers/issues/1206)) ([e51e0f6](https://github.com/feathersjs/feathers/commit/e51e0f6)) -* **compile-task:** on windows machine ([#60](https://github.com/feathersjs/feathers/issues/60)) ([617e0a4](https://github.com/feathersjs/feathers/commit/617e0a4)) -* **package:** update debug to version 3.0.0 ([#86](https://github.com/feathersjs/feathers/issues/86)) ([fd1bb6b](https://github.com/feathersjs/feathers/commit/fd1bb6b)) - +- Make Mocha a proper devDependency for every repository ([#1053](https://github.com/feathersjs/feathers/issues/1053)) ([9974803](https://github.com/feathersjs/feathers/commit/9974803)) +- Update 401.html ([#983](https://github.com/feathersjs/feathers/issues/983)) ([cec6bae](https://github.com/feathersjs/feathers/commit/cec6bae)) +- Update 404.html ([#984](https://github.com/feathersjs/feathers/issues/984)) ([72132d1](https://github.com/feathersjs/feathers/commit/72132d1)) +- Update adapter common tests ([#1135](https://github.com/feathersjs/feathers/issues/1135)) ([8166dda](https://github.com/feathersjs/feathers/commit/8166dda)) +- Update all dependencies to latest ([#1206](https://github.com/feathersjs/feathers/issues/1206)) ([e51e0f6](https://github.com/feathersjs/feathers/commit/e51e0f6)) +- **compile-task:** on windows machine ([#60](https://github.com/feathersjs/feathers/issues/60)) ([617e0a4](https://github.com/feathersjs/feathers/commit/617e0a4)) +- **package:** update debug to version 3.0.0 ([#86](https://github.com/feathersjs/feathers/issues/86)) ([fd1bb6b](https://github.com/feathersjs/feathers/commit/fd1bb6b)) ### Features -* Add TypeScript definitions ([#1275](https://github.com/feathersjs/feathers/issues/1275)) ([9dd6713](https://github.com/feathersjs/feathers/commit/9dd6713)) -* Authentication v3 core server implementation ([#1205](https://github.com/feathersjs/feathers/issues/1205)) ([1bd7591](https://github.com/feathersjs/feathers/commit/1bd7591)) - - - - +- Add TypeScript definitions ([#1275](https://github.com/feathersjs/feathers/issues/1275)) ([9dd6713](https://github.com/feathersjs/feathers/commit/9dd6713)) +- Authentication v3 core server implementation ([#1205](https://github.com/feathersjs/feathers/issues/1205)) ([1bd7591](https://github.com/feathersjs/feathers/commit/1bd7591)) ## [3.3.6](https://github.com/feathersjs/feathers/compare/@feathersjs/errors@3.3.5...@feathersjs/errors@3.3.6) (2019-01-02) - ### Bug Fixes -* Update adapter common tests ([#1135](https://github.com/feathersjs/feathers/issues/1135)) ([8166dda](https://github.com/feathersjs/feathers/commit/8166dda)) - - - - +- Update adapter common tests ([#1135](https://github.com/feathersjs/feathers/issues/1135)) ([8166dda](https://github.com/feathersjs/feathers/commit/8166dda)) -## [3.3.5](https://github.com/feathersjs/feathers/compare/@feathersjs/errors@3.3.4...@feathersjs/errors@3.3.5) (2018-12-16) +## [3.3.5](https://github.com/feathersjs/feathers/compare/@feathersjs/errors@3.3.4...@feathersjs/errors@3.3.5) (2018-12-16) ### Bug Fixes -* Make Mocha a proper devDependency for every repository ([#1053](https://github.com/feathersjs/feathers/issues/1053)) ([9974803](https://github.com/feathersjs/feathers/commit/9974803)) - - - - +- Make Mocha a proper devDependency for every repository ([#1053](https://github.com/feathersjs/feathers/issues/1053)) ([9974803](https://github.com/feathersjs/feathers/commit/9974803)) + ## [3.3.4](https://github.com/feathersjs/feathers/compare/@feathersjs/errors@3.3.3...@feathersjs/errors@3.3.4) (2018-09-21) **Note:** Version bump only for package @feathersjs/errors - - - - -## [3.3.3](https://github.com/feathersjs/feathers/compare/@feathersjs/errors@3.3.2...@feathersjs/errors@3.3.3) (2018-09-17) +## [3.3.3](https://github.com/feathersjs/feathers/compare/@feathersjs/errors@3.3.2...@feathersjs/errors@3.3.3) (2018-09-17) ### Bug Fixes -* Update 401.html ([#983](https://github.com/feathersjs/feathers/issues/983)) ([cec6bae](https://github.com/feathersjs/feathers/commit/cec6bae)) -* Update 404.html ([#984](https://github.com/feathersjs/feathers/issues/984)) ([72132d1](https://github.com/feathersjs/feathers/commit/72132d1)) - - - - +- Update 401.html ([#983](https://github.com/feathersjs/feathers/issues/983)) ([cec6bae](https://github.com/feathersjs/feathers/commit/cec6bae)) +- Update 404.html ([#984](https://github.com/feathersjs/feathers/issues/984)) ([72132d1](https://github.com/feathersjs/feathers/commit/72132d1)) + ## [3.3.2](https://github.com/feathersjs/feathers/compare/@feathersjs/errors@3.3.1...@feathersjs/errors@3.3.2) (2018-09-02) **Note:** Version bump only for package @feathersjs/errors + ## 3.3.1 - Migrate to Monorepo ([feathers#462](https://github.com/feathersjs/feathers/issues/462)) ## [v3.3.0](https://github.com/feathersjs/errors/tree/v3.3.0) (2018-02-12) + [Full Changelog](https://github.com/feathersjs/errors/compare/v3.2.2...v3.3.0) **Closed issues:** @@ -517,6 +364,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Add req.url to notFound handler message [\#105](https://github.com/feathersjs/errors/pull/105) ([FreeLineTM](https://github.com/FreeLineTM)) ## [v3.2.2](https://github.com/feathersjs/errors/tree/v3.2.2) (2018-01-23) + [Full Changelog](https://github.com/feathersjs/errors/compare/v3.2.1...v3.2.2) **Closed issues:** @@ -532,6 +380,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - fix installation declaration [\#99](https://github.com/feathersjs/errors/pull/99) ([jasonmacgowan](https://github.com/jasonmacgowan)) ## [v3.2.1](https://github.com/feathersjs/errors/tree/v3.2.1) (2018-01-03) + [Full Changelog](https://github.com/feathersjs/errors/compare/v3.2.0...v3.2.1) **Closed issues:** @@ -540,10 +389,11 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline **Merged pull requests:** -- Update readme to correspond with latest release [\#98](https://github.com/feathersjs/errors/pull/98) ([daffl](https://github.com/daffl)) +- Update readme to correspond with latest release [\#98](https://github.com/feathersjs/errors/pull/98) ([daffl](https://github.com/daffl)) - Update semistandard to the latest version 🚀 [\#97](https://github.com/feathersjs/errors/pull/97) ([greenkeeper[bot]](https://github.com/apps/greenkeeper)) ## [v3.2.0](https://github.com/feathersjs/errors/tree/v3.2.0) (2017-11-19) + [Full Changelog](https://github.com/feathersjs/errors/compare/v3.1.0...v3.2.0) **Merged pull requests:** @@ -551,6 +401,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Allow ability to log middleware errors [\#95](https://github.com/feathersjs/errors/pull/95) ([daffl](https://github.com/daffl)) ## [v3.1.0](https://github.com/feathersjs/errors/tree/v3.1.0) (2017-11-18) + [Full Changelog](https://github.com/feathersjs/errors/compare/v3.0.0...v3.1.0) **Closed issues:** @@ -562,6 +413,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - 91 allow mixed config [\#94](https://github.com/feathersjs/errors/pull/94) ([DesignByOnyx](https://github.com/DesignByOnyx)) ## [v3.0.0](https://github.com/feathersjs/errors/tree/v3.0.0) (2017-11-01) + [Full Changelog](https://github.com/feathersjs/errors/compare/v3.0.0-pre.1...v3.0.0) **Merged pull requests:** @@ -569,6 +421,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Update to Buzzard infrastructure [\#93](https://github.com/feathersjs/errors/pull/93) ([daffl](https://github.com/daffl)) ## [v3.0.0-pre.1](https://github.com/feathersjs/errors/tree/v3.0.0-pre.1) (2017-10-21) + [Full Changelog](https://github.com/feathersjs/errors/compare/v2.9.2...v3.0.0-pre.1) **Closed issues:** @@ -582,6 +435,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Update sinon to the latest version 🚀 [\#89](https://github.com/feathersjs/errors/pull/89) ([greenkeeper[bot]](https://github.com/apps/greenkeeper)) ## [v2.9.2](https://github.com/feathersjs/errors/tree/v2.9.2) (2017-09-05) + [Full Changelog](https://github.com/feathersjs/errors/compare/v2.9.1...v2.9.2) **Closed issues:** @@ -595,6 +449,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Update sinon to the latest version 🚀 [\#84](https://github.com/feathersjs/errors/pull/84) ([greenkeeper[bot]](https://github.com/apps/greenkeeper)) ## [v2.9.1](https://github.com/feathersjs/errors/tree/v2.9.1) (2017-07-21) + [Full Changelog](https://github.com/feathersjs/errors/compare/v2.9.0...v2.9.1) **Merged pull requests:** @@ -602,6 +457,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Add back default error message [\#83](https://github.com/feathersjs/errors/pull/83) ([daffl](https://github.com/daffl)) ## [v2.9.0](https://github.com/feathersjs/errors/tree/v2.9.0) (2017-07-20) + [Full Changelog](https://github.com/feathersjs/errors/compare/v2.8.2...v2.9.0) **Closed issues:** @@ -614,6 +470,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Update chai to the latest version 🚀 [\#81](https://github.com/feathersjs/errors/pull/81) ([greenkeeper[bot]](https://github.com/apps/greenkeeper)) ## [v2.8.2](https://github.com/feathersjs/errors/tree/v2.8.2) (2017-07-05) + [Full Changelog](https://github.com/feathersjs/errors/compare/v2.8.1...v2.8.2) **Merged pull requests:** @@ -622,6 +479,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Add more information to error debug [\#79](https://github.com/feathersjs/errors/pull/79) ([kamzil](https://github.com/kamzil)) ## [v2.8.1](https://github.com/feathersjs/errors/tree/v2.8.1) (2017-05-30) + [Full Changelog](https://github.com/feathersjs/errors/compare/v2.8.0...v2.8.1) **Merged pull requests:** @@ -629,6 +487,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Fix errors property being lost when cloning [\#76](https://github.com/feathersjs/errors/pull/76) ([0x6431346e](https://github.com/0x6431346e)) ## [v2.8.0](https://github.com/feathersjs/errors/tree/v2.8.0) (2017-05-08) + [Full Changelog](https://github.com/feathersjs/errors/compare/v2.7.1...v2.8.0) **Closed issues:** @@ -640,6 +499,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Allow data to be an array [\#75](https://github.com/feathersjs/errors/pull/75) ([0x6431346e](https://github.com/0x6431346e)) ## [v2.7.1](https://github.com/feathersjs/errors/tree/v2.7.1) (2017-04-28) + [Full Changelog](https://github.com/feathersjs/errors/compare/v2.7.0...v2.7.1) **Closed issues:** @@ -651,6 +511,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Define property toJSON because just assigning it throws an error in N… [\#74](https://github.com/feathersjs/errors/pull/74) ([daffl](https://github.com/daffl)) ## [v2.7.0](https://github.com/feathersjs/errors/tree/v2.7.0) (2017-04-25) + [Full Changelog](https://github.com/feathersjs/errors/compare/v2.6.3...v2.7.0) **Merged pull requests:** @@ -660,6 +521,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Update dependencies to enable Greenkeeper 🌴 [\#71](https://github.com/feathersjs/errors/pull/71) ([greenkeeper[bot]](https://github.com/apps/greenkeeper)) ## [v2.6.3](https://github.com/feathersjs/errors/tree/v2.6.3) (2017-04-08) + [Full Changelog](https://github.com/feathersjs/errors/compare/v2.6.2...v2.6.3) **Closed issues:** @@ -671,6 +533,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - fix typescript definitions with noImplicitAny [\#69](https://github.com/feathersjs/errors/pull/69) ([JVirant](https://github.com/JVirant)) ## [v2.6.2](https://github.com/feathersjs/errors/tree/v2.6.2) (2017-03-16) + [Full Changelog](https://github.com/feathersjs/errors/compare/v2.6.1...v2.6.2) **Closed issues:** @@ -682,6 +545,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Fix declarations for index.d.ts [\#66](https://github.com/feathersjs/errors/pull/66) ([ghost](https://github.com/ghost)) ## [v2.6.1](https://github.com/feathersjs/errors/tree/v2.6.1) (2017-03-06) + [Full Changelog](https://github.com/feathersjs/errors/compare/v2.6.0...v2.6.1) **Merged pull requests:** @@ -689,6 +553,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - fix pull request \#62 [\#63](https://github.com/feathersjs/errors/pull/63) ([superbarne](https://github.com/superbarne)) ## [v2.6.0](https://github.com/feathersjs/errors/tree/v2.6.0) (2017-03-04) + [Full Changelog](https://github.com/feathersjs/errors/compare/v2.5.0...v2.6.0) **Closed issues:** @@ -702,6 +567,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Fix compile npm task on Windows [\#60](https://github.com/feathersjs/errors/pull/60) ([AbraaoAlves](https://github.com/AbraaoAlves)) ## [v2.5.0](https://github.com/feathersjs/errors/tree/v2.5.0) (2016-11-04) + [Full Changelog](https://github.com/feathersjs/errors/compare/v2.4.0...v2.5.0) **Closed issues:** @@ -717,6 +583,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Update mocha to version 3.0.0 🚀 [\#47](https://github.com/feathersjs/errors/pull/47) ([greenkeeperio-bot](https://github.com/greenkeeperio-bot)) ## [v2.4.0](https://github.com/feathersjs/errors/tree/v2.4.0) (2016-07-17) + [Full Changelog](https://github.com/feathersjs/errors/compare/v2.3.0...v2.4.0) **Merged pull requests:** @@ -724,6 +591,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - adding ability to get a feathers error by http status code [\#46](https://github.com/feathersjs/errors/pull/46) ([ekryski](https://github.com/ekryski)) ## [v2.3.0](https://github.com/feathersjs/errors/tree/v2.3.0) (2016-07-10) + [Full Changelog](https://github.com/feathersjs/errors/compare/v2.2.0...v2.3.0) **Closed issues:** @@ -735,6 +603,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Not found [\#45](https://github.com/feathersjs/errors/pull/45) ([ekryski](https://github.com/ekryski)) ## [v2.2.0](https://github.com/feathersjs/errors/tree/v2.2.0) (2016-05-27) + [Full Changelog](https://github.com/feathersjs/errors/compare/v2.1.0...v2.2.0) **Closed issues:** @@ -748,6 +617,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Update babel-plugin-add-module-exports to version 0.2.0 🚀 [\#41](https://github.com/feathersjs/errors/pull/41) ([greenkeeperio-bot](https://github.com/greenkeeperio-bot)) ## [v2.1.0](https://github.com/feathersjs/errors/tree/v2.1.0) (2016-04-03) + [Full Changelog](https://github.com/feathersjs/errors/compare/v2.0.2...v2.1.0) **Closed issues:** @@ -760,6 +630,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Update all dependencies 🌴 [\#34](https://github.com/feathersjs/errors/pull/34) ([greenkeeperio-bot](https://github.com/greenkeeperio-bot)) ## [v2.0.2](https://github.com/feathersjs/errors/tree/v2.0.2) (2016-03-23) + [Full Changelog](https://github.com/feathersjs/errors/compare/v2.0.1...v2.0.2) **Closed issues:** @@ -773,6 +644,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Fixed typo [\#30](https://github.com/feathersjs/errors/pull/30) ([kulakowka](https://github.com/kulakowka)) ## [v2.0.1](https://github.com/feathersjs/errors/tree/v2.0.1) (2016-02-24) + [Full Changelog](https://github.com/feathersjs/errors/compare/v2.0.0...v2.0.1) **Closed issues:** @@ -784,6 +656,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - adding an explicit error type [\#28](https://github.com/feathersjs/errors/pull/28) ([ekryski](https://github.com/ekryski)) ## [v2.0.0](https://github.com/feathersjs/errors/tree/v2.0.0) (2016-02-24) + [Full Changelog](https://github.com/feathersjs/errors/compare/v1.2.4...v2.0.0) **Merged pull requests:** @@ -791,9 +664,11 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - move error handler out of index [\#26](https://github.com/feathersjs/errors/pull/26) ([ekryski](https://github.com/ekryski)) ## [v1.2.4](https://github.com/feathersjs/errors/tree/v1.2.4) (2016-02-24) + [Full Changelog](https://github.com/feathersjs/errors/compare/v1.2.3...v1.2.4) ## [v1.2.3](https://github.com/feathersjs/errors/tree/v1.2.3) (2016-02-21) + [Full Changelog](https://github.com/feathersjs/errors/compare/v1.2.2...v1.2.3) **Merged pull requests:** @@ -801,6 +676,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Adding default error page and make HTML formatting optional [\#25](https://github.com/feathersjs/errors/pull/25) ([daffl](https://github.com/daffl)) ## [v1.2.2](https://github.com/feathersjs/errors/tree/v1.2.2) (2016-02-18) + [Full Changelog](https://github.com/feathersjs/errors/compare/v1.2.1...v1.2.2) **Closed issues:** @@ -812,9 +688,11 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Make fully CommonJS compatible and add error middleware tests [\#23](https://github.com/feathersjs/errors/pull/23) ([daffl](https://github.com/daffl)) ## [v1.2.1](https://github.com/feathersjs/errors/tree/v1.2.1) (2016-02-16) + [Full Changelog](https://github.com/feathersjs/errors/compare/v1.2.0...v1.2.1) ## [v1.2.0](https://github.com/feathersjs/errors/tree/v1.2.0) (2016-02-15) + [Full Changelog](https://github.com/feathersjs/errors/compare/v1.1.6...v1.2.0) **Closed issues:** @@ -826,18 +704,21 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - adding error handler back [\#22](https://github.com/feathersjs/errors/pull/22) ([ekryski](https://github.com/ekryski)) ## [v1.1.6](https://github.com/feathersjs/errors/tree/v1.1.6) (2016-01-12) + [Full Changelog](https://github.com/feathersjs/errors/compare/v1.1.5...v1.1.6) **Closed issues:** - stacktraces are incorrect when used in an ES6 app [\#20](https://github.com/feathersjs/errors/issues/20) - We shouldn't mutate the error object passed in. [\#19](https://github.com/feathersjs/errors/issues/19) -- only one instance of babel-polyfill is allowed [\#17](https://github.com/feathersjs/errors/issues/17) +- only one instance of babel-polyfill is allowed [\#17](https://github.com/feathersjs/errors/issues/17) ## [v1.1.5](https://github.com/feathersjs/errors/tree/v1.1.5) (2015-12-18) + [Full Changelog](https://github.com/feathersjs/errors/compare/v1.1.4...v1.1.5) ## [v1.1.4](https://github.com/feathersjs/errors/tree/v1.1.4) (2015-12-15) + [Full Changelog](https://github.com/feathersjs/errors/compare/v1.1.3...v1.1.4) **Closed issues:** @@ -845,9 +726,11 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - no method 'setPrototypeOf' in Node 0.10 [\#16](https://github.com/feathersjs/errors/issues/16) ## [v1.1.3](https://github.com/feathersjs/errors/tree/v1.1.3) (2015-12-15) + [Full Changelog](https://github.com/feathersjs/errors/compare/v1.1.2...v1.1.3) ## [v1.1.2](https://github.com/feathersjs/errors/tree/v1.1.2) (2015-12-15) + [Full Changelog](https://github.com/feathersjs/errors/compare/v1.1.1...v1.1.2) **Closed issues:** @@ -855,6 +738,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Passing errors as second argument [\#9](https://github.com/feathersjs/errors/issues/9) ## [v1.1.1](https://github.com/feathersjs/errors/tree/v1.1.1) (2015-12-14) + [Full Changelog](https://github.com/feathersjs/errors/compare/v1.1.0...v1.1.1) **Closed issues:** @@ -866,9 +750,11 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Es6 class fix [\#15](https://github.com/feathersjs/errors/pull/15) ([ekryski](https://github.com/ekryski)) ## [v1.1.0](https://github.com/feathersjs/errors/tree/v1.1.0) (2015-12-12) + [Full Changelog](https://github.com/feathersjs/errors/compare/v1.0.0...v1.1.0) ## [v1.0.0](https://github.com/feathersjs/errors/tree/v1.0.0) (2015-12-12) + [Full Changelog](https://github.com/feathersjs/errors/compare/0.2.5...v1.0.0) **Closed issues:** @@ -883,21 +769,27 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - complete rewrite. Closes \#11 and \#12. [\#13](https://github.com/feathersjs/errors/pull/13) ([ekryski](https://github.com/ekryski)) ## [0.2.5](https://github.com/feathersjs/errors/tree/0.2.5) (2015-02-05) + [Full Changelog](https://github.com/feathersjs/errors/compare/0.2.4...0.2.5) ## [0.2.4](https://github.com/feathersjs/errors/tree/0.2.4) (2015-02-05) + [Full Changelog](https://github.com/feathersjs/errors/compare/0.2.3...0.2.4) ## [0.2.3](https://github.com/feathersjs/errors/tree/0.2.3) (2015-01-29) + [Full Changelog](https://github.com/feathersjs/errors/compare/0.2.2...0.2.3) ## [0.2.2](https://github.com/feathersjs/errors/tree/0.2.2) (2015-01-29) + [Full Changelog](https://github.com/feathersjs/errors/compare/0.2.1...0.2.2) ## [0.2.1](https://github.com/feathersjs/errors/tree/0.2.1) (2014-09-03) + [Full Changelog](https://github.com/feathersjs/errors/compare/0.2.0...0.2.1) ## [0.2.0](https://github.com/feathersjs/errors/tree/0.2.0) (2014-07-17) + [Full Changelog](https://github.com/feathersjs/errors/compare/0.1.7...0.2.0) **Implemented enhancements:** @@ -905,15 +797,19 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Handle error objects with an 'errors' object [\#5](https://github.com/feathersjs/errors/issues/5) ## [0.1.7](https://github.com/feathersjs/errors/tree/0.1.7) (2014-07-06) + [Full Changelog](https://github.com/feathersjs/errors/compare/0.1.6...0.1.7) ## [0.1.6](https://github.com/feathersjs/errors/tree/0.1.6) (2014-07-05) + [Full Changelog](https://github.com/feathersjs/errors/compare/0.1.5...0.1.6) ## [0.1.5](https://github.com/feathersjs/errors/tree/0.1.5) (2014-06-13) + [Full Changelog](https://github.com/feathersjs/errors/compare/0.1.4...0.1.5) ## [0.1.4](https://github.com/feathersjs/errors/tree/0.1.4) (2014-06-13) + [Full Changelog](https://github.com/feathersjs/errors/compare/0.1.3...0.1.4) **Closed issues:** @@ -925,6 +821,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Core compatible [\#4](https://github.com/feathersjs/errors/pull/4) ([ekryski](https://github.com/ekryski)) ## [0.1.3](https://github.com/feathersjs/errors/tree/0.1.3) (2014-06-09) + [Full Changelog](https://github.com/feathersjs/errors/compare/0.1.2...0.1.3) **Merged pull requests:** @@ -932,12 +829,13 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Adding a default error page [\#3](https://github.com/feathersjs/errors/pull/3) ([ekryski](https://github.com/ekryski)) ## [0.1.2](https://github.com/feathersjs/errors/tree/0.1.2) (2014-06-05) + [Full Changelog](https://github.com/feathersjs/errors/compare/0.1.1...0.1.2) ## [0.1.1](https://github.com/feathersjs/errors/tree/0.1.1) (2014-06-04) + [Full Changelog](https://github.com/feathersjs/errors/compare/v0.1.0...0.1.1) ## [v0.1.0](https://github.com/feathersjs/errors/tree/v0.1.0) (2014-06-04) - -\* *This Change Log was automatically generated by [github_changelog_generator](https://github.com/skywinder/Github-Changelog-Generator)* +\* _This Change Log was automatically generated by [github_changelog_generator](https://github.com/skywinder/Github-Changelog-Generator)_ diff --git a/packages/errors/LICENSE b/packages/errors/LICENSE index 3f395cc665..59604f46f3 100644 --- a/packages/errors/LICENSE +++ b/packages/errors/LICENSE @@ -1,6 +1,6 @@ The MIT License (MIT) -Copyright (c) 2021 Feathers +Copyright (c) 2022 Feathers Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated documentation files (the "Software"), to deal diff --git a/packages/errors/README.md b/packages/errors/README.md index da59712dd5..9092d9a033 100644 --- a/packages/errors/README.md +++ b/packages/errors/README.md @@ -1,8 +1,8 @@ # @feathersjs/errors [![CI](https://github.com/feathersjs/feathers/workflows/CI/badge.svg)](https://github.com/feathersjs/feathers/actions?query=workflow%3ACI) -[![Dependency Status](https://img.shields.io/david/feathersjs/feathers.svg?style=flat-square&path=packages/errors)](https://david-dm.org/feathersjs/feathers?path=packages/errors) [![Download Status](https://img.shields.io/npm/dm/@feathersjs/errors.svg?style=flat-square)](https://www.npmjs.com/package/@feathersjs/errors) +[![Discord](https://badgen.net/badge/icon/discord?icon=discord&label)](https://discord.gg/qa8kez8QBx) > Common error types for feathers apps @@ -18,6 +18,6 @@ Refer to the [Feathers errors API documentation](https://docs.feathersjs.com/api ## License -Copyright (c) 2021 [Feathers contributors](https://github.com/feathersjs/feathers/graphs/contributors) +Copyright (c) 2022 [Feathers contributors](https://github.com/feathersjs/feathers/graphs/contributors) Licensed under the [MIT license](LICENSE). diff --git a/packages/errors/package.json b/packages/errors/package.json index a68c7c8515..6dd84a8739 100644 --- a/packages/errors/package.json +++ b/packages/errors/package.json @@ -1,7 +1,7 @@ { "name": "@feathersjs/errors", "description": "Common error types for Feathers apps", - "version": "5.0.0-pre.16", + "version": "5.0.0-pre.31", "homepage": "https://feathersjs.com", "main": "lib/", "types": "lib/", @@ -12,7 +12,8 @@ "license": "MIT", "repository": { "type": "git", - "url": "git://github.com/feathersjs/feathers.git" + "url": "git://github.com/feathersjs/feathers.git", + "directory": "packages/errors" }, "author": { "name": "Feathers contributors", @@ -31,7 +32,8 @@ }, "scripts": { "prepublish": "npm run compile", - "compile": "shx rm -rf lib/ && tsc", + "pack": "npm pack --pack-destination ../cli/test/build", + "compile": "shx rm -rf lib/ && tsc && npm run pack", "test": "mocha --config ../../.mocharc.json --recursive test/**.test.ts test/**/*.test.ts" }, "publishConfig": { @@ -47,13 +49,13 @@ "*.js" ], "devDependencies": { - "@feathersjs/feathers": "^5.0.0-pre.16", - "@types/mocha": "^9.0.0", - "@types/node": "^17.0.5", - "mocha": "^9.1.3", - "shx": "^0.3.3", - "ts-node": "^10.4.0", - "typescript": "^4.5.4" - }, - "gitHead": "f0cd227a82d159b528193bd33747c97684a48773" + "@feathersjs/feathers": "^5.0.0-pre.31", + "@types/mocha": "^10.0.0", + "@types/node": "^18.8.2", + "mocha": "^10.0.0", + "shx": "^0.3.4", + "ts-node": "^10.9.1", + "typescript": "^4.8.4" + }, + "gitHead": "4500dbeb8cea566678cf88b3313a88efd93a2ed9" } diff --git a/packages/errors/src/index.ts b/packages/errors/src/index.ts index 25c692bcf3..cca8761fd3 100644 --- a/packages/errors/src/index.ts +++ b/packages/errors/src/index.ts @@ -1,221 +1,221 @@ export interface FeathersErrorJSON { - name: string; - message: string; - code: number; - className: string; - data?: any; - errors?: any; + name: string + message: string + code: number + className: string + data?: any + errors?: any } -export type DynamicError = Error & { [key: string]: any }; -export type ErrorMessage = string | DynamicError | { [key: string]: any } | any[]; +export type DynamicError = Error & { [key: string]: any } +export type ErrorMessage = null | string | DynamicError | { [key: string]: any } | any[] interface ErrorProperties extends Omit { - type: string; + type: string } export class FeathersError extends Error { - readonly type: string; - readonly code: number; - readonly className: string; - readonly data: any; - readonly errors: any; - - constructor (err: ErrorMessage, name: string, code: number, className: string, _data: any) { - let msg = typeof err === 'string' ? err : 'Error'; + readonly type: string + readonly code: number + readonly className: string + readonly data: any + readonly errors: any + + constructor(err: ErrorMessage, name: string, code: number, className: string, _data: any) { + let msg = typeof err === 'string' ? err : 'Error' const properties: ErrorProperties = { name, code, className, type: 'FeathersError' - }; + } if (Array.isArray(_data)) { - properties.data = _data; + properties.data = _data } else if (typeof err === 'object' || _data !== undefined) { - const { message, errors, ...rest } = typeof err === 'object' ? err : _data; + const { message, errors, ...rest } = err !== null && typeof err === 'object' ? err : _data - msg = message || msg; - properties.errors = errors; - properties.data = rest; + msg = message || msg + properties.errors = errors + properties.data = rest } - super(msg); - Object.assign(this, properties); + super(msg) + Object.assign(this, properties) } - toJSON () { + toJSON() { const result: FeathersErrorJSON = { name: this.name, message: this.message, code: this.code, className: this.className - }; + } if (this.data !== undefined) { - result.data = this.data; + result.data = this.data } if (this.errors !== undefined) { - result.errors = this.errors; + result.errors = this.errors } - return result; + return result } } export class BadRequest extends FeathersError { - constructor (message?: ErrorMessage, data?: any) { - super(message, 'BadRequest', 400, 'bad-request', data); + constructor(message?: ErrorMessage, data?: any) { + super(message, 'BadRequest', 400, 'bad-request', data) } } // 401 - Not Authenticated -export class NotAuthenticated extends FeathersError{ - constructor (message?: ErrorMessage, data?: any) { - super(message, 'NotAuthenticated', 401, 'not-authenticated', data); +export class NotAuthenticated extends FeathersError { + constructor(message?: ErrorMessage, data?: any) { + super(message, 'NotAuthenticated', 401, 'not-authenticated', data) } } // 402 - Payment Error export class PaymentError extends FeathersError { - constructor (message?: ErrorMessage, data?: any) { - super(message, 'PaymentError', 402, 'payment-error', data); + constructor(message?: ErrorMessage, data?: any) { + super(message, 'PaymentError', 402, 'payment-error', data) } } // 403 - Forbidden export class Forbidden extends FeathersError { - constructor (message?: ErrorMessage, data?: any) { - super(message, 'Forbidden', 403, 'forbidden', data); + constructor(message?: ErrorMessage, data?: any) { + super(message, 'Forbidden', 403, 'forbidden', data) } } // 404 - Not Found export class NotFound extends FeathersError { - constructor (message?: ErrorMessage, data?: any) { - super(message, 'NotFound', 404, 'not-found', data); + constructor(message?: ErrorMessage, data?: any) { + super(message, 'NotFound', 404, 'not-found', data) } } // 405 - Method Not Allowed export class MethodNotAllowed extends FeathersError { - constructor (message?: ErrorMessage, data?: any) { - super(message, 'MethodNotAllowed', 405, 'method-not-allowed', data); + constructor(message?: ErrorMessage, data?: any) { + super(message, 'MethodNotAllowed', 405, 'method-not-allowed', data) } } // 406 - Not Acceptable export class NotAcceptable extends FeathersError { - constructor (message?: ErrorMessage, data?: any) { - super(message, 'NotAcceptable', 406, 'not-acceptable', data); + constructor(message?: ErrorMessage, data?: any) { + super(message, 'NotAcceptable', 406, 'not-acceptable', data) } } // 408 - Timeout export class Timeout extends FeathersError { - constructor (message?: ErrorMessage, data?: any) { - super(message, 'Timeout', 408, 'timeout', data); + constructor(message?: ErrorMessage, data?: any) { + super(message, 'Timeout', 408, 'timeout', data) } } // 409 - Conflict export class Conflict extends FeathersError { - constructor (message?: ErrorMessage, data?: any) { - super(message, 'Conflict', 409, 'conflict', data); + constructor(message?: ErrorMessage, data?: any) { + super(message, 'Conflict', 409, 'conflict', data) } } // 410 - Gone export class Gone extends FeathersError { - constructor (message?: ErrorMessage, data?: any) { - super(message, 'Gone', 410, 'gone', data); + constructor(message?: ErrorMessage, data?: any) { + super(message, 'Gone', 410, 'gone', data) } } // 411 - Length Required export class LengthRequired extends FeathersError { - constructor (message?: ErrorMessage, data?: any) { - super(message, 'LengthRequired', 411, 'length-required', data); + constructor(message?: ErrorMessage, data?: any) { + super(message, 'LengthRequired', 411, 'length-required', data) } } // 422 Unprocessable export class Unprocessable extends FeathersError { - constructor (message?: ErrorMessage, data?: any) { - super(message, 'Unprocessable', 422, 'unprocessable', data); + constructor(message?: ErrorMessage, data?: any) { + super(message, 'Unprocessable', 422, 'unprocessable', data) } } // 429 Too Many Requests export class TooManyRequests extends FeathersError { - constructor (message?: ErrorMessage, data?: any) { - super(message, 'TooManyRequests', 429, 'too-many-requests', data); + constructor(message?: ErrorMessage, data?: any) { + super(message, 'TooManyRequests', 429, 'too-many-requests', data) } } // 500 - General Error export class GeneralError extends FeathersError { - constructor (message?: ErrorMessage, data?: any) { - super(message, 'GeneralError', 500, 'general-error', data); + constructor(message?: ErrorMessage, data?: any) { + super(message, 'GeneralError', 500, 'general-error', data) } } // 501 - Not Implemented export class NotImplemented extends FeathersError { - constructor (message?: ErrorMessage, data?: any) { - super(message, 'NotImplemented', 501, 'not-implemented', data); + constructor(message?: ErrorMessage, data?: any) { + super(message, 'NotImplemented', 501, 'not-implemented', data) } } // 502 - Bad Gateway export class BadGateway extends FeathersError { - constructor (message?: ErrorMessage, data?: any) { - super(message, 'BadGateway', 502, 'bad-gateway', data); + constructor(message?: ErrorMessage, data?: any) { + super(message, 'BadGateway', 502, 'bad-gateway', data) } } // 503 - Unavailable export class Unavailable extends FeathersError { - constructor (message?: ErrorMessage, data?: any) { - super(message, 'Unavailable', 503, 'unavailable', data); + constructor(message?: ErrorMessage, data?: any) { + super(message, 'Unavailable', 503, 'unavailable', data) } } export interface Errors { - FeathersError: FeathersError; - BadRequest: BadRequest; - NotAuthenticated: NotAuthenticated; - PaymentError: PaymentError; - Forbidden: Forbidden; - NotFound: NotFound; - MethodNotAllowed: MethodNotAllowed; - NotAcceptable: NotAcceptable; - Timeout: Timeout; - Conflict: Conflict; - LengthRequired: LengthRequired; - Unprocessable: Unprocessable; - TooManyRequests: TooManyRequests; - GeneralError: GeneralError; - NotImplemented: NotImplemented; - BadGateway: BadGateway; - Unavailable: Unavailable; - 400: BadRequest; - 401: NotAuthenticated; - 402: PaymentError; - 403: Forbidden; - 404: NotFound; - 405: MethodNotAllowed; - 406: NotAcceptable; - 408: Timeout; - 409: Conflict; - 411: LengthRequired; - 422: Unprocessable; - 429: TooManyRequests; - 500: GeneralError; - 501: NotImplemented; - 502: BadGateway; - 503: Unavailable; + FeathersError: FeathersError + BadRequest: BadRequest + NotAuthenticated: NotAuthenticated + PaymentError: PaymentError + Forbidden: Forbidden + NotFound: NotFound + MethodNotAllowed: MethodNotAllowed + NotAcceptable: NotAcceptable + Timeout: Timeout + Conflict: Conflict + LengthRequired: LengthRequired + Unprocessable: Unprocessable + TooManyRequests: TooManyRequests + GeneralError: GeneralError + NotImplemented: NotImplemented + BadGateway: BadGateway + Unavailable: Unavailable + 400: BadRequest + 401: NotAuthenticated + 402: PaymentError + 403: Forbidden + 404: NotFound + 405: MethodNotAllowed + 406: NotAcceptable + 408: Timeout + 409: Conflict + 411: LengthRequired + 422: Unprocessable + 429: TooManyRequests + 500: GeneralError + 501: NotImplemented + 502: BadGateway + 503: Unavailable } export const errors = { @@ -255,19 +255,19 @@ export const errors = { 503: Unavailable } -export function convert (error: any) { +export function convert(error: any) { if (!error) { - return error; + return error } - const FeathersError = (errors as any)[error.name]; + const FeathersError = (errors as any)[error.name] const result = FeathersError ? new FeathersError(error.message, error.data) - : new Error(error.message || error); + : new Error(error.message || error) if (typeof error === 'object') { - Object.assign(result, error); + Object.assign(result, error) } - return result; + return result } diff --git a/packages/errors/test/index.test.ts b/packages/errors/test/index.test.ts index aa24871280..e4a0263108 100644 --- a/packages/errors/test/index.test.ts +++ b/packages/errors/test/index.test.ts @@ -1,7 +1,7 @@ -import assert from 'assert'; -import * as errors from '../src'; +import assert from 'assert' +import * as errors from '../src' -const { convert } = errors; +const { convert } = errors describe('@feathersjs/errors', () => { describe('errors.convert', () => { @@ -10,221 +10,219 @@ describe('@feathersjs/errors', () => { name: 'BadRequest', message: 'Hi', expando: 'Me' - }); + }) - assert.strictEqual(error.message, 'Hi'); - assert.strictEqual(error.expando, 'Me'); - assert.ok(error instanceof errors.BadRequest); - }); + assert.strictEqual(error.message, 'Hi') + assert.strictEqual(error.expando, 'Me') + assert.ok(error instanceof errors.BadRequest) + }) it('converts other object to error', () => { let error = convert({ message: 'Something went wrong' - }); + }) - assert.ok(error instanceof Error); - assert.strictEqual(error.message, 'Something went wrong'); + assert.ok(error instanceof Error) + assert.strictEqual(error.message, 'Something went wrong') - error = convert('Something went wrong'); + error = convert('Something went wrong') - assert.ok(error instanceof Error); - assert.strictEqual(error.message, 'Something went wrong'); - }); + assert.ok(error instanceof Error) + assert.strictEqual(error.message, 'Something went wrong') + }) - it('converts nothing', () => - assert.strictEqual(convert(null), null) - ); - }); + it('converts nothing', () => assert.strictEqual(convert(null), null)) + }) describe('error types', () => { it('Bad Request', () => { - assert.notStrictEqual(typeof errors.BadRequest, 'undefined', 'has BadRequest'); - }); + assert.notStrictEqual(typeof errors.BadRequest, 'undefined', 'has BadRequest') + }) it('Not Authenticated', () => { - assert.notStrictEqual(typeof errors.NotAuthenticated, 'undefined', 'has NotAuthenticated'); - }); + assert.notStrictEqual(typeof errors.NotAuthenticated, 'undefined', 'has NotAuthenticated') + }) it('Payment Error', () => { - assert.notStrictEqual(typeof errors.PaymentError, 'undefined', 'has PaymentError'); - }); + assert.notStrictEqual(typeof errors.PaymentError, 'undefined', 'has PaymentError') + }) it('Forbidden', () => { - assert.notStrictEqual(typeof errors.Forbidden, 'undefined', 'has Forbidden'); - }); + assert.notStrictEqual(typeof errors.Forbidden, 'undefined', 'has Forbidden') + }) it('Not Found', () => { - assert.notStrictEqual(typeof errors.NotFound, 'undefined', 'has NotFound'); - }); + assert.notStrictEqual(typeof errors.NotFound, 'undefined', 'has NotFound') + }) it('Method Not Allowed', () => { - assert.notStrictEqual(typeof errors.MethodNotAllowed, 'undefined', 'has MethodNotAllowed'); - }); + assert.notStrictEqual(typeof errors.MethodNotAllowed, 'undefined', 'has MethodNotAllowed') + }) it('Not Acceptable', () => { - assert.notStrictEqual(typeof errors.NotAcceptable, 'undefined', 'has NotAcceptable'); - }); + assert.notStrictEqual(typeof errors.NotAcceptable, 'undefined', 'has NotAcceptable') + }) it('Timeout', () => { - assert.notStrictEqual(typeof errors.Timeout, 'undefined', 'has Timeout'); - }); + assert.notStrictEqual(typeof errors.Timeout, 'undefined', 'has Timeout') + }) it('Conflict', () => { - assert.notStrictEqual(typeof errors.Conflict, 'undefined', 'has Conflict'); - }); + assert.notStrictEqual(typeof errors.Conflict, 'undefined', 'has Conflict') + }) it('Gone', () => { - assert.notStrictEqual(typeof errors.Gone, 'undefined', 'has Gone'); - }); + assert.notStrictEqual(typeof errors.Gone, 'undefined', 'has Gone') + }) it('Length Required', () => { - assert.notStrictEqual(typeof errors.LengthRequired, 'undefined', 'has LengthRequired'); - }); + assert.notStrictEqual(typeof errors.LengthRequired, 'undefined', 'has LengthRequired') + }) it('Unprocessable', () => { - assert.notStrictEqual(typeof errors.Unprocessable, 'undefined', 'has Unprocessable'); - }); + assert.notStrictEqual(typeof errors.Unprocessable, 'undefined', 'has Unprocessable') + }) it('Too Many Requests', () => { - assert.notStrictEqual(typeof errors.TooManyRequests, 'undefined', 'has TooManyRequests'); - }); + assert.notStrictEqual(typeof errors.TooManyRequests, 'undefined', 'has TooManyRequests') + }) it('General Error', () => { - assert.notStrictEqual(typeof errors.GeneralError, 'undefined', 'has GeneralError'); - }); + assert.notStrictEqual(typeof errors.GeneralError, 'undefined', 'has GeneralError') + }) it('Not Implemented', () => { - assert.notStrictEqual(typeof errors.NotImplemented, 'undefined', 'has NotImplemented'); - }); + assert.notStrictEqual(typeof errors.NotImplemented, 'undefined', 'has NotImplemented') + }) it('Bad Gateway', () => { - assert.notStrictEqual(typeof errors.BadGateway, 'undefined', 'has BadGateway'); - }); + assert.notStrictEqual(typeof errors.BadGateway, 'undefined', 'has BadGateway') + }) it('Unavailable', () => { - assert.notStrictEqual(typeof errors.Unavailable, 'undefined', 'has Unavailable'); - }); + assert.notStrictEqual(typeof errors.Unavailable, 'undefined', 'has Unavailable') + }) it('400', () => { - assert.notStrictEqual(typeof errors.errors[400], 'undefined', 'has BadRequest alias'); - }); + assert.notStrictEqual(typeof errors.errors[400], 'undefined', 'has BadRequest alias') + }) it('401', () => { - assert.notStrictEqual(typeof errors.errors[401], 'undefined', 'has NotAuthenticated alias'); - }); + assert.notStrictEqual(typeof errors.errors[401], 'undefined', 'has NotAuthenticated alias') + }) it('402', () => { - assert.notStrictEqual(typeof errors.errors[402], 'undefined', 'has PaymentError alias'); - }); + assert.notStrictEqual(typeof errors.errors[402], 'undefined', 'has PaymentError alias') + }) it('403', () => { - assert.notStrictEqual(typeof errors.errors[403], 'undefined', 'has Forbidden alias'); - }); + assert.notStrictEqual(typeof errors.errors[403], 'undefined', 'has Forbidden alias') + }) it('404', () => { - assert.notStrictEqual(typeof errors.errors[404], 'undefined', 'has NotFound alias'); - }); + assert.notStrictEqual(typeof errors.errors[404], 'undefined', 'has NotFound alias') + }) it('405', () => { - assert.notStrictEqual(typeof errors.errors[405], 'undefined', 'has MethodNotAllowed alias'); - }); + assert.notStrictEqual(typeof errors.errors[405], 'undefined', 'has MethodNotAllowed alias') + }) it('406', () => { - assert.notStrictEqual(typeof errors.errors[406], 'undefined', 'has NotAcceptable alias'); - }); + assert.notStrictEqual(typeof errors.errors[406], 'undefined', 'has NotAcceptable alias') + }) it('408', () => { - assert.notStrictEqual(typeof errors.errors[408], 'undefined', 'has Timeout alias'); - }); + assert.notStrictEqual(typeof errors.errors[408], 'undefined', 'has Timeout alias') + }) it('409', () => { - assert.notStrictEqual(typeof errors.errors[409], 'undefined', 'has Conflict alias'); - }); + assert.notStrictEqual(typeof errors.errors[409], 'undefined', 'has Conflict alias') + }) it('410', () => { - assert.notStrictEqual(typeof errors.errors[410], 'undefined', 'has Gone alias'); - }); + assert.notStrictEqual(typeof errors.errors[410], 'undefined', 'has Gone alias') + }) it('411', () => { - assert.notStrictEqual(typeof errors.errors[411], 'undefined', 'has LengthRequired alias'); - }); + assert.notStrictEqual(typeof errors.errors[411], 'undefined', 'has LengthRequired alias') + }) it('422', () => { - assert.notStrictEqual(typeof errors.errors[422], 'undefined', 'has Unprocessable alias'); - }); + assert.notStrictEqual(typeof errors.errors[422], 'undefined', 'has Unprocessable alias') + }) it('429', () => { - assert.notStrictEqual(typeof errors.errors[429], 'undefined', 'has TooManyRequests alias'); - }); + assert.notStrictEqual(typeof errors.errors[429], 'undefined', 'has TooManyRequests alias') + }) it('500', () => { - assert.notStrictEqual(typeof errors.errors[500], 'undefined', 'has GeneralError alias'); - }); + assert.notStrictEqual(typeof errors.errors[500], 'undefined', 'has GeneralError alias') + }) it('501', () => { - assert.notStrictEqual(typeof errors.errors[501], 'undefined', 'has NotImplemented alias'); - }); + assert.notStrictEqual(typeof errors.errors[501], 'undefined', 'has NotImplemented alias') + }) it('502', () => { - assert.notStrictEqual(typeof errors.errors[502], 'undefined', 'has BadGateway alias'); - }); + assert.notStrictEqual(typeof errors.errors[502], 'undefined', 'has BadGateway alias') + }) it('503', () => { - assert.notStrictEqual(typeof errors.errors[503], 'undefined', 'has Unavailable alias'); - }); + assert.notStrictEqual(typeof errors.errors[503], 'undefined', 'has Unavailable alias') + }) it('instantiates every error', () => { - const index: any = errors.errors; + const index: any = errors.errors - Object.keys(index).forEach(name => { - const E = index[name]; + Object.keys(index).forEach((name) => { + const E = index[name] if (E) { // tslint:disable-next-line - new E('Something went wrong'); + new E('Something went wrong') } - }); - }); - }); + }) + }) + }) describe('inheritance', () => { it('instanceof differentiates between error types', () => { - const error = new errors.MethodNotAllowed(); - assert.ok(!(error instanceof errors.BadRequest)); - }); + const error = new errors.MethodNotAllowed() + assert.ok(!(error instanceof errors.BadRequest)) + }) it('follows the prototypical inheritance chain', () => { - const error = new errors.MethodNotAllowed(); - assert.ok(error instanceof Error); - assert.ok(error instanceof errors.FeathersError); - }); + const error = new errors.MethodNotAllowed() + assert.ok(error instanceof Error) + assert.ok(error instanceof errors.FeathersError) + }) it('has the correct constructors', () => { - const error = new errors.NotFound(); - assert.ok(error.constructor === errors.NotFound); - assert.ok(error.constructor.name === 'NotFound'); - }); - }); + const error = new errors.NotFound() + assert.ok(error.constructor === errors.NotFound) + assert.ok(error.constructor.name === 'NotFound') + }) + }) describe('successful error creation', () => { describe('without custom message', () => { it('default error', () => { - const error = new errors.GeneralError(); - assert.strictEqual(error.code, 500); - assert.strictEqual(error.className, 'general-error'); - assert.strictEqual(error.message, 'Error'); - assert.strictEqual(error.data, undefined); - assert.strictEqual(error.errors, undefined); - assert.notStrictEqual(error.stack, undefined); - assert.strictEqual(error instanceof errors.GeneralError, true); - assert.strictEqual(error instanceof errors.FeathersError, true); - }); + const error = new errors.GeneralError() + assert.strictEqual(error.code, 500) + assert.strictEqual(error.className, 'general-error') + assert.strictEqual(error.message, 'Error') + assert.strictEqual(error.data, undefined) + assert.strictEqual(error.errors, undefined) + assert.notStrictEqual(error.stack, undefined) + assert.strictEqual(error instanceof errors.GeneralError, true) + assert.strictEqual(error instanceof errors.FeathersError, true) + }) it('can wrap an existing error', () => { - const error = new errors.BadRequest(new Error()); - assert.strictEqual(error.code, 400); - assert.strictEqual(error.message, 'Error'); - }); + const error = new errors.BadRequest(new Error()) + assert.strictEqual(error.code, 400) + assert.strictEqual(error.message, 'Error') + }) it('with multiple errors', () => { const data = { @@ -233,52 +231,55 @@ describe('@feathersjs/errors', () => { password: 'Invalid Password' }, foo: 'bar' - }; + } - const error = new errors.BadRequest(data); - assert.strictEqual(error.code, 400); - assert.strictEqual(error.message, 'Error'); - assert.deepStrictEqual(error.errors, { email: 'Email Taken', password: 'Invalid Password' }); - assert.deepStrictEqual(error.data, { foo: 'bar' }); - }); + const error = new errors.BadRequest(data) + assert.strictEqual(error.code, 400) + assert.strictEqual(error.message, 'Error') + assert.deepStrictEqual(error.errors, { + email: 'Email Taken', + password: 'Invalid Password' + }) + assert.deepStrictEqual(error.data, { foo: 'bar' }) + }) it('with data', () => { const data = { email: 'Email Taken', password: 'Invalid Password' - }; + } - const error = new errors.GeneralError(data); - assert.strictEqual(error.code, 500); - assert.strictEqual(error.message, 'Error'); - assert.deepStrictEqual(error.data, data); - }); - }); + const error = new errors.GeneralError(data) + assert.strictEqual(error.code, 500) + assert.strictEqual(error.message, 'Error') + assert.deepStrictEqual(error.data, data) + }) + }) describe('with custom message', () => { it('contains our message', () => { - const error = new errors.BadRequest('Invalid Password'); - assert.strictEqual(error.code, 400); - assert.strictEqual(error.message, 'Invalid Password'); - }); + const error = new errors.BadRequest('Invalid Password') + assert.strictEqual(error.code, 400) + assert.strictEqual(error.message, 'Invalid Password') + }) it('can wrap an existing error', () => { - const error = new errors.BadRequest(new Error('Invalid Password')); - assert.strictEqual(error.code, 400); - assert.strictEqual(error.message, 'Invalid Password'); - }); + const error = new errors.BadRequest(new Error('Invalid Password')) + assert.strictEqual(error.code, 400) + assert.strictEqual(error.message, 'Invalid Password') + }) it('with data', () => { const data = { email: 'Email Taken', password: 'Invalid Password' - }; + } - const error = new errors.GeneralError('Custom Error', data); - assert.strictEqual(error.code, 500); - assert.strictEqual(error.message, 'Custom Error'); - assert.deepStrictEqual(error.data, data); - }); + const error = new errors.GeneralError('Custom Error', data) + assert.strictEqual(error.code, 500) + assert.strictEqual(error.message, 'Custom Error') + assert.deepStrictEqual(error.data, data) + }) it('with multiple errors', () => { const data = { @@ -287,16 +288,19 @@ describe('@feathersjs/errors', () => { password: 'Invalid Password' }, foo: 'bar' - }; + } - const error = new errors.BadRequest(data); + const error = new errors.BadRequest(data) - assert.strictEqual(error.code, 400); - assert.strictEqual(error.message, 'Error'); - assert.deepStrictEqual(error.errors, { email: 'Email Taken', password: 'Invalid Password' }); - assert.deepStrictEqual(error.data, { foo: 'bar' }); - }); - }); + assert.strictEqual(error.code, 400) + assert.strictEqual(error.message, 'Error') + assert.deepStrictEqual(error.errors, { + email: 'Email Taken', + password: 'Invalid Password' + }) + assert.deepStrictEqual(error.data, { foo: 'bar' }) + }) + }) it('can return JSON', () => { const data = { @@ -305,13 +309,14 @@ describe('@feathersjs/errors', () => { password: 'Invalid Password' }, foo: 'bar' - }; + } - const expected = '{"name":"GeneralError","message":"Custom Error","code":500,"className":"general-error","data":{"foo":"bar"},"errors":{"email":"Email Taken","password":"Invalid Password"}}'; + const expected = + '{"name":"GeneralError","message":"Custom Error","code":500,"className":"general-error","data":{"foo":"bar"},"errors":{"email":"Email Taken","password":"Invalid Password"}}' - const error = new errors.GeneralError('Custom Error', data); - assert.strictEqual(JSON.stringify(error), expected); - }); + const error = new errors.GeneralError('Custom Error', data) + assert.strictEqual(JSON.stringify(error), expected) + }) it('can handle immutable data', () => { const data = { @@ -320,47 +325,52 @@ describe('@feathersjs/errors', () => { password: 'Invalid Password' }, foo: 'bar' - }; + } - const error = new errors.GeneralError('Custom Error', Object.freeze(data)); - assert.strictEqual(error.data.errors, undefined); - assert.deepStrictEqual(error.data, { foo: 'bar' }); - }); + const error = new errors.GeneralError('Custom Error', Object.freeze(data)) + assert.strictEqual(error.data.errors, undefined) + assert.deepStrictEqual(error.data, { foo: 'bar' }) + }) it('allows arrays as data', () => { const data = [ { hello: 'world' } - ]; + ] + + const error = new errors.GeneralError('Custom Error', data) + assert.strictEqual(error.data.errors, undefined) + assert.ok(Array.isArray(error.data)) + assert.deepStrictEqual(error.data, [{ hello: 'world' }]) + }) - const error = new errors.GeneralError('Custom Error', data); - assert.strictEqual(error.data.errors, undefined); - assert.ok(Array.isArray(error.data)); - assert.deepStrictEqual(error.data, [{ hello: 'world' }]); - }); + it('can be instantiated with `null` (#2789)', () => { + const err = new errors.BadRequest(null, {}) + assert.strictEqual(err.message, 'Error') + }) it('has proper stack trace (#78)', () => { try { - throw new errors.NotFound('Not the error you are looking for'); + throw new errors.NotFound('Not the error you are looking for') } catch (e: any) { - const text = 'NotFound: Not the error you are looking for'; + const text = 'NotFound: Not the error you are looking for' - assert.strictEqual(e.stack.indexOf(text), 0); + assert.strictEqual(e.stack.indexOf(text), 0) - assert.ok(e.stack.indexOf('index.test.ts') !== -1); + assert.ok(e.stack.indexOf('index.test.ts') !== -1) - const oldCST = Error.captureStackTrace; + const oldCST = Error.captureStackTrace - delete Error.captureStackTrace; + delete Error.captureStackTrace try { - throw new errors.NotFound('Not the error you are looking for'); + throw new errors.NotFound('Not the error you are looking for') } catch (e: any) { - assert.ok(e); - Error.captureStackTrace = oldCST; + assert.ok(e) + Error.captureStackTrace = oldCST } } - }); - }); -}); \ No newline at end of file + }) + }) +}) diff --git a/packages/express/CHANGELOG.md b/packages/express/CHANGELOG.md index 1b9166affc..77ea7b97b9 100644 --- a/packages/express/CHANGELOG.md +++ b/packages/express/CHANGELOG.md @@ -3,622 +3,457 @@ All notable changes to this project will be documented in this file. See [Conventional Commits](https://conventionalcommits.org) for commit guidelines. -# [5.0.0-pre.16](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.15...v5.0.0-pre.16) (2022-01-12) - +# [5.0.0-pre.31](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.30...v5.0.0-pre.31) (2022-10-12) -### Features - -* **express, koa:** make transports similar ([#2486](https://github.com/feathersjs/feathers/issues/2486)) ([26aa937](https://github.com/feathersjs/feathers/commit/26aa937c114fb8596dfefc599b1f53cead69c159)) +**Note:** Version bump only for package @feathersjs/express +# [5.0.0-pre.30](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.29...v5.0.0-pre.30) (2022-10-07) +### Bug Fixes +- **core:** Ensure setup and teardown can be overriden and maintain hook functionality ([#2779](https://github.com/feathersjs/feathers/issues/2779)) ([ab580cb](https://github.com/feathersjs/feathers/commit/ab580cbcaa68d19144d86798c13bf564f9d424a6)) +### Features -# [5.0.0-pre.15](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.14...v5.0.0-pre.15) (2021-11-27) +- **core:** Allow to unregister services at runtime ([#2756](https://github.com/feathersjs/feathers/issues/2756)) ([d16601f](https://github.com/feathersjs/feathers/commit/d16601f2277dca5357866ffdefba2a611f6dc7fa)) +# [5.0.0-pre.29](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.28...v5.0.0-pre.29) (2022-09-16) -### Bug Fixes +### Features -* missing express types for Request, Response ([#2498](https://github.com/feathersjs/feathers/issues/2498)) ([ee67131](https://github.com/feathersjs/feathers/commit/ee67131bbaa24c54d3d781bdf8820015759ac488)) -* **typescript:** Overall typing improvements ([#2478](https://github.com/feathersjs/feathers/issues/2478)) ([b8eb804](https://github.com/feathersjs/feathers/commit/b8eb804158556d9651a8607e3c3fda15e0bfd110)) +- Add CORS support to oAuth, Express, Koa and generated application ([#2744](https://github.com/feathersjs/feathers/issues/2744)) ([fd218f2](https://github.com/feathersjs/feathers/commit/fd218f289f8ca4c101e9938e8683e2efef6e8131)) +- **authentication-oauth:** Koa and transport independent oAuth authentication ([#2737](https://github.com/feathersjs/feathers/issues/2737)) ([9231525](https://github.com/feathersjs/feathers/commit/9231525a24bb790ba9c5d940f2867a9c727691c9)) +# [5.0.0-pre.28](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.27...v5.0.0-pre.28) (2022-08-03) -### Features +### Bug Fixes -* **core:** add `context.http` and move `statusCode` there ([#2496](https://github.com/feathersjs/feathers/issues/2496)) ([b701bf7](https://github.com/feathersjs/feathers/commit/b701bf77fb83048aa1dffa492b3d77dd53f7b72b)) -* **core:** Improve legacy hooks integration ([08c8b40](https://github.com/feathersjs/feathers/commit/08c8b40999bf3889c61a4d4fad97a2c4f78bafc9)) +- **cli:** Improve generated application and client ([#2701](https://github.com/feathersjs/feathers/issues/2701)) ([bd55ffb](https://github.com/feathersjs/feathers/commit/bd55ffb812e89bf215f4515e7f137656ea888c3f)) +# [5.0.0-pre.27](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.26...v5.0.0-pre.27) (2022-07-13) +**Note:** Version bump only for package @feathersjs/express +# [5.0.0-pre.26](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.25...v5.0.0-pre.26) (2022-06-22) +**Note:** Version bump only for package @feathersjs/express -# [5.0.0-pre.14](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.13...v5.0.0-pre.14) (2021-10-13) +# [5.0.0-pre.25](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.24...v5.0.0-pre.25) (2022-06-22) **Note:** Version bump only for package @feathersjs/express +# [5.0.0-pre.24](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.23...v5.0.0-pre.24) (2022-06-21) +### Bug Fixes +- **authentication:** Add safe dispatch data for authentication requests ([#2662](https://github.com/feathersjs/feathers/issues/2662)) ([d8104a1](https://github.com/feathersjs/feathers/commit/d8104a19ee9181e6a5ea81014af29ff9a3c28a8a)) +### Features -# [5.0.0-pre.13](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.12...v5.0.0-pre.13) (2021-10-13) +- **cli:** Add support for JavaScript to the new CLI ([#2668](https://github.com/feathersjs/feathers/issues/2668)) ([ebac587](https://github.com/feathersjs/feathers/commit/ebac587f7d00dc7607c3f546352d79f79b89a5d4)) -**Note:** Version bump only for package @feathersjs/express +# [5.0.0-pre.23](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.22...v5.0.0-pre.23) (2022-06-06) +### Bug Fixes +- **express:** Ensure Express options can be set before configuring REST transport ([#2655](https://github.com/feathersjs/feathers/issues/2655)) ([c9b8f74](https://github.com/feathersjs/feathers/commit/c9b8f74a0196acb99be44ac5e0fff3f1128288cd)) +# [5.0.0-pre.22](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.21...v5.0.0-pre.22) (2022-05-24) +**Note:** Version bump only for package @feathersjs/express -# [5.0.0-pre.12](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.11...v5.0.0-pre.12) (2021-10-12) +# [5.0.0-pre.21](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.20...v5.0.0-pre.21) (2022-05-23) **Note:** Version bump only for package @feathersjs/express +# [5.0.0-pre.20](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.19...v5.0.0-pre.20) (2022-05-04) +### Bug Fixes +- **dependencies:** Lock monorepo package version numbers ([#2623](https://github.com/feathersjs/feathers/issues/2623)) ([5640c10](https://github.com/feathersjs/feathers/commit/5640c1020cc139994e695d658c08bad3494db507)) +# [5.0.0-pre.19](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.18...v5.0.0-pre.19) (2022-05-01) -# [5.0.0-pre.11](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.10...v5.0.0-pre.11) (2021-10-06) +### Bug Fixes -**Note:** Version bump only for package @feathersjs/express +- **express:** Fix typo in types reference in package.json ([#2613](https://github.com/feathersjs/feathers/issues/2613)) ([eacf1b3](https://github.com/feathersjs/feathers/commit/eacf1b3474e6d9da69b8671244c23a75cff87d95)) +### Features +- **typescript:** Improve params and query typeability ([#2600](https://github.com/feathersjs/feathers/issues/2600)) ([df28b76](https://github.com/feathersjs/feathers/commit/df28b7619161f1df5e700326f52cca1a92dc5d28)) +# [5.0.0-pre.18](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.17...v5.0.0-pre.18) (2022-04-11) +### Features -# [5.0.0-pre.10](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.9...v5.0.0-pre.10) (2021-09-19) +- **core:** Add app.teardown functionality ([#2570](https://github.com/feathersjs/feathers/issues/2570)) ([fcdf524](https://github.com/feathersjs/feathers/commit/fcdf524ae1995bb59265d39f12e98b7794bed023)) +- **core:** Finalize app.teardown() functionality ([#2584](https://github.com/feathersjs/feathers/issues/2584)) ([1a166f3](https://github.com/feathersjs/feathers/commit/1a166f3ded811ecacf0ae8cb67880bc9fa2eeafa)) +- **transport-commons:** add `context.http.response` ([#2524](https://github.com/feathersjs/feathers/issues/2524)) ([5bc9d44](https://github.com/feathersjs/feathers/commit/5bc9d447043c2e2b742c73ed28ecf3b3264dd9e5)) -**Note:** Version bump only for package @feathersjs/express +# [5.0.0-pre.17](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.16...v5.0.0-pre.17) (2022-02-15) +### Bug Fixes +- **express:** Fix application typings to work with typed configuration ([#2539](https://github.com/feathersjs/feathers/issues/2539)) ([b9dfaee](https://github.com/feathersjs/feathers/commit/b9dfaee834b13864c1ed4f2f6a244eb5bb70395b)) +# [5.0.0-pre.16](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.15...v5.0.0-pre.16) (2022-01-12) +### Features -# [5.0.0-pre.9](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.8...v5.0.0-pre.9) (2021-08-09) +- **express, koa:** make transports similar ([#2486](https://github.com/feathersjs/feathers/issues/2486)) ([26aa937](https://github.com/feathersjs/feathers/commit/26aa937c114fb8596dfefc599b1f53cead69c159)) -**Note:** Version bump only for package @feathersjs/express +# [5.0.0-pre.15](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.14...v5.0.0-pre.15) (2021-11-27) +### Bug Fixes +- missing express types for Request, Response ([#2498](https://github.com/feathersjs/feathers/issues/2498)) ([ee67131](https://github.com/feathersjs/feathers/commit/ee67131bbaa24c54d3d781bdf8820015759ac488)) +- **typescript:** Overall typing improvements ([#2478](https://github.com/feathersjs/feathers/issues/2478)) ([b8eb804](https://github.com/feathersjs/feathers/commit/b8eb804158556d9651a8607e3c3fda15e0bfd110)) +### Features +- **core:** add `context.http` and move `statusCode` there ([#2496](https://github.com/feathersjs/feathers/issues/2496)) ([b701bf7](https://github.com/feathersjs/feathers/commit/b701bf77fb83048aa1dffa492b3d77dd53f7b72b)) +- **core:** Improve legacy hooks integration ([08c8b40](https://github.com/feathersjs/feathers/commit/08c8b40999bf3889c61a4d4fad97a2c4f78bafc9)) -# [5.0.0-pre.8](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.7...v5.0.0-pre.8) (2021-08-09) +# [5.0.0-pre.14](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.13...v5.0.0-pre.14) (2021-10-13) **Note:** Version bump only for package @feathersjs/express +# [5.0.0-pre.13](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.12...v5.0.0-pre.13) (2021-10-13) +**Note:** Version bump only for package @feathersjs/express +# [5.0.0-pre.12](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.11...v5.0.0-pre.12) (2021-10-12) +**Note:** Version bump only for package @feathersjs/express -# [5.0.0-pre.7](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.6...v5.0.0-pre.7) (2021-08-09) +# [5.0.0-pre.11](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.10...v5.0.0-pre.11) (2021-10-06) **Note:** Version bump only for package @feathersjs/express +# [5.0.0-pre.10](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.9...v5.0.0-pre.10) (2021-09-19) +**Note:** Version bump only for package @feathersjs/express +# [5.0.0-pre.9](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.8...v5.0.0-pre.9) (2021-08-09) +**Note:** Version bump only for package @feathersjs/express -# [5.0.0-pre.6](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.5...v5.0.0-pre.6) (2021-08-08) +# [5.0.0-pre.8](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.7...v5.0.0-pre.8) (2021-08-09) **Note:** Version bump only for package @feathersjs/express +# [5.0.0-pre.7](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.6...v5.0.0-pre.7) (2021-08-09) +**Note:** Version bump only for package @feathersjs/express +# [5.0.0-pre.6](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.5...v5.0.0-pre.6) (2021-08-08) +**Note:** Version bump only for package @feathersjs/express # [5.0.0-pre.5](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.4...v5.0.0-pre.5) (2021-06-23) **Note:** Version bump only for package @feathersjs/express - - - - # [5.0.0-pre.4](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.3...v5.0.0-pre.4) (2021-05-13) - ### Features -* **koa:** KoaJS transport adapter ([#2315](https://github.com/feathersjs/feathers/issues/2315)) ([2554b57](https://github.com/feathersjs/feathers/commit/2554b57cf05731df58feeba9c12faab18e442107)) - - - - +- **koa:** KoaJS transport adapter ([#2315](https://github.com/feathersjs/feathers/issues/2315)) ([2554b57](https://github.com/feathersjs/feathers/commit/2554b57cf05731df58feeba9c12faab18e442107)) # [5.0.0-pre.3](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.2...v5.0.0-pre.3) (2021-04-21) - ### Bug Fixes -* **typescript:** Improve TypeScript backwards compatibility ([#2310](https://github.com/feathersjs/feathers/issues/2310)) ([f33be73](https://github.com/feathersjs/feathers/commit/f33be73fc46a533efb15df9aab0658e3240d3897)) - +- **typescript:** Improve TypeScript backwards compatibility ([#2310](https://github.com/feathersjs/feathers/issues/2310)) ([f33be73](https://github.com/feathersjs/feathers/commit/f33be73fc46a533efb15df9aab0658e3240d3897)) ### Features -* **dependencies:** Remove direct debug dependency ([#2296](https://github.com/feathersjs/feathers/issues/2296)) ([501d416](https://github.com/feathersjs/feathers/commit/501d4164d30c6a126906dc640cdfdc82207ba34a)) - - - - +- **dependencies:** Remove direct debug dependency ([#2296](https://github.com/feathersjs/feathers/issues/2296)) ([501d416](https://github.com/feathersjs/feathers/commit/501d4164d30c6a126906dc640cdfdc82207ba34a)) # [5.0.0-pre.2](https://github.com/feathersjs/feathers/compare/v5.0.0-beta.1...v5.0.0-pre.2) (2021-04-06) **Note:** Version bump only for package @feathersjs/express - - - - # [5.0.0-beta.1](https://github.com/feathersjs/feathers/compare/v5.0.0-beta.0...v5.0.0-beta.1) (2021-04-03) **Note:** Version bump only for package @feathersjs/express - - - - # [5.0.0-beta.0](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.1...v5.0.0-beta.0) (2021-03-28) - ### Bug Fixes -* Resolve some type problems ([#2260](https://github.com/feathersjs/feathers/issues/2260)) ([a3d75fa](https://github.com/feathersjs/feathers/commit/a3d75fa29490e8a19412a12bc993ee7bb573068f)) -* Update Grant usage and other dependencies ([#2264](https://github.com/feathersjs/feathers/issues/2264)) ([7b0f8fa](https://github.com/feathersjs/feathers/commit/7b0f8fad252419ed0ad0bf259cdf3104d322ab60)) - +- Resolve some type problems ([#2260](https://github.com/feathersjs/feathers/issues/2260)) ([a3d75fa](https://github.com/feathersjs/feathers/commit/a3d75fa29490e8a19412a12bc993ee7bb573068f)) +- Update Grant usage and other dependencies ([#2264](https://github.com/feathersjs/feathers/issues/2264)) ([7b0f8fa](https://github.com/feathersjs/feathers/commit/7b0f8fad252419ed0ad0bf259cdf3104d322ab60)) ### Features -* **core:** Public custom service methods ([#2270](https://github.com/feathersjs/feathers/issues/2270)) ([e65abfb](https://github.com/feathersjs/feathers/commit/e65abfb5388df6c19a11c565cf1076a29f32668d)) -* Application service types default to any ([#1566](https://github.com/feathersjs/feathers/issues/1566)) ([d93ba9a](https://github.com/feathersjs/feathers/commit/d93ba9a17edd20d3397bb00f4f6e82e804e42ed6)) -* Feathers v5 core refactoring and features ([#2255](https://github.com/feathersjs/feathers/issues/2255)) ([2dafb7c](https://github.com/feathersjs/feathers/commit/2dafb7ce14ba57406aeec13d10ca45b1e709bee9)) -* **core:** Remove Uberproto ([#2178](https://github.com/feathersjs/feathers/issues/2178)) ([ddf8821](https://github.com/feathersjs/feathers/commit/ddf8821f53317e6a378657f7d66acb03a037ee47)) - +- **core:** Public custom service methods ([#2270](https://github.com/feathersjs/feathers/issues/2270)) ([e65abfb](https://github.com/feathersjs/feathers/commit/e65abfb5388df6c19a11c565cf1076a29f32668d)) +- Application service types default to any ([#1566](https://github.com/feathersjs/feathers/issues/1566)) ([d93ba9a](https://github.com/feathersjs/feathers/commit/d93ba9a17edd20d3397bb00f4f6e82e804e42ed6)) +- Feathers v5 core refactoring and features ([#2255](https://github.com/feathersjs/feathers/issues/2255)) ([2dafb7c](https://github.com/feathersjs/feathers/commit/2dafb7ce14ba57406aeec13d10ca45b1e709bee9)) +- **core:** Remove Uberproto ([#2178](https://github.com/feathersjs/feathers/issues/2178)) ([ddf8821](https://github.com/feathersjs/feathers/commit/ddf8821f53317e6a378657f7d66acb03a037ee47)) ### BREAKING CHANGES -* **core:** Services no longer extend Uberproto objects and -`service.mixin()` is no longer available. - - - - +- **core:** Services no longer extend Uberproto objects and + `service.mixin()` is no longer available. # [5.0.0-pre.1](https://github.com/feathersjs/feathers/compare/v4.5.11...v5.0.0-pre.1) (2020-12-17) - - # [5.0.0-pre.0](https://github.com/feathersjs/feathers/compare/v4.5.4...v5.0.0-pre.0) (2020-05-19) - ### Features -* **core:** use @feathers/hooks and add async type ([#1929](https://github.com/feathersjs/feathers/issues/1929)) ([a5c4756](https://github.com/feathersjs/feathers/commit/a5c47562eae8410c82fe2f6308f26f8e78b6a3e8)) - - - - +- **core:** use @feathers/hooks and add async type ([#1929](https://github.com/feathersjs/feathers/issues/1929)) ([a5c4756](https://github.com/feathersjs/feathers/commit/a5c47562eae8410c82fe2f6308f26f8e78b6a3e8)) # [5.0.0-pre.0](https://github.com/feathersjs/feathers/compare/v4.5.4...v5.0.0-pre.0) (2020-05-19) - ### Features -* **core:** use @feathers/hooks and add async type ([#1929](https://github.com/feathersjs/feathers/issues/1929)) ([a5c4756](https://github.com/feathersjs/feathers/commit/a5c47562eae8410c82fe2f6308f26f8e78b6a3e8)) - - +- **core:** use @feathers/hooks and add async type ([#1929](https://github.com/feathersjs/feathers/issues/1929)) ([a5c4756](https://github.com/feathersjs/feathers/commit/a5c47562eae8410c82fe2f6308f26f8e78b6a3e8)) ## [4.5.11](https://github.com/feathersjs/feathers/compare/v4.5.10...v4.5.11) (2020-12-05) **Note:** Version bump only for package @feathersjs/express - - - - ## [4.5.10](https://github.com/feathersjs/feathers/compare/v4.5.9...v4.5.10) (2020-11-08) - ### Bug Fixes -* **authentication:** consistent response return between local and jwt strategy ([#2042](https://github.com/feathersjs/feathers/issues/2042)) ([8d25be1](https://github.com/feathersjs/feathers/commit/8d25be101a2593a9e789375c928a07780b9e28cf)) - - - - +- **authentication:** consistent response return between local and jwt strategy ([#2042](https://github.com/feathersjs/feathers/issues/2042)) ([8d25be1](https://github.com/feathersjs/feathers/commit/8d25be101a2593a9e789375c928a07780b9e28cf)) ## [4.5.9](https://github.com/feathersjs/feathers/compare/v4.5.8...v4.5.9) (2020-10-09) **Note:** Version bump only for package @feathersjs/express - - - - ## [4.5.8](https://github.com/feathersjs/feathers/compare/v4.5.7...v4.5.8) (2020-08-12) **Note:** Version bump only for package @feathersjs/express - - - - ## [4.5.7](https://github.com/feathersjs/feathers/compare/v4.5.6...v4.5.7) (2020-07-24) **Note:** Version bump only for package @feathersjs/express - - - - ## [4.5.6](https://github.com/feathersjs/feathers/compare/v4.5.5...v4.5.6) (2020-07-12) **Note:** Version bump only for package @feathersjs/express - - - - ## [4.5.5](https://github.com/feathersjs/feathers/compare/v4.5.4...v4.5.5) (2020-07-11) **Note:** Version bump only for package @feathersjs/express - - - - ## [4.5.4](https://github.com/feathersjs/feathers/compare/v4.5.3...v4.5.4) (2020-04-29) **Note:** Version bump only for package @feathersjs/express - - - - ## [4.5.3](https://github.com/feathersjs/feathers/compare/v4.5.2...v4.5.3) (2020-04-17) **Note:** Version bump only for package @feathersjs/express - - - - ## [4.5.2](https://github.com/feathersjs/feathers/compare/v4.5.1...v4.5.2) (2020-03-04) - ### Bug Fixes -* Updated typings for express middleware ([#1839](https://github.com/feathersjs/feathers/issues/1839)) ([6b8e897](https://github.com/feathersjs/feathers/commit/6b8e8971a9dbb08913edd1be48826624645d9dc1)) - - - - +- Updated typings for express middleware ([#1839](https://github.com/feathersjs/feathers/issues/1839)) ([6b8e897](https://github.com/feathersjs/feathers/commit/6b8e8971a9dbb08913edd1be48826624645d9dc1)) ## [4.5.1](https://github.com/feathersjs/feathers/compare/v4.5.0...v4.5.1) (2020-01-24) **Note:** Version bump only for package @feathersjs/express - - - - # [4.5.0](https://github.com/feathersjs/feathers/compare/v4.4.3...v4.5.0) (2020-01-18) **Note:** Version bump only for package @feathersjs/express - - - - ## [4.4.3](https://github.com/feathersjs/feathers/compare/v4.4.1...v4.4.3) (2019-12-06) **Note:** Version bump only for package @feathersjs/express - - - - ## [4.4.1](https://github.com/feathersjs/feathers/compare/v4.4.0...v4.4.1) (2019-11-27) **Note:** Version bump only for package @feathersjs/express - - - - # [4.4.0](https://github.com/feathersjs/feathers/compare/v4.3.11...v4.4.0) (2019-11-27) - ### Features -* **authentication:** Add parseStrategies to allow separate strategies for creating JWTs and parsing headers ([#1708](https://github.com/feathersjs/feathers/issues/1708)) ([5e65629](https://github.com/feathersjs/feathers/commit/5e65629b924724c3e81d7c81df047e123d1c8bd7)) - - - - +- **authentication:** Add parseStrategies to allow separate strategies for creating JWTs and parsing headers ([#1708](https://github.com/feathersjs/feathers/issues/1708)) ([5e65629](https://github.com/feathersjs/feathers/commit/5e65629b924724c3e81d7c81df047e123d1c8bd7)) ## [4.3.11](https://github.com/feathersjs/feathers/compare/v4.3.10...v4.3.11) (2019-11-11) **Note:** Version bump only for package @feathersjs/express - - - - ## [4.3.10](https://github.com/feathersjs/feathers/compare/v4.3.9...v4.3.10) (2019-10-26) **Note:** Version bump only for package @feathersjs/express - - - - ## [4.3.9](https://github.com/feathersjs/feathers/compare/v4.3.8...v4.3.9) (2019-10-26) - ### Bug Fixes -* Small type improvements ([#1624](https://github.com/feathersjs/feathers/issues/1624)) ([50162c6](https://github.com/feathersjs/feathers/commit/50162c6e562f0a47c6a280c4f01fff7c3afee293)) - - - - +- Small type improvements ([#1624](https://github.com/feathersjs/feathers/issues/1624)) ([50162c6](https://github.com/feathersjs/feathers/commit/50162c6e562f0a47c6a280c4f01fff7c3afee293)) ## [4.3.7](https://github.com/feathersjs/feathers/compare/v4.3.6...v4.3.7) (2019-10-14) - ### Bug Fixes -* Typings for express request and response properties ([#1609](https://github.com/feathersjs/feathers/issues/1609)) ([38cf8c9](https://github.com/feathersjs/feathers/commit/38cf8c950c1a4fb4a6d78d68d70e7fdd63b71c3c)) - - - - +- Typings for express request and response properties ([#1609](https://github.com/feathersjs/feathers/issues/1609)) ([38cf8c9](https://github.com/feathersjs/feathers/commit/38cf8c950c1a4fb4a6d78d68d70e7fdd63b71c3c)) ## [4.3.5](https://github.com/feathersjs/feathers/compare/v4.3.4...v4.3.5) (2019-10-07) **Note:** Version bump only for package @feathersjs/express - - - - ## [4.3.4](https://github.com/feathersjs/feathers/compare/v4.3.3...v4.3.4) (2019-10-03) **Note:** Version bump only for package @feathersjs/express - - - - ## [4.3.3](https://github.com/feathersjs/feathers/compare/v4.3.2...v4.3.3) (2019-09-21) **Note:** Version bump only for package @feathersjs/express - - - - ## [4.3.2](https://github.com/feathersjs/feathers/compare/v4.3.1...v4.3.2) (2019-09-16) - ### Bug Fixes -* Add info to express error handler logger type ([#1557](https://github.com/feathersjs/feathers/issues/1557)) ([3e1d26c](https://github.com/feathersjs/feathers/commit/3e1d26c)) - - - - +- Add info to express error handler logger type ([#1557](https://github.com/feathersjs/feathers/issues/1557)) ([3e1d26c](https://github.com/feathersjs/feathers/commit/3e1d26c)) ## [4.3.1](https://github.com/feathersjs/feathers/compare/v4.3.0...v4.3.1) (2019-09-09) **Note:** Version bump only for package @feathersjs/express - - - - # [4.3.0](https://github.com/feathersjs/feathers/compare/v4.3.0-pre.4...v4.3.0) (2019-08-27) **Note:** Version bump only for package @feathersjs/express - - - - # [4.3.0-pre.4](https://github.com/feathersjs/feathers/compare/v4.3.0-pre.3...v4.3.0-pre.4) (2019-08-22) **Note:** Version bump only for package @feathersjs/express - - - - # [4.3.0-pre.3](https://github.com/feathersjs/feathers/compare/v4.3.0-pre.2...v4.3.0-pre.3) (2019-08-19) - ### Bug Fixes -* Update all dependencies ([7d53a00](https://github.com/feathersjs/feathers/commit/7d53a00)) - - - - +- Update all dependencies ([7d53a00](https://github.com/feathersjs/feathers/commit/7d53a00)) # [4.3.0-pre.2](https://github.com/feathersjs/feathers/compare/v4.3.0-pre.1...v4.3.0-pre.2) (2019-08-02) - ### Bug Fixes -* Add method to reliably get default authentication service ([#1470](https://github.com/feathersjs/feathers/issues/1470)) ([e542cb3](https://github.com/feathersjs/feathers/commit/e542cb3)) - - - - +- Add method to reliably get default authentication service ([#1470](https://github.com/feathersjs/feathers/issues/1470)) ([e542cb3](https://github.com/feathersjs/feathers/commit/e542cb3)) # [4.3.0-pre.1](https://github.com/feathersjs/feathers/compare/v4.0.0-pre.5...v4.3.0-pre.1) (2019-07-11) **Note:** Version bump only for package @feathersjs/express - - - - # [4.0.0-pre.5](https://github.com/feathersjs/feathers/compare/v4.0.0-pre.4...v4.0.0-pre.5) (2019-07-10) - ### Bug Fixes -* Remove unnecessary top level export files in @feathersjs/express ([#1442](https://github.com/feathersjs/feathers/issues/1442)) ([73c3fb2](https://github.com/feathersjs/feathers/commit/73c3fb2)) - +- Remove unnecessary top level export files in @feathersjs/express ([#1442](https://github.com/feathersjs/feathers/issues/1442)) ([73c3fb2](https://github.com/feathersjs/feathers/commit/73c3fb2)) ### Features -* @feathersjs/express allow to pass an existing Express application instance ([#1446](https://github.com/feathersjs/feathers/issues/1446)) ([853a6b0](https://github.com/feathersjs/feathers/commit/853a6b0)) - - - - +- @feathersjs/express allow to pass an existing Express application instance ([#1446](https://github.com/feathersjs/feathers/issues/1446)) ([853a6b0](https://github.com/feathersjs/feathers/commit/853a6b0)) # [4.0.0-pre.4](https://github.com/feathersjs/feathers/compare/v4.0.0-pre.3...v4.0.0-pre.4) (2019-07-05) - ### Bug Fixes -* @feathersjs/express: allow middleware arrays ([#1421](https://github.com/feathersjs/feathers/issues/1421)) ([b605ab8](https://github.com/feathersjs/feathers/commit/b605ab8)) -* @feathersjs/express: replace `reduce` with `map` ([#1429](https://github.com/feathersjs/feathers/issues/1429)) ([44542e9](https://github.com/feathersjs/feathers/commit/44542e9)) -* Clean up hooks code ([#1407](https://github.com/feathersjs/feathers/issues/1407)) ([f25c88b](https://github.com/feathersjs/feathers/commit/f25c88b)) - - - - +- @feathersjs/express: allow middleware arrays ([#1421](https://github.com/feathersjs/feathers/issues/1421)) ([b605ab8](https://github.com/feathersjs/feathers/commit/b605ab8)) +- @feathersjs/express: replace `reduce` with `map` ([#1429](https://github.com/feathersjs/feathers/issues/1429)) ([44542e9](https://github.com/feathersjs/feathers/commit/44542e9)) +- Clean up hooks code ([#1407](https://github.com/feathersjs/feathers/issues/1407)) ([f25c88b](https://github.com/feathersjs/feathers/commit/f25c88b)) # [4.0.0-pre.3](https://github.com/feathersjs/feathers/compare/v4.0.0-pre.2...v4.0.0-pre.3) (2019-06-01) - ### Bug Fixes -* Update dependencies and fix tests ([#1373](https://github.com/feathersjs/feathers/issues/1373)) ([d743a7f](https://github.com/feathersjs/feathers/commit/d743a7f)) - - - - +- Update dependencies and fix tests ([#1373](https://github.com/feathersjs/feathers/issues/1373)) ([d743a7f](https://github.com/feathersjs/feathers/commit/d743a7f)) # [4.0.0-pre.2](https://github.com/feathersjs/feathers/compare/v4.0.0-pre.1...v4.0.0-pre.2) (2019-05-15) - ### Bug Fixes -* Use `export =` in TypeScript definitions ([#1285](https://github.com/feathersjs/feathers/issues/1285)) ([12d0f4b](https://github.com/feathersjs/feathers/commit/12d0f4b)) - - - - +- Use `export =` in TypeScript definitions ([#1285](https://github.com/feathersjs/feathers/issues/1285)) ([12d0f4b](https://github.com/feathersjs/feathers/commit/12d0f4b)) # [4.0.0-pre.1](https://github.com/feathersjs/feathers/compare/v4.0.0-pre.0...v4.0.0-pre.1) (2019-05-08) - ### Bug Fixes -* Always require strategy parameter in authentication ([#1327](https://github.com/feathersjs/feathers/issues/1327)) ([d4a8021](https://github.com/feathersjs/feathers/commit/d4a8021)) -* Merge httpStrategies and authStrategies option ([#1308](https://github.com/feathersjs/feathers/issues/1308)) ([afa4d55](https://github.com/feathersjs/feathers/commit/afa4d55)) - +- Always require strategy parameter in authentication ([#1327](https://github.com/feathersjs/feathers/issues/1327)) ([d4a8021](https://github.com/feathersjs/feathers/commit/d4a8021)) +- Merge httpStrategies and authStrategies option ([#1308](https://github.com/feathersjs/feathers/issues/1308)) ([afa4d55](https://github.com/feathersjs/feathers/commit/afa4d55)) ### Features -* Add params.headers to all transports when available ([#1303](https://github.com/feathersjs/feathers/issues/1303)) ([ebce79b](https://github.com/feathersjs/feathers/commit/ebce79b)) -* express use service.methods ([#945](https://github.com/feathersjs/feathers/issues/945)) ([3f0b1c3](https://github.com/feathersjs/feathers/commit/3f0b1c3)) - - - - +- Add params.headers to all transports when available ([#1303](https://github.com/feathersjs/feathers/issues/1303)) ([ebce79b](https://github.com/feathersjs/feathers/commit/ebce79b)) +- express use service.methods ([#945](https://github.com/feathersjs/feathers/issues/945)) ([3f0b1c3](https://github.com/feathersjs/feathers/commit/3f0b1c3)) # [4.0.0-pre.0](https://github.com/feathersjs/feathers/compare/v3.2.0-pre.1...v4.0.0-pre.0) (2019-04-21) - ### Bug Fixes -* Make Mocha a proper devDependency for every repository ([#1053](https://github.com/feathersjs/feathers/issues/1053)) ([9974803](https://github.com/feathersjs/feathers/commit/9974803)) -* Update adapter common tests ([#1135](https://github.com/feathersjs/feathers/issues/1135)) ([8166dda](https://github.com/feathersjs/feathers/commit/8166dda)) -* Update all dependencies to latest ([#1206](https://github.com/feathersjs/feathers/issues/1206)) ([e51e0f6](https://github.com/feathersjs/feathers/commit/e51e0f6)) -* **chore:** Properly configure and run code linter ([#1092](https://github.com/feathersjs/feathers/issues/1092)) ([fd3fc34](https://github.com/feathersjs/feathers/commit/fd3fc34)) -* **package:** update @feathersjs/commons to version 2.0.0 ([#31](https://github.com/feathersjs/feathers/issues/31)) ([c1ef5b1](https://github.com/feathersjs/feathers/commit/c1ef5b1)) -* **package:** update debug to version 3.0.0 ([#2](https://github.com/feathersjs/feathers/issues/2)) ([7e19603](https://github.com/feathersjs/feathers/commit/7e19603)) - +- Make Mocha a proper devDependency for every repository ([#1053](https://github.com/feathersjs/feathers/issues/1053)) ([9974803](https://github.com/feathersjs/feathers/commit/9974803)) +- Update adapter common tests ([#1135](https://github.com/feathersjs/feathers/issues/1135)) ([8166dda](https://github.com/feathersjs/feathers/commit/8166dda)) +- Update all dependencies to latest ([#1206](https://github.com/feathersjs/feathers/issues/1206)) ([e51e0f6](https://github.com/feathersjs/feathers/commit/e51e0f6)) +- **chore:** Properly configure and run code linter ([#1092](https://github.com/feathersjs/feathers/issues/1092)) ([fd3fc34](https://github.com/feathersjs/feathers/commit/fd3fc34)) +- **package:** update @feathersjs/commons to version 2.0.0 ([#31](https://github.com/feathersjs/feathers/issues/31)) ([c1ef5b1](https://github.com/feathersjs/feathers/commit/c1ef5b1)) +- **package:** update debug to version 3.0.0 ([#2](https://github.com/feathersjs/feathers/issues/2)) ([7e19603](https://github.com/feathersjs/feathers/commit/7e19603)) ### Features -* @feathersjs/authentication-oauth ([#1299](https://github.com/feathersjs/feathers/issues/1299)) ([656bae7](https://github.com/feathersjs/feathers/commit/656bae7)) -* Add AuthenticationBaseStrategy and make authentication option handling more explicit ([#1284](https://github.com/feathersjs/feathers/issues/1284)) ([2667d92](https://github.com/feathersjs/feathers/commit/2667d92)) -* Add TypeScript definitions ([#1275](https://github.com/feathersjs/feathers/issues/1275)) ([9dd6713](https://github.com/feathersjs/feathers/commit/9dd6713)) -* Allow registering a service at the root level ([#1115](https://github.com/feathersjs/feathers/issues/1115)) ([c73d322](https://github.com/feathersjs/feathers/commit/c73d322)) -* Authentication v3 client ([#1240](https://github.com/feathersjs/feathers/issues/1240)) ([65b43bd](https://github.com/feathersjs/feathers/commit/65b43bd)) -* Authentication v3 Express integration ([#1218](https://github.com/feathersjs/feathers/issues/1218)) ([82bcfbe](https://github.com/feathersjs/feathers/commit/82bcfbe)) - +- @feathersjs/authentication-oauth ([#1299](https://github.com/feathersjs/feathers/issues/1299)) ([656bae7](https://github.com/feathersjs/feathers/commit/656bae7)) +- Add AuthenticationBaseStrategy and make authentication option handling more explicit ([#1284](https://github.com/feathersjs/feathers/issues/1284)) ([2667d92](https://github.com/feathersjs/feathers/commit/2667d92)) +- Add TypeScript definitions ([#1275](https://github.com/feathersjs/feathers/issues/1275)) ([9dd6713](https://github.com/feathersjs/feathers/commit/9dd6713)) +- Allow registering a service at the root level ([#1115](https://github.com/feathersjs/feathers/issues/1115)) ([c73d322](https://github.com/feathersjs/feathers/commit/c73d322)) +- Authentication v3 client ([#1240](https://github.com/feathersjs/feathers/issues/1240)) ([65b43bd](https://github.com/feathersjs/feathers/commit/65b43bd)) +- Authentication v3 Express integration ([#1218](https://github.com/feathersjs/feathers/issues/1218)) ([82bcfbe](https://github.com/feathersjs/feathers/commit/82bcfbe)) ### BREAKING CHANGES -* Rewrite for authentication v3 - - - - +- Rewrite for authentication v3 ## [1.3.1](https://github.com/feathersjs/feathers/compare/@feathersjs/express@1.3.0...@feathersjs/express@1.3.1) (2019-01-02) - ### Bug Fixes -* Update adapter common tests ([#1135](https://github.com/feathersjs/feathers/issues/1135)) ([8166dda](https://github.com/feathersjs/feathers/commit/8166dda)) - - - - +- Update adapter common tests ([#1135](https://github.com/feathersjs/feathers/issues/1135)) ([8166dda](https://github.com/feathersjs/feathers/commit/8166dda)) -# [1.3.0](https://github.com/feathersjs/feathers/compare/@feathersjs/express@1.2.7...@feathersjs/express@1.3.0) (2018-12-16) +# [1.3.0](https://github.com/feathersjs/feathers/compare/@feathersjs/express@1.2.7...@feathersjs/express@1.3.0) (2018-12-16) ### Bug Fixes -* Make Mocha a proper devDependency for every repository ([#1053](https://github.com/feathersjs/feathers/issues/1053)) ([9974803](https://github.com/feathersjs/feathers/commit/9974803)) -* **chore:** Properly configure and run code linter ([#1092](https://github.com/feathersjs/feathers/issues/1092)) ([fd3fc34](https://github.com/feathersjs/feathers/commit/fd3fc34)) - +- Make Mocha a proper devDependency for every repository ([#1053](https://github.com/feathersjs/feathers/issues/1053)) ([9974803](https://github.com/feathersjs/feathers/commit/9974803)) +- **chore:** Properly configure and run code linter ([#1092](https://github.com/feathersjs/feathers/issues/1092)) ([fd3fc34](https://github.com/feathersjs/feathers/commit/fd3fc34)) ### Features -* Allow registering a service at the root level ([#1115](https://github.com/feathersjs/feathers/issues/1115)) ([c73d322](https://github.com/feathersjs/feathers/commit/c73d322)) - - - - +- Allow registering a service at the root level ([#1115](https://github.com/feathersjs/feathers/issues/1115)) ([c73d322](https://github.com/feathersjs/feathers/commit/c73d322)) + ## [1.2.7](https://github.com/feathersjs/feathers/compare/@feathersjs/express@1.2.6...@feathersjs/express@1.2.7) (2018-09-21) **Note:** Version bump only for package @feathersjs/express - - - - + ## [1.2.6](https://github.com/feathersjs/feathers/compare/@feathersjs/express@1.2.5...@feathersjs/express@1.2.6) (2018-09-17) **Note:** Version bump only for package @feathersjs/express - - - - + ## [1.2.5](https://github.com/feathersjs/feathers/compare/@feathersjs/express@1.2.4...@feathersjs/express@1.2.5) (2018-09-02) **Note:** Version bump only for package @feathersjs/express + ## 1.2.4 - Migrate to Monorepo ([feathers#462](https://github.com/feathersjs/feathers/issues/462)) ## [v1.2.3](https://github.com/feathersjs/express/tree/v1.2.3) (2018-06-03) + [Full Changelog](https://github.com/feathersjs/express/compare/v1.2.2...v1.2.3) **Closed issues:** @@ -631,6 +466,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Update uberproto to the latest version [\#28](https://github.com/feathersjs/express/pull/28) ([bertho-zero](https://github.com/bertho-zero)) ## [v1.2.2](https://github.com/feathersjs/express/tree/v1.2.2) (2018-04-16) + [Full Changelog](https://github.com/feathersjs/express/compare/v1.2.1...v1.2.2) **Merged pull requests:** @@ -638,6 +474,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Allow multiple express middleware functions to be passed into `app.use` [\#25](https://github.com/feathersjs/express/pull/25) ([eXigentCoder](https://github.com/eXigentCoder)) ## [v1.2.1](https://github.com/feathersjs/express/tree/v1.2.1) (2018-03-29) + [Full Changelog](https://github.com/feathersjs/express/compare/v1.2.0...v1.2.1) **Closed issues:** @@ -651,11 +488,12 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Update axios to the latest version 🚀 [\#22](https://github.com/feathersjs/express/pull/22) ([greenkeeper[bot]](https://github.com/apps/greenkeeper)) ## [v1.2.0](https://github.com/feathersjs/express/tree/v1.2.0) (2018-02-09) + [Full Changelog](https://github.com/feathersjs/express/compare/v1.1.2...v1.2.0) **Closed issues:** -- Error in `create` method results in unhandled rejection [\#19](https://github.com/feathersjs/express/issues/19) +- Error in `create` method results in unhandled rejection [\#19](https://github.com/feathersjs/express/issues/19) - @feathersjs/express call without paramaters could returns an instance of express [\#18](https://github.com/feathersjs/express/issues/18) - Feathers-express blows up the feathers application version property and the example doesn't work [\#16](https://github.com/feathersjs/express/issues/16) @@ -667,6 +505,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Update semistandard to the latest version 🚀 [\#14](https://github.com/feathersjs/express/pull/14) ([greenkeeper[bot]](https://github.com/apps/greenkeeper)) ## [v1.1.2](https://github.com/feathersjs/express/tree/v1.1.2) (2017-11-16) + [Full Changelog](https://github.com/feathersjs/express/compare/v1.1.1...v1.1.2) **Merged pull requests:** @@ -674,6 +513,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Export default and original Express object [\#12](https://github.com/feathersjs/express/pull/12) ([daffl](https://github.com/daffl)) ## [v1.1.1](https://github.com/feathersjs/express/tree/v1.1.1) (2017-11-06) + [Full Changelog](https://github.com/feathersjs/express/compare/v1.1.0...v1.1.1) **Merged pull requests:** @@ -681,6 +521,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Also add notFound to export [\#11](https://github.com/feathersjs/express/pull/11) ([daffl](https://github.com/daffl)) ## [v1.1.0](https://github.com/feathersjs/express/tree/v1.1.0) (2017-11-05) + [Full Changelog](https://github.com/feathersjs/express/compare/v1.0.0...v1.1.0) **Merged pull requests:** @@ -688,9 +529,11 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Re-export Express error handler [\#10](https://github.com/feathersjs/express/pull/10) ([daffl](https://github.com/daffl)) ## [v1.0.0](https://github.com/feathersjs/express/tree/v1.0.0) (2017-11-01) + [Full Changelog](https://github.com/feathersjs/express/compare/v1.0.0-pre.4...v1.0.0) ## [v1.0.0-pre.4](https://github.com/feathersjs/express/tree/v1.0.0-pre.4) (2017-10-25) + [Full Changelog](https://github.com/feathersjs/express/compare/v1.0.0-pre.3...v1.0.0-pre.4) **Merged pull requests:** @@ -698,6 +541,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Update to better returnHook handling [\#9](https://github.com/feathersjs/express/pull/9) ([daffl](https://github.com/daffl)) ## [v1.0.0-pre.3](https://github.com/feathersjs/express/tree/v1.0.0-pre.3) (2017-10-21) + [Full Changelog](https://github.com/feathersjs/express/compare/v1.0.0-pre.2...v1.0.0-pre.3) **Merged pull requests:** @@ -707,6 +551,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Update axios to the latest version 🚀 [\#6](https://github.com/feathersjs/express/pull/6) ([greenkeeper[bot]](https://github.com/apps/greenkeeper)) ## [v1.0.0-pre.2](https://github.com/feathersjs/express/tree/v1.0.0-pre.2) (2017-10-18) + [Full Changelog](https://github.com/feathersjs/express/compare/v1.0.0-pre.1...v1.0.0-pre.2) **Merged pull requests:** @@ -716,10 +561,9 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Update debug to the latest version 🚀 [\#2](https://github.com/feathersjs/express/pull/2) ([greenkeeper[bot]](https://github.com/apps/greenkeeper)) ## [v1.0.0-pre.1](https://github.com/feathersjs/express/tree/v1.0.0-pre.1) (2017-07-19) + **Merged pull requests:** - Update dependencies to enable Greenkeeper 🌴 [\#1](https://github.com/feathersjs/express/pull/1) ([greenkeeper[bot]](https://github.com/apps/greenkeeper)) - - -\* *This Change Log was automatically generated by [github_changelog_generator](https://github.com/skywinder/Github-Changelog-Generator)* +\* _This Change Log was automatically generated by [github_changelog_generator](https://github.com/skywinder/Github-Changelog-Generator)_ diff --git a/packages/express/LICENSE b/packages/express/LICENSE index 9f0c6ea9b0..b8be257c56 100644 --- a/packages/express/LICENSE +++ b/packages/express/LICENSE @@ -1,6 +1,6 @@ The MIT License (MIT) -Copyright (c) 2021 Feathers +Copyright (c) 2022 Feathers Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated documentation files (the "Software"), to deal diff --git a/packages/express/README.md b/packages/express/README.md index 275b6cd760..1be7ef5171 100644 --- a/packages/express/README.md +++ b/packages/express/README.md @@ -1,8 +1,8 @@ # @feathersjs/express [![CI](https://github.com/feathersjs/feathers/workflows/CI/badge.svg)](https://github.com/feathersjs/feathers/actions?query=workflow%3ACI) -[![Dependency Status](https://img.shields.io/david/feathersjs/feathers.svg?style=flat-square&path=packages/express)](https://david-dm.org/feathersjs/feathers?path=packages/express) [![Download Status](https://img.shields.io/npm/dm/@feathersjs/express.svg?style=flat-square)](https://www.npmjs.com/package/@feathersjs/express) +[![Discord](https://badgen.net/badge/icon/discord?icon=discord&label)](https://discord.gg/qa8kez8QBx) > Feathers Express framework bindings and REST provider @@ -18,6 +18,6 @@ Refer to the [Feathers Express API documentation](https://docs.feathersjs.com/ap ## License -Copyright (c) 2021 [Feathers contributors](https://github.com/feathersjs/feathers/graphs/contributors) +Copyright (c) 2022 [Feathers contributors](https://github.com/feathersjs/feathers/graphs/contributors) Licensed under the [MIT license](LICENSE). diff --git a/packages/express/package.json b/packages/express/package.json index 4c4cfd6fb7..50a01ecce1 100644 --- a/packages/express/package.json +++ b/packages/express/package.json @@ -1,9 +1,10 @@ { "name": "@feathersjs/express", "description": "Feathers Express framework bindings and REST provider", - "version": "5.0.0-pre.16", + "version": "5.0.0-pre.31", "homepage": "https://feathersjs.com", "main": "lib/", + "types": "lib/", "keywords": [ "feathers", "feathers-plugin" @@ -15,7 +16,8 @@ }, "repository": { "type": "git", - "url": "git://github.com/feathersjs/feathers.git" + "url": "git://github.com/feathersjs/feathers.git", + "directory": "packages/express" }, "author": { "name": "Feathers contributors", @@ -39,7 +41,8 @@ ], "scripts": { "prepublish": "npm run compile", - "compile": "shx rm -rf lib/ && tsc", + "pack": "npm pack --pack-destination ../cli/test/build", + "compile": "shx rm -rf lib/ && tsc && npm run pack", "test": "mocha --config ../../.mocharc.json --recursive test/**.test.ts test/**/*.test.ts" }, "directories": { @@ -49,27 +52,28 @@ "access": "public" }, "dependencies": { - "@feathersjs/authentication": "^5.0.0-pre.16", - "@feathersjs/commons": "^5.0.0-pre.16", - "@feathersjs/errors": "^5.0.0-pre.16", - "@feathersjs/feathers": "^5.0.0-pre.16", - "@feathersjs/transport-commons": "^5.0.0-pre.16", - "@types/express": "^4.17.13", - "@types/express-serve-static-core": "^4.17.27", - "express": "^4.17.2" + "@feathersjs/authentication": "^5.0.0-pre.31", + "@feathersjs/commons": "^5.0.0-pre.31", + "@feathersjs/errors": "^5.0.0-pre.31", + "@feathersjs/feathers": "^5.0.0-pre.31", + "@feathersjs/transport-commons": "^5.0.0-pre.31", + "@types/express": "^4.17.14", + "@types/express-serve-static-core": "^4.17.31", + "cors": "^2.8.5", + "express": "^4.18.1" }, "devDependencies": { - "@feathersjs/authentication-local": "^5.0.0-pre.16", - "@feathersjs/tests": "^5.0.0-pre.16", - "@types/lodash": "^4.14.178", - "@types/mocha": "^9.0.0", - "@types/node": "^17.0.5", - "axios": "^0.24.0", + "@feathersjs/authentication-local": "^5.0.0-pre.31", + "@feathersjs/tests": "^5.0.0-pre.31", + "@types/lodash": "^4.14.186", + "@types/mocha": "^10.0.0", + "@types/node": "^18.8.2", + "axios": "^0.27.2", "lodash": "^4.17.21", - "mocha": "^9.1.3", - "shx": "^0.3.3", - "ts-node": "^10.4.0", - "typescript": "^4.5.4" + "mocha": "^10.0.0", + "shx": "^0.3.4", + "ts-node": "^10.9.1", + "typescript": "^4.8.4" }, - "gitHead": "f0cd227a82d159b528193bd33747c97684a48773" + "gitHead": "4500dbeb8cea566678cf88b3313a88efd93a2ed9" } diff --git a/packages/express/src/authentication.ts b/packages/express/src/authentication.ts index 4172c80c67..519e7e32e2 100644 --- a/packages/express/src/authentication.ts +++ b/packages/express/src/authentication.ts @@ -1,61 +1,66 @@ -import { RequestHandler, Request, Response } from 'express'; -import { HookContext } from '@feathersjs/feathers'; -import { createDebug } from '@feathersjs/commons'; -import { authenticate as AuthenticateHook } from '@feathersjs/authentication'; +import { RequestHandler, Request, Response } from 'express' +import { HookContext } from '@feathersjs/feathers' +import { createDebug } from '@feathersjs/commons' +import { authenticate as AuthenticateHook } from '@feathersjs/authentication' -import { Application } from './declarations'; +import { Application } from './declarations' -const debug = createDebug('@feathersjs/express/authentication'); +const debug = createDebug('@feathersjs/express/authentication') -const toHandler = (func: (req: Request, res: Response, next: () => void) => Promise): RequestHandler => { - return (req, res, next) => func(req, res, next).catch(error => next(error)); -}; +const toHandler = ( + func: (req: Request, res: Response, next: () => void) => Promise +): RequestHandler => { + return (req, res, next) => func(req, res, next).catch((error) => next(error)) +} export type AuthenticationSettings = { - service?: string; - strategies?: string[]; -}; + service?: string + strategies?: string[] +} -export function parseAuthentication (settings: AuthenticationSettings = {}): RequestHandler { +export function parseAuthentication(settings: AuthenticationSettings = {}): RequestHandler { return toHandler(async (req, res, next) => { - const app = req.app as any as Application; - const service = app.defaultAuthentication?.(settings.service); + const app = req.app as any as Application + const service = app.defaultAuthentication?.(settings.service) if (!service) { - return next(); + return next() } - const config = service.configuration; - const authStrategies = settings.strategies || config.parseStrategies || config.authStrategies || []; + const config = service.configuration + const authStrategies = settings.strategies || config.parseStrategies || config.authStrategies || [] if (authStrategies.length === 0) { - debug('No `authStrategies` or `parseStrategies` found in authentication configuration'); - return next(); + debug('No `authStrategies` or `parseStrategies` found in authentication configuration') + return next() } const authentication = await service.parse(req, res, ...authStrategies) if (authentication) { - debug('Parsed authentication from HTTP header', authentication); - req.feathers = { ...req.feathers, authentication }; + debug('Parsed authentication from HTTP header', authentication) + req.feathers = { ...req.feathers, authentication } } - return next(); - }); + return next() + }) } -export function authenticate (settings: string | AuthenticationSettings, ...strategies: string[]): RequestHandler { - const hook = AuthenticateHook(settings, ...strategies); +export function authenticate( + settings: string | AuthenticationSettings, + ...strategies: string[] +): RequestHandler { + const hook = AuthenticateHook(settings, ...strategies) return toHandler(async (req, _res, next) => { - const app = req.app as any as Application; - const params = req.feathers; - const context = { app, params } as any as HookContext; + const app = req.app as any as Application + const params = req.feathers + const context = { app, params } as any as HookContext - await hook(context); + await hook(context) - req.feathers = context.params; + req.feathers = context.params - return next(); - }); + return next() + }) } diff --git a/packages/express/src/declarations.ts b/packages/express/src/declarations.ts index 6418587b25..a4f9665e7a 100644 --- a/packages/express/src/declarations.ts +++ b/packages/express/src/declarations.ts @@ -1,62 +1,68 @@ -import http from 'http'; -import express, { Express } from 'express'; +import http from 'http' +import express, { Express } from 'express' import { - Application as FeathersApplication, Params as FeathersParams, - HookContext, ServiceMethods, ServiceInterface, RouteLookup -} from '@feathersjs/feathers'; + Application as FeathersApplication, + Params as FeathersParams, + HookContext, + ServiceMethods, + ServiceInterface, + RouteLookup +} from '@feathersjs/feathers' interface ExpressUseHandler { - ( + ( path: L, ...middlewareOrService: ( - Express|express.RequestHandler| - (keyof any extends keyof Services ? ServiceInterface : Services[L]) + | Express + | express.RequestHandler + | express.RequestHandler[] + | (keyof any extends keyof Services ? ServiceInterface : Services[L]) )[] - ): T; - (path: string|RegExp, ...expressHandlers: express.RequestHandler[]): T; - (...expressHandlers: express.RequestHandler[]): T; - (handler: Express|express.ErrorRequestHandler): T; + ): T + (path: string | RegExp, ...expressHandlers: express.RequestHandler[]): T + (...expressHandlers: express.RequestHandler[]): T + (handler: Express | express.ErrorRequestHandler): T } export interface ExpressOverrides { - listen(port: number, hostname: string, backlog: number, callback?: () => void): Promise; - listen(port: number, hostname: string, callback?: () => void): Promise; - listen(port: number|string|any, callback?: () => void): Promise; - listen(callback?: () => void): Promise; - use: ExpressUseHandler; + listen(port: number, hostname: string, backlog: number, callback?: () => void): Promise + listen(port: number, hostname: string, callback?: () => void): Promise + listen(port: number | string | any, callback?: () => void): Promise + listen(callback?: () => void): Promise + use: ExpressUseHandler + server?: http.Server } -export type Application = - Omit & +export type Application = Omit & FeathersApplication & - ExpressOverrides; + ExpressOverrides declare module '@feathersjs/feathers/lib/declarations' { interface ServiceOptions { express?: { - before?: express.RequestHandler[]; - after?: express.RequestHandler[]; - composed?: express.RequestHandler; - }; + before?: express.RequestHandler[] + after?: express.RequestHandler[] + composed?: express.RequestHandler + } } } declare module 'express-serve-static-core' { interface Request { - feathers?: Partial; - lookup?: RouteLookup; + feathers?: Partial & { [key: string]: any } + lookup?: RouteLookup } interface Response { - data?: any; - hook?: HookContext; + data?: any + hook?: HookContext } interface IRouterMatcher { // eslint-disable-next-line

( - path: PathParams, - ...handlers: (RequestHandler | Partial | Application)[] - ): T; + path: PathParams, + ...handlers: (RequestHandler | Partial | Application)[] + ): T } } diff --git a/packages/express/src/handlers.ts b/packages/express/src/handlers.ts index 364d8d4192..73c162759c 100644 --- a/packages/express/src/handlers.ts +++ b/packages/express/src/handlers.ts @@ -1,130 +1,132 @@ -import path from 'path'; -import { NotFound, GeneralError } from '@feathersjs/errors'; -import { Request, Response, NextFunction, ErrorRequestHandler, RequestHandler } from 'express'; +import path from 'path' +import { NotFound, GeneralError } from '@feathersjs/errors' +import { Request, Response, NextFunction, ErrorRequestHandler, RequestHandler } from 'express' const defaults = { public: path.resolve(__dirname, '..', 'public'), logger: console -}; -const defaultHtmlError = path.resolve(defaults.public, 'default.html'); +} +const defaultHtmlError = path.resolve(defaults.public, 'default.html') -export function notFound ({ verbose = false } = {}): RequestHandler { +export function notFound({ verbose = false } = {}): RequestHandler { return function (req: Request, _res: Response, next: NextFunction) { - const url = `${req.url}`; - const message = `Page not found${verbose ? ': ' + url : ''}`; + const url = `${req.url}` + const message = `Page not found${verbose ? ': ' + url : ''}` - next(new NotFound(message, { url })); - }; + next(new NotFound(message, { url })) + } } export type ErrorHandlerOptions = { - public?: string; - logger?: boolean|{ error?: (msg: any) => void, info?: (msg: any) => void }; - html?: any; - json?: any; -}; + public?: string + logger?: boolean | { error?: (msg: any) => void; info?: (msg: any) => void } + html?: any + json?: any +} -export function errorHandler (_options: ErrorHandlerOptions = {}): ErrorRequestHandler { - const options = Object.assign({}, defaults, _options); +export function errorHandler(_options: ErrorHandlerOptions = {}): ErrorRequestHandler { + const options = Object.assign({}, defaults, _options) if (typeof options.html === 'undefined') { options.html = { 401: path.resolve(options.public, '401.html'), 404: path.resolve(options.public, '404.html'), default: defaultHtmlError - }; + } } if (typeof options.json === 'undefined') { - options.json = {}; + options.json = {} } return function (error: any, req: Request, res: Response, next: NextFunction) { // Set the error code for HTTP processing semantics - error.code = !isNaN(parseInt(error.code, 10)) ? parseInt(error.code, 10) : 500; + error.code = !isNaN(parseInt(error.code, 10)) ? parseInt(error.code, 10) : 500 // Log the error if it didn't come from a service method call if (options.logger && typeof options.logger.error === 'function' && !res.hook) { if (error.code >= 500) { - options.logger.error(error); + options.logger.error(error) } else { - options.logger.info(error); + options.logger.info(error) } } if (error.type !== 'FeathersError') { - const oldError = error; + const oldError = error - error = oldError.errors ? new GeneralError(oldError.message, { - errors: oldError.errors - }) : new GeneralError(oldError.message); + error = oldError.errors + ? new GeneralError(oldError.message, { + errors: oldError.errors + }) + : new GeneralError(oldError.message) if (oldError.stack) { - error.stack = oldError.stack; + error.stack = oldError.stack } } - const formatter: { [key: string]: any } = {}; + const formatter: { [key: string]: any } = {} // If the developer passed a custom function for ALL html errors if (typeof options.html === 'function') { - formatter['text/html'] = options.html; + formatter['text/html'] = options.html } else { - let file = options.html[error.code]; + let file = options.html[error.code] if (!file) { - file = options.html.default || defaultHtmlError; + file = options.html.default || defaultHtmlError } // If the developer passed a custom function for individual html errors if (typeof file === 'function') { - formatter['text/html'] = file; + formatter['text/html'] = file } else { formatter['text/html'] = function () { - res.set('Content-Type', 'text/html'); - res.sendFile(file); - }; + res.set('Content-Type', 'text/html') + res.sendFile(file) + } } } // If the developer passed a custom function for ALL json errors if (typeof options.json === 'function') { - formatter['application/json'] = options.json; + formatter['application/json'] = options.json } else { - const handler = options.json[error.code] || options.json.default; + const handler = options.json[error.code] || options.json.default // If the developer passed a custom function for individual json errors if (typeof handler === 'function') { - formatter['application/json'] = handler; + formatter['application/json'] = handler } else { // Don't show stack trace if it is a 404 error if (error.code === 404) { - error.stack = null; + error.stack = null } formatter['application/json'] = function () { - const output = Object.assign({}, error.toJSON()); + const output = Object.assign({}, error.toJSON()) if (process.env.NODE_ENV === 'production') { - delete output.stack; + delete output.stack } - res.set('Content-Type', 'application/json'); - res.json(output); - }; + res.set('Content-Type', 'application/json') + res.json(output) + } } } - res.status(error.code); + res.status(error.code) - const contentType = req.headers['content-type'] || ''; - const accepts = req.headers.accept || ''; + const contentType = req.headers['content-type'] || '' + const accepts = req.headers.accept || '' // by default just send back json if (contentType.indexOf('json') !== -1 || accepts.indexOf('json') !== -1) { - formatter['application/json'](error, req, res, next); + formatter['application/json'](error, req, res, next) } else if (options.html && (contentType.indexOf('html') !== -1 || accepts.indexOf('html') !== -1)) { - formatter['text/html'](error, req, res, next); + formatter['text/html'](error, req, res, next) } else { // TODO (EK): Maybe just return plain text - formatter['application/json'](error, req, res, next); + formatter['application/json'](error, req, res, next) } - }; + } } diff --git a/packages/express/src/index.ts b/packages/express/src/index.ts index 5a0249e446..4699da5da0 100644 --- a/packages/express/src/index.ts +++ b/packages/express/src/index.ts @@ -1,112 +1,150 @@ -import express, { Express } from 'express'; -import { Application as FeathersApplication, defaultServiceMethods } from '@feathersjs/feathers'; -import { routing } from '@feathersjs/transport-commons'; -import { createDebug } from '@feathersjs/commons'; - -import { Application } from './declarations'; - -export { default as original, static, static as serveStatic, json, raw, text, urlencoded, query } from 'express'; - -export * from './authentication'; -export * from './declarations'; -export * from './handlers'; -export * from './rest'; +import express, { Express } from 'express' +import { Application as FeathersApplication, defaultServiceMethods } from '@feathersjs/feathers' +import { routing } from '@feathersjs/transport-commons' +import { createDebug } from '@feathersjs/commons' +import cors from 'cors' + +import { rest, RestOptions, formatter } from './rest' +import { errorHandler, notFound, ErrorHandlerOptions } from './handlers' +import { Application, ExpressOverrides } from './declarations' +import { AuthenticationSettings, authenticate, parseAuthentication } from './authentication' +import { default as original, static as serveStatic, json, raw, text, urlencoded, query } from 'express' + +export { + original, + serveStatic, + serveStatic as static, + json, + raw, + text, + urlencoded, + query, + rest, + RestOptions, + formatter, + errorHandler, + notFound, + Application, + ErrorHandlerOptions, + ExpressOverrides, + AuthenticationSettings, + parseAuthentication, + authenticate, + cors +} -const debug = createDebug('@feathersjs/express'); +const debug = createDebug('@feathersjs/express') -export default function feathersExpress (feathersApp?: FeathersApplication, expressApp: Express = express()): Application { +export default function feathersExpress( + feathersApp?: FeathersApplication, + expressApp: Express = express() +): Application { if (!feathersApp) { - return expressApp as any; + return expressApp as any } if (typeof feathersApp.setup !== 'function') { - throw new Error('@feathersjs/express requires a valid Feathers application instance'); + throw new Error('@feathersjs/express requires a valid Feathers application instance') } - const app = expressApp as any as Application; - const { use: expressUse, listen: expressListen } = expressApp as any; - const feathersUse = feathersApp.use; + const app = expressApp as any as Application + const { use: expressUse, listen: expressListen } = expressApp as any + const { use: feathersUse, teardown: feathersTeardown } = feathersApp Object.assign(app, { - use (location: string & keyof S, ...rest: any[]) { - let service: any; - let options = {}; + use(location: string & keyof S, ...rest: any[]) { + let service: any + let options = {} - const middleware = rest.reduce(function (middleware, arg) { + const middleware = rest.reduce( + function (middleware, arg) { if (typeof arg === 'function' || Array.isArray(arg)) { - middleware[service ? 'after' : 'before'].push(arg); + middleware[service ? 'after' : 'before'].push(arg) } else if (!service) { - service = arg; - } else if (arg.methods || arg.events) { - options = arg; + service = arg + } else if (arg.methods || arg.events || arg.express || arg.koa) { + options = arg } else { - throw new Error('Invalid options passed to app.use'); + throw new Error('Invalid options passed to app.use') } - return middleware; - }, { + return middleware + }, + { before: [], after: [] - }); + } + ) - const hasMethod = (methods: string[]) => methods.some(name => - (service && typeof service[name] === 'function') - ); + const hasMethod = (methods: string[]) => + methods.some((name) => service && typeof service[name] === 'function') // Check for service (any object with at least one service method) if (hasMethod(['handle', 'set']) || !hasMethod(defaultServiceMethods)) { - debug('Passing app.use call to Express app'); - return expressUse.call(this, location, ...rest); + debug('Passing app.use call to Express app') + return expressUse.call(this, location, ...rest) } - debug('Registering service with middleware', middleware); + debug('Registering service with middleware', middleware) // Since this is a service, call Feathers `.use` feathersUse.call(this, location, service, { - ...options, - express: middleware - }); + express: middleware, + ...options + }) - return this; + return this }, - async listen (...args: any[]) { - const server = expressListen.call(this, ...args); + async listen(...args: any[]) { + const server = expressListen.call(this, ...args) - await this.setup(server); - debug('Feathers application listening'); + this.server = server + await this.setup(server) + debug('Feathers application listening') - return server; + return server } - } as Application); + } as Application) const appDescriptors = { ...Object.getOwnPropertyDescriptors(Object.getPrototypeOf(app)), ...Object.getOwnPropertyDescriptors(app) - }; + } const newDescriptors = { ...Object.getOwnPropertyDescriptors(Object.getPrototypeOf(feathersApp)), ...Object.getOwnPropertyDescriptors(feathersApp) - }; + } // Copy all non-existing properties (including non-enumerables) // that don't already exist on the Express app - Object.keys(newDescriptors).forEach(prop => { - const appProp = appDescriptors[prop]; - const newProp = newDescriptors[prop]; + Object.keys(newDescriptors).forEach((prop) => { + const appProp = appDescriptors[prop] + const newProp = newDescriptors[prop] if (appProp === undefined && newProp !== undefined) { - Object.defineProperty(expressApp, prop, newProp); + Object.defineProperty(expressApp, prop, newProp) } - }); + }) + + // Assign teardown and setup which will also make sure that hooks are initialized + app.setup = feathersApp.setup as any + app.teardown = async function teardown(server?: any) { + return feathersTeardown.call(this, server).then( + () => + new Promise((resolve, reject) => { + if (this.server) { + this.server.close((e) => (e ? reject(e) : resolve(this))) + } else { + resolve(this) + } + }) + ) + } - app.configure(routing() as any); - app.use((req, _res, next) => { - req.feathers = { ...req.feathers, provider: 'rest' }; - return next(); - }); + app.configure(routing() as any) - return app; + return app } if (typeof module !== 'undefined') { - module.exports = Object.assign(feathersExpress, module.exports); + module.exports = Object.assign(feathersExpress, module.exports) } diff --git a/packages/express/src/rest.ts b/packages/express/src/rest.ts index 35e280e484..2949880041 100644 --- a/packages/express/src/rest.ts +++ b/packages/express/src/rest.ts @@ -1,111 +1,117 @@ -import { Request, Response, RequestHandler, Router } from 'express'; -import { MethodNotAllowed } from '@feathersjs/errors'; -import { createDebug } from '@feathersjs/commons'; -import { http } from '@feathersjs/transport-commons'; -import { createContext, defaultServiceMethods, getServiceOptions } from '@feathersjs/feathers'; +import { Request, Response, RequestHandler, Router } from 'express' +import { MethodNotAllowed } from '@feathersjs/errors' +import { createDebug } from '@feathersjs/commons' +import { http } from '@feathersjs/transport-commons' +import { createContext, defaultServiceMethods, getServiceOptions } from '@feathersjs/feathers' -import { AuthenticationSettings, parseAuthentication } from './authentication'; -import { Application } from './declarations'; +import { AuthenticationSettings, parseAuthentication } from './authentication' +import { Application } from './declarations' -const debug = createDebug('@feathersjs/express/rest'); +const debug = createDebug('@feathersjs/express/rest') -const toHandler = (func: (req: Request, res: Response, next: () => void) => Promise): RequestHandler => { - return (req, res, next) => func(req, res, next).catch(error => next(error)); -}; +const toHandler = ( + func: (req: Request, res: Response, next: () => void) => Promise +): RequestHandler => { + return (req, res, next) => func(req, res, next).catch((error) => next(error)) +} const serviceMiddleware = (): RequestHandler => { return toHandler(async (req, res, next) => { - const { query, headers, path, body: data, method: httpMethod } = req; - const methodOverride = req.headers[http.METHOD_HEADER] as string | undefined; + const { query, headers, path, body: data, method: httpMethod } = req + const methodOverride = req.headers[http.METHOD_HEADER] as string | undefined - const { service, params: { __id: id = null, ...route } = {} } = req.lookup!; - const method = http.getServiceMethod(httpMethod, id, methodOverride); - const { methods } = getServiceOptions(service); + // eslint-disable-next-line @typescript-eslint/no-non-null-assertion + const { service, params: { __id: id = null, ...route } = {} } = req.lookup! + const method = http.getServiceMethod(httpMethod, id, methodOverride) + const { methods } = getServiceOptions(service) - debug(`Found service for path ${path}, attempting to run '${method}' service method`); + debug(`Found service for path ${path}, attempting to run '${method}' service method`) if (!methods.includes(method) || defaultServiceMethods.includes(methodOverride)) { - const error = new MethodNotAllowed(`Method \`${method}\` is not supported by this endpoint.`); - res.statusCode = error.code; - throw error; + const error = new MethodNotAllowed(`Method \`${method}\` is not supported by this endpoint.`) + res.statusCode = error.code + throw error } - const createArguments = http.argumentsFor[method as 'get'] || http.argumentsFor.default; - const params = { query, headers, route, ...req.feathers }; - const args = createArguments({ id, data, params }); - const contextBase = createContext(service, method, { http: {} }); - res.hook = contextBase; - - const context = await (service as any)[method](...args, contextBase); - res.hook = context; + const createArguments = http.argumentsFor[method as 'get'] || http.argumentsFor.default + const params = { query, headers, route, ...req.feathers } + const args = createArguments({ id, data, params }) + const contextBase = createContext(service, method, { http: {} }) + res.hook = contextBase - const result = http.getData(context); - const statusCode = http.getStatusCode(context, result); + const context = await (service as any)[method](...args, contextBase) + res.hook = context - res.data = result; - res.statusCode = statusCode; + const response = http.getResponse(context) + res.statusCode = response.status + res.set(response.headers) + res.data = response.body - return next(); - }); -}; + return next() + }) +} const servicesMiddleware = (): RequestHandler => { return toHandler(async (req, res, next) => { - const app = req.app as any as Application; - const lookup = app.lookup(req.path); + const app = req.app as any as Application + const lookup = app.lookup(req.path) if (!lookup) { - return next(); + return next() } - req.lookup = lookup; + req.lookup = lookup - const options = getServiceOptions(lookup.service); - const middleware = options.express!.composed!; + const options = getServiceOptions(lookup.service) + const middleware = options.express.composed - return middleware(req, res, next); - }); -}; + return middleware(req, res, next) + }) +} export const formatter: RequestHandler = (_req, res, next) => { if (res.data === undefined) { - return next(); + return next() } res.format({ - 'application/json' () { - res.json(res.data); + 'application/json'() { + res.json(res.data) } - }); -}; + }) +} export type RestOptions = { - formatter?: RequestHandler; - authentication?: AuthenticationSettings; -}; + formatter?: RequestHandler + authentication?: AuthenticationSettings +} export const rest = (options?: RestOptions | RequestHandler) => { - options = typeof options === 'function' ? { formatter: options } : options || {}; + options = typeof options === 'function' ? { formatter: options } : options || {} - const formatterMiddleware = options.formatter || formatter; - const authenticationOptions = options.authentication; + const formatterMiddleware = options.formatter || formatter + const authenticationOptions = options.authentication return (app: Application) => { if (typeof app.route !== 'function') { - throw new Error('@feathersjs/express/rest needs an Express compatible app.'); + throw new Error('@feathersjs/express/rest needs an Express compatible app.') } - app.use(parseAuthentication(authenticationOptions)); - app.use(servicesMiddleware()); + app.use((req, _res, next) => { + req.feathers = { ...req.feathers, provider: 'rest' } + return next() + }) + app.use(parseAuthentication(authenticationOptions)) + app.use(servicesMiddleware()) app.mixins.push((_service, _path, options) => { - const { express: { before = [], after = [] } = {} } = options; + const { express: { before = [], after = [] } = {} } = options - const middlewares = [].concat(before, serviceMiddleware(), after, formatterMiddleware); - const middleware = Router().use(middlewares); + const middlewares = [].concat(before, serviceMiddleware(), after, formatterMiddleware) + const middleware = Router().use(middlewares) - options.express ||= {}; - options.express.composed = middleware; - }); - }; + options.express ||= {} + options.express.composed = middleware + }) + } } diff --git a/packages/express/test/authentication.test.ts b/packages/express/test/authentication.test.ts index 020d54a2bb..9a342f39de 100644 --- a/packages/express/test/authentication.test.ts +++ b/packages/express/test/authentication.test.ts @@ -1,77 +1,77 @@ -import { omit } from 'lodash'; -import { strict as assert } from 'assert'; -import { default as _axios } from 'axios'; -import { feathers } from '@feathersjs/feathers'; -import { createApplication } from '@feathersjs/authentication-local/test/fixture'; -import { authenticate, AuthenticationResult } from '@feathersjs/authentication'; -import * as express from '../src'; - -const expressify = express.default; +/* eslint-disable @typescript-eslint/ban-ts-comment */ +import { omit } from 'lodash' +import { strict as assert } from 'assert' +import { default as _axios } from 'axios' +import { feathers } from '@feathersjs/feathers' +import { createApplication } from '@feathersjs/authentication-local/test/fixture' +import { authenticate, AuthenticationResult } from '@feathersjs/authentication' +import * as express from '../src' + +const expressify = express.default const axios = _axios.create({ baseURL: 'http://localhost:9876/' -}); +}) describe('@feathersjs/express/authentication', () => { - const email = 'expresstest@authentication.com'; - const password = 'superexpress'; + const email = 'expresstest@authentication.com' + const password = 'superexpress' - let app: express.Application; - let server: any; - let user: any; - let authResult: AuthenticationResult; + let app: express.Application + let user: any + let authResult: AuthenticationResult before(async () => { - const expressApp = expressify(feathers()) - .use(express.json()) - .configure(express.rest()); + const expressApp = expressify(feathers()).use(express.json()).configure(express.rest()) - app = createApplication(expressApp as any) as unknown as express.Application; - server = await app.listen(9876); + app = createApplication(expressApp as any) as unknown as express.Application + + await app.listen(9876) app.use('/dummy', { - get (id, params) { - return Promise.resolve({ id, params }); + get(id, params) { + return Promise.resolve({ id, params }) } - }); + }) - //@ts-ignore + // @ts-ignore app.use('/protected', express.authenticate('jwt'), (req, res) => { - res.json(req.feathers.user); - }); + res.json(req.feathers.user) + }) - app.use(express.errorHandler({ - logger: false - })); + app.use( + express.errorHandler({ + logger: false + }) + ) app.service('dummy').hooks({ - before: [ authenticate('jwt') ] - }); + before: [authenticate('jwt')] + }) - const result = await app.service('users').create({ email, password }); + const result = await app.service('users').create({ email, password }) - user = result; + user = result const res = await axios.post('/authentication', { strategy: 'local', password, email - }); + }) - authResult = res.data; - }); + authResult = res.data + }) - after(done => server.close(done)); + after(() => app.teardown()) describe('service authentication', () => { it('successful local authentication', () => { - assert.ok(authResult.accessToken); + assert.ok(authResult.accessToken) assert.deepStrictEqual(omit(authResult.authentication, 'payload'), { - strategy: 'local', - accessToken: authResult.accessToken - }); - assert.strictEqual(authResult.user.email, email); - assert.strictEqual(authResult.user.password, undefined); - }); + strategy: 'local' + }) + assert.strictEqual(authResult.user.email, email) + assert.strictEqual(authResult.user.password, undefined) + }) it('local authentication with wrong password fails', async () => { try { @@ -79,96 +79,105 @@ describe('@feathersjs/express/authentication', () => { strategy: 'local', password: 'wrong', email - }); - assert.fail('Should never get here'); + }) + assert.fail('Should never get here') } catch (error: any) { - const { data } = error.response; - assert.strictEqual(data.name, 'NotAuthenticated'); - assert.strictEqual(data.message, 'Invalid login'); + const { data } = error.response + assert.strictEqual(data.name, 'NotAuthenticated') + assert.strictEqual(data.message, 'Invalid login') } - }); + }) it('authenticating with JWT works but returns same accessToken', async () => { - const { accessToken } = authResult; + const { accessToken } = authResult const { data } = await axios.post('/authentication', { strategy: 'jwt', accessToken - }); + }) - assert.strictEqual(data.accessToken, accessToken); - assert.strictEqual(data.authentication.strategy, 'jwt'); - assert.strictEqual(data.authentication.payload.sub, user.id.toString()); - assert.strictEqual(data.user.email, email); - }); + assert.strictEqual(data.accessToken, accessToken) + assert.strictEqual(data.authentication.strategy, 'jwt') + assert.strictEqual(data.authentication.payload.sub, user.id.toString()) + assert.strictEqual(data.user.email, email) + }) it('can make a protected request with Authorization header', async () => { - const { accessToken } = authResult; + const { accessToken } = authResult - const { data, data: { params } } = await axios.get('/dummy/dave', { + const { + data, + data: { params } + } = await axios.get('/dummy/dave', { headers: { Authorization: accessToken } - }); + }) - assert.strictEqual(data.id, 'dave'); - assert.deepStrictEqual(params.user, user); - assert.strictEqual(params.authentication.accessToken, accessToken); - }); + assert.strictEqual(data.id, 'dave') + assert.deepStrictEqual(params.user, user) + assert.strictEqual(params.authentication.accessToken, accessToken) + }) it('errors when there are no authStrategies and parseStrategies', async () => { - const { accessToken } = authResult; - app.get('authentication').authStrategies = []; - delete app.get('authentication').parseStrategies; + const { accessToken } = authResult + app.get('authentication').authStrategies = [] + delete app.get('authentication').parseStrategies try { await axios.get('/dummy/dave', { headers: { Authorization: accessToken } - }); - assert.fail('Should never get here'); + }) + assert.fail('Should never get here') } catch (error: any) { - assert.strictEqual(error.response.data.name, 'NotAuthenticated'); - app.get('authentication').authStrategies = [ 'jwt', 'local' ]; + assert.strictEqual(error.response.data.name, 'NotAuthenticated') + app.get('authentication').authStrategies = ['jwt', 'local'] } - }); + }) it('can make a protected request with Authorization header and bearer scheme', async () => { - const { accessToken } = authResult; + const { accessToken } = authResult - const { data, data: { params } } = await axios.get('/dummy/dave', { + const { + data, + data: { params } + } = await axios.get('/dummy/dave', { headers: { Authorization: ` Bearer: ${accessToken}` } - }); + }) - assert.strictEqual(data.id, 'dave'); - assert.deepStrictEqual(params.user, user); - assert.strictEqual(params.authentication.accessToken, accessToken); - }); - }); + assert.strictEqual(data.id, 'dave') + assert.deepStrictEqual(params.user, user) + assert.strictEqual(params.authentication.accessToken, accessToken) + }) + }) describe('authenticate middleware', () => { it('errors without valid strategies', () => { try { // @ts-ignore - authenticate(); - assert.fail('Should never get here'); + authenticate() + assert.fail('Should never get here') } catch (error: any) { - assert.strictEqual(error.message, 'The authenticate hook needs at least one allowed strategy'); + assert.strictEqual(error.message, 'The authenticate hook needs at least one allowed strategy') } - }); + }) it('protected endpoint fails when JWT is not present', () => { - return axios.get('/protected').then(() => { - assert.fail('Should never get here'); - }).catch(error => { - const { data } = error.response; - - assert.strictEqual(data.name, 'NotAuthenticated'); - assert.strictEqual(data.message, 'Not authenticated'); - }); - }); + return axios + .get('/protected') + .then(() => { + assert.fail('Should never get here') + }) + .catch((error) => { + const { data } = error.response + + assert.strictEqual(data.name, 'NotAuthenticated') + assert.strictEqual(data.message, 'Not authenticated') + }) + }) it.skip('protected endpoint fails with invalid Authorization header', async () => { try { @@ -176,26 +185,26 @@ describe('@feathersjs/express/authentication', () => { headers: { Authorization: 'Bearer: something wrong' } - }); - assert.fail('Should never get here'); + }) + assert.fail('Should never get here') } catch (error: any) { - const { data } = error.response; + const { data } = error.response - assert.strictEqual(data.name, 'NotAuthenticated'); - assert.strictEqual(data.message, 'Not authenticated'); + assert.strictEqual(data.name, 'NotAuthenticated') + assert.strictEqual(data.message, 'Not authenticated') } - }); + }) it('can request protected endpoint with JWT present', async () => { const { data } = await axios.get('/protected', { headers: { Authorization: `Bearer ${authResult.accessToken}` } - }); - - assert.strictEqual(data.email, user.email); - assert.strictEqual(data.id, user.id); - assert.strictEqual(data.password, user.password); - }); - }); -}); + }) + + assert.strictEqual(data.email, user.email) + assert.strictEqual(data.id, user.id) + assert.strictEqual(data.password, user.password) + }) + }) +}) diff --git a/packages/express/test/error-handler.test.ts b/packages/express/test/error-handler.test.ts index 1ba565b6ae..e12b653d88 100644 --- a/packages/express/test/error-handler.test.ts +++ b/packages/express/test/error-handler.test.ts @@ -1,220 +1,244 @@ -/* eslint-disable @typescript-eslint/no-unused-vars */ -import { strict as assert } from 'assert'; -import express, { Request, Response, NextFunction } from 'express'; -import axios from 'axios'; +/* eslint-disable @typescript-eslint/no-unused-vars, @typescript-eslint/no-empty-function */ +import { strict as assert } from 'assert' +import express, { Request, Response, NextFunction } from 'express' +import axios from 'axios' import fs from 'fs' -import { join } from 'path'; -import { BadRequest, NotAcceptable, NotAuthenticated, NotFound, PaymentError } from '@feathersjs/errors'; +import { join } from 'path' +import { BadRequest, NotAcceptable, NotAuthenticated, NotFound, PaymentError } from '@feathersjs/errors' -import { errorHandler } from '../src'; +import { errorHandler } from '../src' -const content = 'Error'; +const content = 'Error' const htmlHandler = function (_error: Error, _req: Request, res: Response, _next: NextFunction) { - res.send(content); -}; + res.send(content) +} const jsonHandler = function (error: Error, _req: Request, res: Response, _next: NextFunction) { - res.json(error); -}; + res.json(error) +} describe('error-handler', () => { describe('supports catch-all custom handlers', function () { before(function () { - this.app = express().get('/error', function (_req: Request, _res: Response, next: NextFunction) { - next(new Error('Something went wrong')); - }).use(errorHandler({ - html: htmlHandler, - json: jsonHandler - })); + this.app = express() + .get('/error', function (_req: Request, _res: Response, next: NextFunction) { + next(new Error('Something went wrong')) + }) + .use( + errorHandler({ + html: htmlHandler, + json: jsonHandler + }) + ) - this.server = this.app.listen(5050); - }); + this.server = this.app.listen(5050) + }) after(function (done) { - this.server.close(done); - }); + this.server.close(done) + }) describe('JSON handler', () => { const options = { url: 'http://localhost:5050/error', headers: { 'Content-Type': 'application/json', - 'Accept': 'application/json' + Accept: 'application/json' } - }; + } it('can send a custom response', async () => { try { - await axios(options); - assert.fail('Should never get here'); + await axios(options) + assert.fail('Should never get here') } catch (error: any) { assert.deepEqual(error.response.data, { name: 'GeneralError', message: 'Something went wrong', code: 500, className: 'general-error' - }); + }) } - }); - }); - }); + }) + }) + }) describe('supports error-code specific custom handlers', () => { describe('HTML handler', () => { const req = { headers: { 'content-type': 'text/html' } - }; + } const makeRes = (errCode: number, props?: any) => { - return Object.assign({ - set () {}, - status (code: number) { - assert.equal(code, errCode); - } - }, props); - }; + return Object.assign( + { + set() {}, + status(code: number) { + assert.equal(code, errCode) + } + }, + props + ) + } - it('if the value is a string, calls res.sendFile', done => { - const err = new NotAuthenticated(); + it('if the value is a string, calls res.sendFile', (done) => { + const err = new NotAuthenticated() const middleware = errorHandler({ logger: null, html: { 401: 'path/to/401.html' } - }); + }) const res = makeRes(401, { - sendFile (f: any) { - assert.equal(f, 'path/to/401.html'); - done(); + sendFile(f: any) { + assert.equal(f, 'path/to/401.html') + done() } - }); - (middleware as any)(err, req, res); - }); + }) + ;(middleware as any)(err, req, res) + }) - it('if the value is a function, calls as middleware ', done => { - const err = new PaymentError(); - const res = makeRes(402); + it('if the value is a function, calls as middleware ', (done) => { + const err = new PaymentError() + const res = makeRes(402) const middleware = errorHandler({ logger: null, - html: { 402: (_err: any, _req: any, _res: any) => { - assert.equal(_err, err); - assert.equal(_req, req); - assert.equal(_res, res); - done(); - } } - }); - (middleware as any)(err, req, res); - }); + html: { + 402: (_err: any, _req: any, _res: any) => { + assert.equal(_err, err) + assert.equal(_req, req) + assert.equal(_res, res) + done() + } + } + }) + ;(middleware as any)(err, req, res) + }) - it('falls back to default if error code config is available', done => { - const err = new NotAcceptable(); - const res = makeRes(406); + it('falls back to default if error code config is available', (done) => { + const err = new NotAcceptable() + const res = makeRes(406) const middleware = errorHandler({ logger: null, - html: { default: (_err: any, _req: any, _res: any) => { - assert.equal(_err, err); - assert.equal(_req, req); - assert.equal(_res, res); - done(); - } } - }); - (middleware as any)(err, req, res); - }); - }); + html: { + default: (_err: any, _req: any, _res: any) => { + assert.equal(_err, err) + assert.equal(_req, req) + assert.equal(_res, res) + done() + } + } + }) + ;(middleware as any)(err, req, res) + }) + }) describe('JSON handler', () => { const req = { headers: { 'content-type': 'application/json' } - }; + } const makeRes = (errCode: number, props?: any) => { - return Object.assign({ - set () {}, - status (code: number) { - assert.equal(code, errCode); - } - }, props); - }; + return Object.assign( + { + set() {}, + status(code: number) { + assert.equal(code, errCode) + } + }, + props + ) + } - it('calls res.json by default', done => { - const err = new NotAuthenticated(); + it('calls res.json by default', (done) => { + const err = new NotAuthenticated() const middleware = errorHandler({ logger: null, json: {} - }); + }) const res = makeRes(401, { - json (obj: any) { - assert.deepEqual(obj, err.toJSON()); - done(); + json(obj: any) { + assert.deepEqual(obj, err.toJSON()) + done() } - }); - (middleware as any)(err, req, res); - }); + }) + ;(middleware as any)(err, req, res) + }) - it('if the value is a function, calls as middleware ', done => { - const err = new PaymentError(); - const res = makeRes(402); + it('if the value is a function, calls as middleware ', (done) => { + const err = new PaymentError() + const res = makeRes(402) const middleware = errorHandler({ logger: null, - json: { 402: (_err: any, _req: any, _res: any) => { - assert.equal(_err, err); - assert.equal(_req, req); - assert.equal(_res, res); - done(); - } } - }); - (middleware as any)(err, req, res); - }); + json: { + 402: (_err: any, _req: any, _res: any) => { + assert.equal(_err, err) + assert.equal(_req, req) + assert.equal(_res, res) + done() + } + } + }) + ;(middleware as any)(err, req, res) + }) - it('falls back to default if error code config is available', done => { - const err = new NotAcceptable(); - const res = makeRes(406); + it('falls back to default if error code config is available', (done) => { + const err = new NotAcceptable() + const res = makeRes(406) const middleware = errorHandler({ logger: null, - json: { default: (_err: any, _req: any, _res: any) => { - assert.equal(_err, err); - assert.equal(_req, req); - assert.equal(_res, res); - done(); - } } - }); - (middleware as any)(err, req, res); - }); - }); - }); + json: { + default: (_err: any, _req: any, _res: any) => { + assert.equal(_err, err) + assert.equal(_req, req) + assert.equal(_res, res) + done() + } + } + }) + ;(middleware as any)(err, req, res) + }) + }) + }) describe('use as app error handler', function () { before(function () { this.app = express() .get('/error', function (_req: Request, _res: Response, next: NextFunction) { - next(new Error('Something went wrong')); + next(new Error('Something went wrong')) }) .get('/string-error', function (_req: Request, _res: Response, next: NextFunction) { - const e: any = new Error('Something was not found'); - e.code = '404'; + const e: any = new Error('Something was not found') + e.code = '404' - next(e); + next(e) }) .get('/bad-request', function (_req: Request, _res: Response, next: NextFunction) { - next(new BadRequest({ - message: 'Invalid Password', - errors: [{ - path: 'password', - value: null, - message: '\'password\' cannot be \'null\'' - }] - })); + next( + new BadRequest({ + message: 'Invalid Password', + errors: [ + { + path: 'password', + value: null, + message: "'password' cannot be 'null'" + } + ] + }) + ) }) .use(function (_req: Request, _res: Response, next: NextFunction) { - next(new NotFound('File not found')); + next(new NotFound('File not found')) }) - .use(errorHandler({ - logger: null - })); + .use( + errorHandler({ + logger: null + }) + ) - this.server = this.app.listen(5050); - }); + this.server = this.app.listen(5050) + }) after(function (done) { - this.server.close(done); - }); + this.server.close(done) + }) describe('converts an non-feathers error', () => { it('is an instance of GeneralError', async () => { @@ -222,59 +246,59 @@ describe('error-handler', () => { await axios({ url: 'http://localhost:5050/error', responseType: 'json' - }); - assert.fail('Should never get here'); + }) + assert.fail('Should never get here') } catch (error: any) { - assert.equal(error.response.status, 500); + assert.equal(error.response.status, 500) assert.deepEqual(error.response.data, { name: 'GeneralError', message: 'Something went wrong', code: 500, className: 'general-error' - }); + }) } - }); - }); + }) + }) describe('text/html format', () => { - it('serves a 404.html', done => { + it('serves a 404.html', (done) => { fs.readFile(join(__dirname, '..', 'public', '404.html'), async function (_err, html) { try { await axios({ url: 'http://localhost:5050/path/to/nowhere', headers: { 'Content-Type': 'text/html', - 'Accept': 'text/html' + Accept: 'text/html' } - }); - assert.fail('Should never get here'); + }) + assert.fail('Should never get here') } catch (error: any) { - assert.equal(error.response.status, 404); - assert.equal(error.response.data, html.toString()); - done(); + assert.equal(error.response.status, 404) + assert.equal(error.response.data, html.toString()) + done() } - }); - }); + }) + }) - it('serves a 500.html', done => { + it('serves a 500.html', (done) => { fs.readFile(join(__dirname, '..', 'public', 'default.html'), async function (_err, html) { try { await axios({ url: 'http://localhost:5050/error', headers: { 'Content-Type': 'text/html', - 'Accept': 'text/html' + Accept: 'text/html' } - }); - assert.fail('Should never get here'); + }) + assert.fail('Should never get here') } catch (error: any) { - assert.equal(error.response.status, 500); - assert.equal(error.response.data, html.toString()); - done(); + assert.equal(error.response.status, 500) + assert.equal(error.response.data, html.toString()) + done() } - }); - }); - }); + }) + }) + }) describe('application/json format', () => { it('500', async () => { @@ -283,20 +307,20 @@ describe('error-handler', () => { url: 'http://localhost:5050/error', headers: { 'Content-Type': 'application/json', - 'Accept': 'application/json' + Accept: 'application/json' } - }); - assert.fail('Should never get here'); + }) + assert.fail('Should never get here') } catch (error: any) { - assert.equal(error.response.status, 500); + assert.equal(error.response.status, 500) assert.deepEqual(error.response.data, { name: 'GeneralError', message: 'Something went wrong', code: 500, className: 'general-error' - }); + }) } - }); + }) it('404', async () => { try { @@ -304,19 +328,20 @@ describe('error-handler', () => { url: 'http://localhost:5050/path/to/nowhere', headers: { 'Content-Type': 'application/json', - 'Accept': 'application/json' + Accept: 'application/json' } - }); - assert.fail('Should never get here'); + }) + assert.fail('Should never get here') } catch (error: any) { - assert.equal(error.response.status, 404); - assert.deepEqual(error.response.data, { name: 'NotFound', + assert.equal(error.response.status, 404) + assert.deepEqual(error.response.data, { + name: 'NotFound', message: 'File not found', code: 404, className: 'not-found' - }); + }) } - }); + }) it('400', async () => { try { @@ -324,46 +349,51 @@ describe('error-handler', () => { url: 'http://localhost:5050/bad-request', headers: { 'Content-Type': 'application/json', - 'Accept': 'application/json' + Accept: 'application/json' } - }); - assert.fail('Should never get here'); + }) + assert.fail('Should never get here') } catch (error: any) { - assert.equal(error.response.status, 400); - assert.deepEqual(error.response.data, { name: 'BadRequest', + assert.equal(error.response.status, 400) + assert.deepEqual(error.response.data, { + name: 'BadRequest', message: 'Invalid Password', code: 400, className: 'bad-request', data: {}, - errors: [{ - path: 'password', - value: null, - message: '\'password\' cannot be \'null\'' - }] - }); + errors: [ + { + path: 'password', + value: null, + message: "'password' cannot be 'null'" + } + ] + }) } - }); - }); + }) + }) it('returns JSON by default', async () => { try { - await axios('http://localhost:5050/bad-request'); - assert.fail('Should never get here'); + await axios('http://localhost:5050/bad-request') + assert.fail('Should never get here') } catch (error: any) { - assert.equal(error.response.status, 400); + assert.equal(error.response.status, 400) assert.deepEqual(error.response.data, { name: 'BadRequest', message: 'Invalid Password', code: 400, className: 'bad-request', data: {}, - errors: [{ - path: 'password', - value: null, - message: '\'password\' cannot be \'null\'' - }] - }); + errors: [ + { + path: 'password', + value: null, + message: "'password' cannot be 'null'" + } + ] + }) } - }); - }); -}); + }) + }) +}) diff --git a/packages/express/test/index.test.ts b/packages/express/test/index.test.ts index 715907936b..b22566f22d 100644 --- a/packages/express/test/index.test.ts +++ b/packages/express/test/index.test.ts @@ -1,250 +1,291 @@ -import { strict as assert } from 'assert'; -import express, { Request, Response, NextFunction } from 'express'; -import axios from 'axios'; -import fs from 'fs'; -import path from 'path'; -import https from 'https'; -import { feathers, HookContext, Id, Application } from '@feathersjs/feathers'; - -import * as expressify from '../src'; -import { RequestListener } from 'http'; +/* eslint-disable @typescript-eslint/ban-ts-comment */ +import { strict as assert } from 'assert' +import express, { Request, Response, NextFunction } from 'express' +import axios from 'axios' +import fs from 'fs' +import path from 'path' +import https from 'https' +import { feathers, HookContext, Id } from '@feathersjs/feathers' + +import { default as feathersExpress, rest, notFound, errorHandler, original, serveStatic } from '../src' +import { RequestListener } from 'http' describe('@feathersjs/express', () => { const service = { - async get (id: Id) { - return { id }; + async get(id: Id) { + return { id } } - }; + } it('exports .default, .original .rest, .notFound and .errorHandler', () => { - assert.strictEqual(expressify.original, express); - assert.strictEqual(typeof expressify.rest, 'function'); - assert.ok(expressify.notFound); - assert.ok(expressify.errorHandler); - }); + assert.strictEqual(original, express) + assert.strictEqual(typeof rest, 'function') + assert.ok(notFound) + assert.ok(errorHandler) + }) + + it('returns an Express application, keeps Feathers service and configuration typings typings', () => { + type Config = { + hostname: string + port: number + } + + const app = feathersExpress, Config>(feathers()) + + app.set('hostname', 'test.com') - it('returns an Express application', () => { - const app: Application = expressify.default(feathers()); + const hostname = app.get('hostname') - assert.strictEqual(typeof app, 'function'); - }); + assert.strictEqual(hostname, 'test.com') + assert.strictEqual(typeof app, 'function') + }) it('allows to use an existing Express instance', () => { - const expressApp = express(); - const app = expressify.default(feathers(), expressApp); + const expressApp = express() + const app = feathersExpress(feathers(), expressApp) - assert.strictEqual(app, expressApp); - }); + assert.strictEqual(app, expressApp) + }) it('exports `express.rest`', () => { - assert.ok(typeof expressify.rest === 'function'); - }); + assert.ok(typeof rest === 'function') + }) it('returns a plain express app when no app is provided', () => { - const app = expressify.default(); + const app = feathersExpress() - assert.strictEqual(typeof app.use, 'function'); - assert.strictEqual(typeof app.service, 'undefined'); - assert.strictEqual(typeof app.services, 'undefined'); - }); + assert.strictEqual(typeof app.use, 'function') + assert.strictEqual(typeof app.service, 'undefined') + assert.strictEqual(typeof app.services, 'undefined') + }) it('errors when app with wrong version is provided', () => { try { // @ts-ignore - expressify.default({}); + feathersExpress({}) } catch (e: any) { - assert.strictEqual(e.message, '@feathersjs/express requires a valid Feathers application instance'); + assert.strictEqual(e.message, '@feathersjs/express requires a valid Feathers application instance') } try { - const app = feathers(); - app.version = '2.9.9'; + const app = feathers() + app.version = '2.9.9' - expressify.default(app); + feathersExpress(app) } catch (e: any) { - assert.strictEqual(e.message, '@feathersjs/express requires an instance of a Feathers application version 3.x or later (got 2.9.9)'); + assert.strictEqual( + e.message, + '@feathersjs/express requires an instance of a Feathers application version 3.x or later (got 2.9.9)' + ) } try { - const app = feathers(); - delete app.version; + const app = feathers() + delete app.version - expressify.default(app); + feathersExpress(app) } catch (e: any) { - assert.strictEqual(e.message, '@feathersjs/express requires an instance of a Feathers application version 3.x or later (got unknown)'); + assert.strictEqual( + e.message, + '@feathersjs/express requires an instance of a Feathers application version 3.x or later (got unknown)' + ) } - }); + }) it('Can use Express sub-apps', () => { - const typedApp = feathers<{}>(); - const app = expressify.default(typedApp); - const child = express(); + const typedApp = feathers>() + const app = feathersExpress(typedApp) + const child = express() - app.use('/path', child); - assert.strictEqual((child as any).parent, app); - }); + app.use('/path', child) + assert.strictEqual((child as any).parent, app) + }) it('Can use express.static', () => { - const app = expressify.default(feathers()); + const app = feathersExpress(feathers()) - app.use('/path', expressify.static(__dirname)); - }); + app.use('/path', serveStatic(__dirname)) + }) it('has Feathers functionality', async () => { - const app = expressify.default(feathers()); + const app = feathersExpress(feathers()) - app.use('/myservice', service); + app.use('/myservice', service) app.hooks({ after: { - get (hook: HookContext) { - hook.result.fromAppHook = true; + get(hook: HookContext) { + hook.result.fromAppHook = true } } - }); + }) app.service('myservice').hooks({ after: { - get (hook: HookContext) { - hook.result.fromHook = true; + get(hook: HookContext) { + hook.result.fromHook = true } } - }); + }) - const data = await app.service('myservice').get(10); + const data = await app.service('myservice').get(10) assert.deepStrictEqual(data, { id: 10, fromHook: true, fromAppHook: true - }); - }); + }) + }) it('can register a service and start an Express server', async () => { - const app = expressify.default(feathers()); + const app = feathersExpress(feathers()) const response = { message: 'Hello world' - }; + } - app.use('/myservice', service); - app.use((_req: Request, res: Response) => res.json(response)); + app.use('/myservice', service) + app.use((_req: Request, res: Response) => res.json(response)) - const server = await app.listen(8787); - const data = await app.service('myservice').get(10); + const server = await app.listen(8787) + const data = await app.service('myservice').get(10) - assert.deepStrictEqual(data, { id: 10 }); + assert.deepStrictEqual(data, { id: 10 }) - const res = await axios.get('http://localhost:8787'); - assert.deepStrictEqual(res.data, response); + const res = await axios.get('http://localhost:8787') + assert.deepStrictEqual(res.data, response) - await new Promise(resolve => server.close(() => resolve(server))); - }); + await new Promise((resolve) => server.close(() => resolve(server))) + }) it('.listen calls .setup', async () => { - const app = expressify.default(feathers()); - let called = false; + const app = feathersExpress(feathers()) + let called = false app.use('/myservice', { - async get (id: Id) { - return { id }; + async get(id: Id) { + return { id } }, - async setup (appParam, path) { - assert.strictEqual(appParam, app); - assert.strictEqual(path, 'myservice'); - called = true; + async setup(appParam, path) { + assert.strictEqual(appParam, app) + assert.strictEqual(path, 'myservice') + called = true } - }); + }) + + const server = await app.listen(8787) + + assert.ok(called) + await new Promise((resolve) => server.close(() => resolve(server))) + }) - const server = await app.listen(8787); + it('.teardown closes http server', async () => { + const app = feathersExpress(feathers()) + let called = false - assert.ok(called); - await new Promise(resolve => server.close(() => resolve(server))); - }); + const server = await app.listen(8787) + server.on('close', () => { + called = true + }) + + await app.teardown() + assert.ok(called) + }) it('passes middleware as options', () => { - const feathersApp = feathers(); - const app = expressify.default(feathersApp); - const oldUse = feathersApp.use; - const a = (_req: Request, _res: Response, next: NextFunction) => next(); - const b = (_req: Request, _res: Response, next: NextFunction) => next(); - const c = (_req: Request, _res: Response, next: NextFunction) => next(); + const feathersApp = feathers() + const app = feathersExpress(feathersApp) + const oldUse = feathersApp.use + const a = (_req: Request, _res: Response, next: NextFunction) => next() + const b = (_req: Request, _res: Response, next: NextFunction) => next() + const c = (_req: Request, _res: Response, next: NextFunction) => next() const service = { - async get (id: Id) { - return { id }; + async get(id: Id) { + return { id } } - }; + } feathersApp.use = function (path, serviceArg, options) { - assert.strictEqual(path, '/myservice'); - assert.strictEqual(serviceArg, service); + assert.strictEqual(path, '/myservice') + assert.strictEqual(serviceArg, service) assert.deepStrictEqual(options.express, { before: [a, b], after: [c] - }); - return (oldUse as any).apply(this, arguments); - }; + }) + // eslint-disable-next-line prefer-rest-params + return (oldUse as any).apply(this, arguments) + } - app.use('/myservice', a, b, service, c); - }); + app.use('/myservice', a, b, service, c) + }) it('Express wrapped and context.app are the same', async () => { - const app = expressify.default(feathers()); + const app = feathersExpress(feathers()) app.use('/test', { - async get (id: Id) { - return { id }; + async get(id: Id) { + return { id } } - }); + }) app.service('test').hooks({ before: { - get: [context => { - assert.ok(context.app === app); - }] + get: [ + (context) => { + assert.ok(context.app === app) + } + ] } - }); + }) assert.deepStrictEqual(await app.service('test').get('testing'), { id: 'testing' - }); - }); + }) + }) - it('Works with HTTPS', done => { + it('Works with HTTPS', (done) => { const todoService = { - async get (name: Id) { + async get(name: Id) { return { id: name, description: `You have to do ${name}!` - }; + } } - }; + } - const app = expressify.default(feathers()).configure(expressify.rest()); + const app = feathersExpress(feathers()).configure(rest()) - app.use('/secureTodos', todoService); + app.use('/secureTodos', todoService) - const httpsServer = https.createServer({ - key: fs.readFileSync(path.join(__dirname, '..', '..', 'tests', 'resources', 'privatekey.pem')), - cert: fs.readFileSync(path.join(__dirname, '..', '..', 'tests', 'resources', 'certificate.pem')), - rejectUnauthorized: false, - requestCert: false - }, app as unknown as RequestListener).listen(7889); + const httpsServer = https + .createServer( + { + key: fs.readFileSync(path.join(__dirname, '..', '..', 'tests', 'resources', 'privatekey.pem')), + cert: fs.readFileSync(path.join(__dirname, '..', '..', 'tests', 'resources', 'certificate.pem')), + rejectUnauthorized: false, + requestCert: false + }, + app as unknown as RequestListener + ) + .listen(7889) - app.setup(httpsServer); + app.setup(httpsServer) httpsServer.on('listening', function () { const instance = axios.create({ httpsAgent: new https.Agent({ rejectUnauthorized: false }) - }); - - instance.get('https://localhost:7889/secureTodos/dishes').then(response => { - assert.ok(response.status === 200, 'Got OK status code'); - assert.strictEqual(response.data.description, 'You have to do dishes!'); - httpsServer.close(() => done()); - }).catch(done); - }); - }); -}); + }) + + instance + .get('https://localhost:7889/secureTodos/dishes') + .then((response) => { + assert.ok(response.status === 200, 'Got OK status code') + assert.strictEqual(response.data.description, 'You have to do dishes!') + httpsServer.close(() => done()) + }) + .catch(done) + }) + }) +}) diff --git a/packages/express/test/not-found-handler.test.ts b/packages/express/test/not-found-handler.test.ts index 4db680e456..89db3cf1bd 100644 --- a/packages/express/test/not-found-handler.test.ts +++ b/packages/express/test/not-found-handler.test.ts @@ -1,36 +1,44 @@ -import { strict as assert } from 'assert'; -import { NotFound } from '@feathersjs/errors'; +import { strict as assert } from 'assert' +import { NotFound } from '@feathersjs/errors' -import { notFound } from '../src'; +import { notFound } from '../src' -const handler = notFound as any; +const handler = notFound as any describe('not-found-handler', () => { - it('returns NotFound error', done => { - handler()({ - url: 'some/where', - headers: {} - }, {}, function (error: any) { - assert.ok(error instanceof NotFound); - assert.equal(error.message, 'Page not found'); - assert.deepEqual(error.data, { - url: 'some/where' - }); - done(); - }); - }); + it('returns NotFound error', (done) => { + handler()( + { + url: 'some/where', + headers: {} + }, + {}, + function (error: any) { + assert.ok(error instanceof NotFound) + assert.equal(error.message, 'Page not found') + assert.deepEqual(error.data, { + url: 'some/where' + }) + done() + } + ) + }) - it('returns NotFound error with URL when verbose', done => { - handler({ verbose: true })({ - url: 'some/where', - headers: {} - }, {}, function (error: any) { - assert.ok(error instanceof NotFound); - assert.equal(error.message, 'Page not found: some/where'); - assert.deepEqual(error.data, { - url: 'some/where' - }); - done(); - }); - }); -}); + it('returns NotFound error with URL when verbose', (done) => { + handler({ verbose: true })( + { + url: 'some/where', + headers: {} + }, + {}, + function (error: any) { + assert.ok(error instanceof NotFound) + assert.equal(error.message, 'Page not found: some/where') + assert.deepEqual(error.data, { + url: 'some/where' + }) + done() + } + ) + }) +}) diff --git a/packages/express/test/rest.test.ts b/packages/express/test/rest.test.ts index 69f5f2ced8..f6d6e7c3a4 100644 --- a/packages/express/test/rest.test.ts +++ b/packages/express/test/rest.test.ts @@ -1,160 +1,182 @@ /* eslint-disable @typescript-eslint/no-unused-vars */ -import { strict as assert } from 'assert'; -import axios, { AxiosRequestConfig } from 'axios'; +import { strict as assert } from 'assert' +import axios, { AxiosRequestConfig } from 'axios' -import { Server } from 'http'; -import { Request, Response, NextFunction } from 'express'; -import { feathers, HookContext, Id, Params } from '@feathersjs/feathers'; -import { Service, restTests } from '@feathersjs/tests'; -import { BadRequest } from '@feathersjs/errors'; +import { Server } from 'http' +import { Request, Response, NextFunction } from 'express' +import { ApplicationHookMap, feathers, HookContext, Id, Params } from '@feathersjs/feathers' +import { Service, restTests } from '@feathersjs/tests' +import { BadRequest } from '@feathersjs/errors' import * as express from '../src' -const expressify = express.default; -const { rest } = express; +const expressify = express.default +const { rest } = express const errorHandler = express.errorHandler({ logger: false -}); +}) describe('@feathersjs/express/rest provider', () => { describe('base functionality', () => { it('throws an error if you did not expressify', () => { - const app = feathers(); + const app = feathers() try { - app.configure(rest() as any); - assert.ok(false, 'Should never get here'); + app.configure(rest() as any) + assert.ok(false, 'Should never get here') } catch (e: any) { - assert.strictEqual(e.message, '@feathersjs/express/rest needs an Express compatible app.'); + assert.strictEqual(e.message, '@feathersjs/express/rest needs an Express compatible app.') } - }); + }) it('lets you set the handler manually', async () => { - const app = expressify(feathers()); + const app = expressify(feathers()) - app.configure(rest(function (_req, res) { - res.format({ - 'text/plain' () { - res.end(`The todo is: ${res.data.description}`); + app + .configure( + rest(function (_req, res) { + res.format({ + 'text/plain'() { + res.end(`The todo is: ${res.data.description}`) + } + }) + }) + ) + .use('/todo', { + async get(id: Id) { + return { + description: `You have to do ${id}` + } } - }); - })).use('/todo', { - async get (id: Id) { - return { - description: `You have to do ${id}` - }; - } - }); + }) - const server = await app.listen(4776); + const server = await app.listen(4776) - const res = await axios.get('http://localhost:4776/todo/dishes'); + const res = await axios.get('http://localhost:4776/todo/dishes') - assert.strictEqual(res.data, 'The todo is: You have to do dishes'); - server.close(); - }); + assert.strictEqual(res.data, 'The todo is: You have to do dishes') + server.close() + }) it('lets you set no handler', async () => { - const app = expressify(feathers()); - const data = { fromHandler: true }; + const app = expressify(feathers()) + const data = { fromHandler: true } - app.configure(rest(null)) + app + .configure(rest(null)) .use('/todo', { - async get (id: Id) { + async get(id: Id) { return { description: `You have to do ${id}` - }; + } } }) - .use((_req: Request, res: Response) => res.json(data)); + .use((_req: Request, res: Response) => res.json(data)) - const server = await app.listen(5775); + const server = await app.listen(5775) const res = await axios.get('http://localhost:5775/todo-handler/dishes') - assert.deepStrictEqual(res.data, data); + assert.deepStrictEqual(res.data, data) - server.close(); - }); - }); + server.close() + }) + }) describe('CRUD', () => { - let server: Server; - let app: express.Application; + let app: express.Application before(async () => { app = expressify(feathers()) + .use(express.cors()) .use(express.json()) .configure(rest(express.formatter)) .use('codes', { - async get (id: Id) { - return { id }; + async get(id: Id) { + return { id } }, - async create (data: any) { - return data; + async create(data: any) { + return data } }) .use('/', new Service()) - .use('todo', new Service()); + .use('todo', new Service()) + + app.hooks({ + setup: [ + async (context, next) => { + assert.ok(context.app) + await next() + } + ], + teardown: [ + async (context, next) => { + assert.ok(context.app) + await next() + } + ] + } as ApplicationHookMap) - server = await app.listen(4777, () => app.use('tasks', new Service())); - }); + await app.listen(4777, () => app.use('tasks', new Service())) + }) - after(done => server.close(done)); + after(() => app.teardown()) - restTests('Services', 'todo', 4777); - restTests('Root Service', '/', 4777); - restTests('Dynamic Services', 'tasks', 4777); + restTests('Services', 'todo', 4777) + restTests('Root Service', '/', 4777) + restTests('Dynamic Services', 'tasks', 4777) describe('res.hook', () => { const convertHook = (hook: HookContext) => { - const result: any = Object.assign({}, hook); + const result: any = Object.assign({}, hook) - delete result.self; - delete result.service; - delete result.app; - delete result.error; + delete result.self + delete result.service + delete result.app + delete result.error - return result; - }; + return result + } it('sets the actual hook object in res.hook', async () => { const params = { route: {}, query: { test: 'param' }, provider: 'rest' - }; + } - app.use('/hook', { - async get (id) { - return { - description: `You have to do ${id}` - }; - } - }, function (_req: Request, res: Response, next: NextFunction) { - res.data = convertHook(res.hook); + app.use( + '/hook', + { + async get(id) { + return { + description: `You have to do ${id}` + } + } + }, + function (_req: Request, res: Response, next: NextFunction) { + res.data = convertHook(res.hook) - next(); - }); + next() + } + ) app.service('hook').hooks({ - after (hook: HookContext) { - (hook as any).addedProperty = true; + after(hook: HookContext) { + hook.addedProperty = true } - }); + }) - const res = await axios.get('http://localhost:4777/hook/dishes?test=param'); + const res = await axios.get('http://localhost:4777/hook/dishes?test=param') const paramsWithHeaders = { ...params, headers: res.data.params.headers - }; + } assert.deepStrictEqual(res.data, { id: 'dishes', params: paramsWithHeaders, - arguments: [ - 'dishes', paramsWithHeaders - ], + arguments: ['dishes', paramsWithHeaders], type: null, method: 'get', path: 'hook', @@ -162,86 +184,105 @@ describe('@feathersjs/express/rest provider', () => { event: null, result: { description: 'You have to do dishes' }, addedProperty: true - }); - }); + }) + }) it('can use hook.dispatch', async () => { app.use('/hook-dispatch', { - async get () { - return {}; + async get() { + return {} } - }); + }) app.service('hook-dispatch').hooks({ - after (hook: HookContext) { + after(hook: HookContext) { hook.dispatch = { id: hook.id, fromDispatch: true - }; + } } - }); + }) - const res = await axios.get('http://localhost:4777/hook-dispatch/dishes'); + const res = await axios.get('http://localhost:4777/hook-dispatch/dishes') assert.deepStrictEqual(res.data, { id: 'dishes', fromDispatch: true - }); - }); + }) + }) it('allows to set statusCode in a hook', async () => { app.use('/hook-status', { - async get () { - return {}; + async get() { + return {} } - }); + }) app.service('hook-status').hooks({ - after (hook: HookContext) { - hook.http!.statusCode = 206; + after(hook: HookContext) { + hook.http.status = 206 + } + }) + + const res = await axios.get('http://localhost:4777/hook-status/dishes') + + assert.strictEqual(res.status, 206) + }) + + it('allows to set response headers in a hook', async () => { + app.use('/hook-headers', { + async get() { + return {} + } + }) + + app.service('hook-headers').hooks({ + after(hook: HookContext) { + hook.http.headers = { foo: 'first', bar: ['second', 'third'] } } - }); + }) - const res = await axios.get('http://localhost:4777/hook-status/dishes'); + const res = await axios.get('http://localhost:4777/hook-headers/dishes') - assert.strictEqual(res.status, 206); - }); + assert.strictEqual(res.headers.foo, 'first') + assert.strictEqual(res.headers.bar, 'second, third') + }) it('sets the hook object in res.hook on error', async () => { const params = { route: {}, query: {}, provider: 'rest' - }; + } app.use('/hook-error', { - async get () { - throw new Error('I blew up'); + async get() { + throw new Error('I blew up') } - }); + }) app.use(function (error: Error, _req: Request, res: Response, _next: NextFunction) { - res.status(500); + res.status(500) res.json({ hook: convertHook(res.hook), error: { message: error.message } - }); - }); + }) + }) try { - await axios('http://localhost:4777/hook-error/dishes'); - assert.fail('Should never get here'); + await axios('http://localhost:4777/hook-error/dishes') + assert.fail('Should never get here') } catch (error: any) { - const { data } = error.response; + const { data } = error.response const paramsWithHeaders = { ...params, headers: data.hook.params.headers - }; + } assert.deepStrictEqual(error.response.data, { hook: { id: 'dishes', params: paramsWithHeaders, - arguments: ['dishes', paramsWithHeaders ], + arguments: ['dishes', paramsWithHeaders], type: null, event: null, method: 'get', @@ -249,31 +290,33 @@ describe('@feathersjs/express/rest provider', () => { http: {} }, error: { message: 'I blew up' } - }); + }) } - }); - }); - }); + }) + }) + }) describe('middleware', () => { it('sets service parameters and provider type', async () => { const service = { - async get (_id: Id, params: Params) { - return params; + async get(_id: Id, params: Params) { + return params } - }; + } const app = expressify(feathers()) .use(function (req: Request, _res: Response, next: NextFunction) { - assert.ok(req.feathers, 'Feathers object initialized'); - req.feathers.test = 'Happy'; - next(); + req.feathers = { + ...req.feathers, + test: 'Happy' + } + next() }) .configure(rest(express.formatter)) - .use('service', service); - const server = await app.listen(4778); + .use('service', service) + const server = await app.listen(4778) - const res = await axios.get('http://localhost:4778/service/bla?some=param&another=thing'); + const res = await axios.get('http://localhost:4778/service/bla?some=param&another=thing') const expected = { headers: res.data.headers, test: 'Happy', @@ -283,33 +326,34 @@ describe('@feathersjs/express/rest provider', () => { some: 'param', another: 'thing' } - }; + } - assert.ok(res.status === 200, 'Got OK status code'); - assert.deepStrictEqual(res.data, expected, 'Got params object back'); - server.close(); - }); + assert.ok(res.status === 200, 'Got OK status code') + assert.deepStrictEqual(res.data, expected, 'Got params object back') + server.close() + }) it('Lets you configure your own middleware before the handler (#40)', async () => { const data = { description: 'Do dishes!', id: 'dishes' - }; - const app = expressify(feathers()); + } + const app = expressify(feathers()) - app.use(function defaultContentTypeMiddleware (req, _res, next) { - req.headers['content-type'] = req.headers['content-type'] || 'application/json'; - next(); - }) + app + .use(function defaultContentTypeMiddleware(req, _res, next) { + req.headers['content-type'] = req.headers['content-type'] || 'application/json' + next() + }) .use(express.json()) .configure(rest(express.formatter)) .use('/todo', { - async create (data: any) { - return data; + async create(data: any) { + return data } - }); + }) - const server = await app.listen(4775); + const server = await app.listen(4775) const res = await axios({ url: 'http://localhost:4775/todo', method: 'post', @@ -317,228 +361,258 @@ describe('@feathersjs/express/rest provider', () => { headers: { 'content-type': '' } - }); + }) - assert.deepStrictEqual(res.data, data); - server.close(); - }); + assert.deepStrictEqual(res.data, data) + server.close() + }) it('allows middleware before and after a service', async () => { - const app = expressify(feathers()); + const app = expressify(feathers()) app .use(express.json()) .configure(rest()) - .use('/todo', function (req, _res, next) { - req.body.before = ['before first']; - next(); - }, function (req, _res, next) { - req.body.before.push('before second'); - next(); - }, { - async create (data: any) { - return data; + .use( + '/todo', + function (req, _res, next) { + req.body.before = ['before first'] + next() + }, + function (req, _res, next) { + req.body.before.push('before second') + next() + }, + { + async create(data: any) { + return data + } + }, + function (_req, res, next) { + res.data.after = ['after first'] + next() + }, + function (_req, res, next) { + res.data.after.push('after second') + next() } - }, function (_req, res, next) { - res.data.after = ['after first']; - next(); - }, function (_req, res, next) { - res.data.after.push('after second'); - next(); - }); + ) - const server = await app.listen(4776); - const res = await axios.post('http://localhost:4776/todo', { text: 'Do dishes' }); + const server = await app.listen(4776) + const res = await axios.post('http://localhost:4776/todo', { + text: 'Do dishes' + }) assert.deepStrictEqual(res.data, { text: 'Do dishes', before: ['before first', 'before second'], after: ['after first', 'after second'] - }); + }) - server.close(); - }); + server.close() + }) it('allows middleware arrays before and after a service', async () => { - const app = expressify(feathers()); + const app = expressify(feathers()) - app - .use(express.json()) - .configure(rest()) - .use('/todo', [function (req: Request, _res: Response, next: NextFunction) { - req.body.before = ['before first']; - next(); - }, function (req: Request, _res: Response, next: NextFunction) { - req.body.before.push('before second'); - next(); - }], { - async create (data) { - return data; + app.use(express.json()) + app.configure(rest()) + app.use( + '/todo', + [ + function (req: Request, _res: Response, next: NextFunction) { + req.body.before = ['before first'] + next() + }, + function (req: Request, _res: Response, next: NextFunction) { + req.body.before.push('before second') + next() + } + ], + { + async create(data) { + return data } - }, [function (_req: Request, res: Response, next: NextFunction) { - res.data.after = ['after first']; - next(); - }], function (_req: Request, res: Response, next: NextFunction) { - res.data.after.push('after second'); - next(); - }); + }, + [ + function (_req: Request, res: Response, next: NextFunction) { + res.data.after = ['after first'] + next() + } + ], + function (_req: Request, res: Response, next: NextFunction) { + res.data.after.push('after second') + next() + } + ) - const server = await app.listen(4776); - const res = await axios.post('http://localhost:4776/todo', { text: 'Do dishes' }); + const server = await app.listen(4776) + const res = await axios.post('http://localhost:4776/todo', { + text: 'Do dishes' + }) assert.deepStrictEqual(res.data, { text: 'Do dishes', before: ['before first', 'before second'], after: ['after first', 'after second'] - }); - server.close(); - }); + }) + server.close() + }) it('allows an array of middleware without a service', async () => { - const app = expressify(feathers()); + const app = expressify(feathers()) const middlewareArray = [ function (_req: Request, res: Response, next: NextFunction) { - res.data = ['first']; - next(); - }, function (_req: Request, res: Response, next: NextFunction) { - res.data.push('second'); - next(); - }, function (req: Request, res: Response) { - res.data.push(req.body.text); - res.status(200).json(res.data); - }]; - app - .use(express.json()) - .configure(rest()) - .use('/array-middleware', middlewareArray); + res.data = ['first'] + next() + }, + function (_req: Request, res: Response, next: NextFunction) { + res.data.push('second') + next() + }, + function (req: Request, res: Response) { + res.data.push(req.body.text) + res.status(200).json(res.data) + } + ] + app.use(express.json()).configure(rest()).use('/array-middleware', middlewareArray) - const server = await app.listen(4776); - const res = await axios.post('http://localhost:4776/array-middleware', { text: 'Do dishes' }); + const server = await app.listen(4776) + const res = await axios.post('http://localhost:4776/array-middleware', { + text: 'Do dishes' + }) - assert.deepStrictEqual(res.data, ['first', 'second', 'Do dishes']); - server.close(); - }); + assert.deepStrictEqual(res.data, ['first', 'second', 'Do dishes']) + server.close() + }) it('formatter does nothing when there is no res.data', async () => { - const data = { message: 'It worked' }; - const app = expressify(feathers()).use('/test', - express.formatter, - (_req: Request, res: Response) => res.json(data) - ); + const data = { message: 'It worked' } + const app = expressify(feathers()).use('/test', express.formatter, (_req: Request, res: Response) => + res.json(data) + ) - const server = await app.listen(7988); - const res = await axios.get('http://localhost:7988/test'); + const server = await app.listen(7988) + const res = await axios.get('http://localhost:7988/test') - assert.deepStrictEqual(res.data, data); - server.close(); - }); - }); + assert.deepStrictEqual(res.data, data) + server.close() + }) + }) describe('HTTP status codes', () => { - let app: express.Application; - let server: Server; + let app: express.Application + let server: Server before(async () => { app = expressify(feathers()) .configure(rest(express.formatter)) .use('todo', { - async get (id: Id) { + async get(id: Id) { return { description: `You have to do ${id}` - }; + } }, - async patch () { - throw new Error('Not implemented'); + async patch() { + throw new Error('Not implemented') }, - async find () { - return null; + async find() { + return null } - }); + }) app.use(function (_req, res, next) { if (typeof res.data !== 'undefined') { - next(new Error('Should never get here')); + next(new Error('Should never get here')) } else { - next(); + next() } - }); + }) // Error handler app.use(function (error: Error, _req: Request, res: Response, _next: NextFunction) { if (res.statusCode < 400) { - res.status(500); + res.status(500) } - res.json({ message: error.message }); - }); + res.json({ message: error.message }) + }) - server = await app.listen(4780); - }); + server = await app.listen(4780) + }) - after(done => server.close(done)); + after((done) => server.close(done)) it('throws a 405 for undefined service methods (#99)', async () => { - const res = await axios.get('http://localhost:4780/todo/dishes'); + const res = await axios.get('http://localhost:4780/todo/dishes') - assert.ok(res.status === 200, 'Got OK status code for .get'); - assert.deepStrictEqual(res.data, { - description: 'You have to do dishes' - }, 'Got expected object'); + assert.ok(res.status === 200, 'Got OK status code for .get') + assert.deepStrictEqual( + res.data, + { + description: 'You have to do dishes' + }, + 'Got expected object' + ) try { - await axios.post('http://localhost:4780/todo'); - assert.fail('Should never get here'); + await axios.post('http://localhost:4780/todo') + assert.fail('Should never get here') } catch (error: any) { - assert.ok(error.response.status === 405, 'Got 405 for .create'); - assert.deepStrictEqual(error.response.data, { - message: 'Method `create` is not supported by this endpoint.' - }, 'Error serialized as expected'); + assert.ok(error.response.status === 405, 'Got 405 for .create') + assert.deepStrictEqual( + error.response.data, + { + message: 'Method `create` is not supported by this endpoint.' + }, + 'Error serialized as expected' + ) } - }); + }) it('throws a 404 for undefined route', async () => { try { - await axios.get('http://localhost:4780/todo/foo/bar'); - assert.fail('Should never get here'); + await axios.get('http://localhost:4780/todo/foo/bar') + assert.fail('Should never get here') } catch (error: any) { - assert.ok(error.response.status === 404, 'Got Not Found code'); + assert.ok(error.response.status === 404, 'Got Not Found code') } - }); + }) it('empty response sets 204 status codes, does not run other middleware (#391)', async () => { - const res = await axios.get('http://localhost:4780/todo'); + const res = await axios.get('http://localhost:4780/todo') - assert.ok(res.status === 204, 'Got empty status code'); - }); - }); + assert.ok(res.status === 204, 'Got empty status code') + }) + }) describe('route parameters', () => { - let server: Server; - let app: express.Application; + let server: Server + let app: express.Application before(async () => { app = expressify(feathers()) .configure(rest()) .use('/:appId/:id/todo', { - async get (id: Id, params: Params) { + async get(id: Id, params: Params) { if (params.query.error) { - throw new BadRequest('Not good'); + throw new BadRequest('Not good') } return { id, route: params.route - }; + } } }) - .use(errorHandler); + .use(errorHandler) - server = await app.listen(6880); - }); + server = await app.listen(6880) + }) - after(done => server.close(done)); + after((done) => server.close(done)) it('adds route params as `params.route` and allows id property (#76, #407)', async () => { const expected = { @@ -547,35 +621,35 @@ describe('@feathersjs/express/rest provider', () => { appId: 'theApp', id: 'myId' } - }; + } - const res = await axios.get(`http://localhost:6880/theApp/myId/todo/${expected.id}`); + const res = await axios.get(`http://localhost:6880/theApp/myId/todo/${expected.id}`) - assert.ok(res.status === 200, 'Got OK status code'); - assert.deepStrictEqual(expected, res.data); - }); + assert.ok(res.status === 200, 'Got OK status code') + assert.deepStrictEqual(expected, res.data) + }) it('properly serializes error for nested routes (#1096)', async () => { try { - await axios.get('http://localhost:6880/theApp/myId/todo/test?error=true'); - assert.fail('Should never het here'); + await axios.get('http://localhost:6880/theApp/myId/todo/test?error=true') + assert.fail('Should never het here') } catch (error: any) { - const { response } = error; + const { response } = error - assert.strictEqual(response.status, 400); + assert.strictEqual(response.status, 400) assert.deepStrictEqual(response.data, { name: 'BadRequest', message: 'Not good', code: 400, className: 'bad-request' - }); + }) } - }); - }); + }) + }) describe('Custom methods', () => { - let server: Server; - let app: express.Application; + let server: Server + let app: express.Application before(async () => { app = expressify(feathers()) @@ -584,57 +658,61 @@ describe('@feathersjs/express/rest provider', () => { .use('/todo', new Service(), { methods: ['find', 'customMethod'] }) - .use(errorHandler); + .use(errorHandler) - server = await app.listen(4781); - }); + server = await app.listen(4781) + }) - after(done => server.close(done)); + after((done) => server.close(done)) it('calls .customMethod with X-Service-Method header', async () => { - const payload = { text: 'Do dishes' }; + const payload = { text: 'Do dishes' } const res = await axios.post('http://localhost:4781/todo', payload, { headers: { 'X-Service-Method': 'customMethod' } - }); + }) assert.deepEqual(res.data, { data: payload, method: 'customMethod', provider: 'rest' - }); - }); + }) + }) it('throws MethodNotImplement for .setup, non option and default methods', async () => { const options: AxiosRequestConfig = { method: 'POST', url: 'http://localhost:4781/todo', data: { text: 'Do dishes' } - }; + } const testMethod = (name: string) => { - return assert.rejects(() => axios({ - ...options, - headers: { - 'X-Service-Method': name + return assert.rejects( + () => + axios({ + ...options, + headers: { + 'X-Service-Method': name + } + }), + (error: any) => { + assert.deepEqual(error.response.data, { + name: 'MethodNotAllowed', + message: `Method \`${name}\` is not supported by this endpoint.`, + code: 405, + className: 'method-not-allowed' + }) + + return true } - }), (error: any) => { - assert.deepEqual(error.response.data, { - name: 'MethodNotAllowed', - message: `Method \`${name}\` is not supported by this endpoint.`, - code: 405, - className: 'method-not-allowed' - }); - - return true; - }); + ) } - await testMethod('setup'); - await testMethod('internalMethod'); - await testMethod('nonExisting'); - await testMethod('create'); - await testMethod('find'); - }); - }); -}); + await testMethod('setup') + await testMethod('internalMethod') + await testMethod('nonExisting') + await testMethod('create') + await testMethod('find') + }) + }) +}) diff --git a/packages/feathers/CHANGELOG.md b/packages/feathers/CHANGELOG.md index f6c32beaba..61e949a8f1 100644 --- a/packages/feathers/CHANGELOG.md +++ b/packages/feathers/CHANGELOG.md @@ -3,602 +3,447 @@ All notable changes to this project will be documented in this file. See [Conventional Commits](https://conventionalcommits.org) for commit guidelines. -# [5.0.0-pre.16](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.15...v5.0.0-pre.16) (2022-01-12) - +# [5.0.0-pre.31](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.30...v5.0.0-pre.31) (2022-10-12) ### Features -* **express, koa:** make transports similar ([#2486](https://github.com/feathersjs/feathers/issues/2486)) ([26aa937](https://github.com/feathersjs/feathers/commit/26aa937c114fb8596dfefc599b1f53cead69c159)) +- **cli:** Generate full client test suite and improve typed client ([#2788](https://github.com/feathersjs/feathers/issues/2788)) ([57119b6](https://github.com/feathersjs/feathers/commit/57119b6bb2797f7297cf054268a248c093ecd538)) +# [5.0.0-pre.30](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.29...v5.0.0-pre.30) (2022-10-07) +### Bug Fixes +- **core:** Ensure setup and teardown can be overriden and maintain hook functionality ([#2779](https://github.com/feathersjs/feathers/issues/2779)) ([ab580cb](https://github.com/feathersjs/feathers/commit/ab580cbcaa68d19144d86798c13bf564f9d424a6)) +### Features -# [5.0.0-pre.15](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.14...v5.0.0-pre.15) (2021-11-27) +- **core:** Allow to unregister services at runtime ([#2756](https://github.com/feathersjs/feathers/issues/2756)) ([d16601f](https://github.com/feathersjs/feathers/commit/d16601f2277dca5357866ffdefba2a611f6dc7fa)) +# [5.0.0-pre.29](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.28...v5.0.0-pre.29) (2022-09-16) -### Bug Fixes +### Features -* **typescript:** Overall typing improvements ([#2478](https://github.com/feathersjs/feathers/issues/2478)) ([b8eb804](https://github.com/feathersjs/feathers/commit/b8eb804158556d9651a8607e3c3fda15e0bfd110)) +- **cli:** Adding ClientService to CLI ([#2750](https://github.com/feathersjs/feathers/issues/2750)) ([1d45427](https://github.com/feathersjs/feathers/commit/1d45427988521ac028755cbe128685fcdf34f636)) +# [5.0.0-pre.28](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.27...v5.0.0-pre.28) (2022-08-03) -### Features +### Bug Fixes -* **core:** add `context.http` and move `statusCode` there ([#2496](https://github.com/feathersjs/feathers/issues/2496)) ([b701bf7](https://github.com/feathersjs/feathers/commit/b701bf77fb83048aa1dffa492b3d77dd53f7b72b)) -* **core:** Improve legacy hooks integration ([08c8b40](https://github.com/feathersjs/feathers/commit/08c8b40999bf3889c61a4d4fad97a2c4f78bafc9)) -* **transport-commons:** Ability to register routes with custom params ([#2482](https://github.com/feathersjs/feathers/issues/2482)) ([497990a](https://github.com/feathersjs/feathers/commit/497990ae4a980e5a52a1f0f932db12cd0e6e254a)) +- **cli:** Improve generated application and client ([#2701](https://github.com/feathersjs/feathers/issues/2701)) ([bd55ffb](https://github.com/feathersjs/feathers/commit/bd55ffb812e89bf215f4515e7f137656ea888c3f)) +- **core:** Get hooks to work reliably with custom methods ([#2714](https://github.com/feathersjs/feathers/issues/2714)) ([8d7e04a](https://github.com/feathersjs/feathers/commit/8d7e04acd0f0e2af9f4c13efee652d296dd3bc51)) +# [5.0.0-pre.27](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.26...v5.0.0-pre.27) (2022-07-13) +**Note:** Version bump only for package @feathersjs/feathers +# [5.0.0-pre.26](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.25...v5.0.0-pre.26) (2022-06-22) +**Note:** Version bump only for package @feathersjs/feathers -# [5.0.0-pre.14](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.13...v5.0.0-pre.14) (2021-10-13) +# [5.0.0-pre.25](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.24...v5.0.0-pre.25) (2022-06-22) **Note:** Version bump only for package @feathersjs/feathers +# [5.0.0-pre.24](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.23...v5.0.0-pre.24) (2022-06-21) +### Features +- **authentication-local:** Add passwordHash property resolver ([#2660](https://github.com/feathersjs/feathers/issues/2660)) ([b41279b](https://github.com/feathersjs/feathers/commit/b41279b55eea3771a6fa4983a37be2413287bbc6)) +- **cli:** Add typed client to a generated app ([#2669](https://github.com/feathersjs/feathers/issues/2669)) ([5b801b5](https://github.com/feathersjs/feathers/commit/5b801b5017ddc3eaa95622b539f51d605916bc86)) +# [5.0.0-pre.23](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.22...v5.0.0-pre.23) (2022-06-06) -# [5.0.0-pre.13](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.12...v5.0.0-pre.13) (2021-10-13) - -**Note:** Version bump only for package @feathersjs/feathers +### Features +- **client:** Improve client side custom method support ([#2654](https://github.com/feathersjs/feathers/issues/2654)) ([c138acf](https://github.com/feathersjs/feathers/commit/c138acf50affbe6b66177d084d3c7a3e9220f09f)) +- **core:** Rename async hooks to around hooks, allow usual registration format ([#2652](https://github.com/feathersjs/feathers/issues/2652)) ([2a485a0](https://github.com/feathersjs/feathers/commit/2a485a07929184261f27437fc0fdfe5a44694834)) +# [5.0.0-pre.22](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.21...v5.0.0-pre.22) (2022-05-24) +### Bug Fixes +- **schema:** Allows resolveData with different resolvers based on method ([#2644](https://github.com/feathersjs/feathers/issues/2644)) ([be71fa2](https://github.com/feathersjs/feathers/commit/be71fa2fe260e05b7dcc0d5f439e33f2e9ec2434)) -# [5.0.0-pre.12](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.11...v5.0.0-pre.12) (2021-10-12) +# [5.0.0-pre.21](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.20...v5.0.0-pre.21) (2022-05-23) -**Note:** Version bump only for package @feathersjs/feathers +### Bug Fixes +- **core:** Do not throw missing method error for regular hook methods ([#2636](https://github.com/feathersjs/feathers/issues/2636)) ([afe9a3b](https://github.com/feathersjs/feathers/commit/afe9a3b3d49897eff045ee237ca2937a6b975291)) +# [5.0.0-pre.20](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.19...v5.0.0-pre.20) (2022-05-04) +### Bug Fixes +- **dependencies:** Lock monorepo package version numbers ([#2623](https://github.com/feathersjs/feathers/issues/2623)) ([5640c10](https://github.com/feathersjs/feathers/commit/5640c1020cc139994e695d658c08bad3494db507)) -# [5.0.0-pre.11](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.10...v5.0.0-pre.11) (2021-10-06) +# [5.0.0-pre.19](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.18...v5.0.0-pre.19) (2022-05-01) +### Features -### Bug Fixes +- **typescript:** Improve adapter typings ([#2605](https://github.com/feathersjs/feathers/issues/2605)) ([3b2ca0a](https://github.com/feathersjs/feathers/commit/3b2ca0a6a8e03e8390272c4d7e930b4bffdaacf5)) +- **typescript:** Improve params and query typeability ([#2600](https://github.com/feathersjs/feathers/issues/2600)) ([df28b76](https://github.com/feathersjs/feathers/commit/df28b7619161f1df5e700326f52cca1a92dc5d28)) -* **core:** Allow to return a new hook context in basic hooks ([#2462](https://github.com/feathersjs/feathers/issues/2462)) ([422b6fc](https://github.com/feathersjs/feathers/commit/422b6fc11cf9e42f4234f0823a0b06a4df50982d)) +# [5.0.0-pre.18](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.17...v5.0.0-pre.18) (2022-04-11) +### Bug Fixes +- **core:** Ensure that dynamically registered services are always set up ([#2593](https://github.com/feathersjs/feathers/issues/2593)) ([27cc7d0](https://github.com/feathersjs/feathers/commit/27cc7d08321861cd69e6b66e1fdfa43c50664820)) +### Features +- **authentication:** Add setup method for auth strategies ([#1611](https://github.com/feathersjs/feathers/issues/1611)) ([a3c3581](https://github.com/feathersjs/feathers/commit/a3c35814dccdbbf6de96f04f60b226ce206c6dbe)) +- **core:** Add app.setup and app.teardown hook support ([#2585](https://github.com/feathersjs/feathers/issues/2585)) ([ae4ebee](https://github.com/feathersjs/feathers/commit/ae4ebee5d39957651473007c4d3adb210160e040)) +- **core:** Add app.teardown functionality ([#2570](https://github.com/feathersjs/feathers/issues/2570)) ([fcdf524](https://github.com/feathersjs/feathers/commit/fcdf524ae1995bb59265d39f12e98b7794bed023)) +- **core:** Finalize app.teardown() functionality ([#2584](https://github.com/feathersjs/feathers/issues/2584)) ([1a166f3](https://github.com/feathersjs/feathers/commit/1a166f3ded811ecacf0ae8cb67880bc9fa2eeafa)) +- **transport-commons:** add `context.http.response` ([#2524](https://github.com/feathersjs/feathers/issues/2524)) ([5bc9d44](https://github.com/feathersjs/feathers/commit/5bc9d447043c2e2b742c73ed28ecf3b3264dd9e5)) -# [5.0.0-pre.10](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.9...v5.0.0-pre.10) (2021-09-19) +# [5.0.0-pre.17](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.16...v5.0.0-pre.17) (2022-02-15) **Note:** Version bump only for package @feathersjs/feathers +# [5.0.0-pre.16](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.15...v5.0.0-pre.16) (2022-01-12) +### Features +- **express, koa:** make transports similar ([#2486](https://github.com/feathersjs/feathers/issues/2486)) ([26aa937](https://github.com/feathersjs/feathers/commit/26aa937c114fb8596dfefc599b1f53cead69c159)) +# [5.0.0-pre.15](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.14...v5.0.0-pre.15) (2021-11-27) -# [5.0.0-pre.9](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.8...v5.0.0-pre.9) (2021-08-09) - -**Note:** Version bump only for package @feathersjs/feathers - +### Bug Fixes +- **typescript:** Overall typing improvements ([#2478](https://github.com/feathersjs/feathers/issues/2478)) ([b8eb804](https://github.com/feathersjs/feathers/commit/b8eb804158556d9651a8607e3c3fda15e0bfd110)) +### Features +- **core:** add `context.http` and move `statusCode` there ([#2496](https://github.com/feathersjs/feathers/issues/2496)) ([b701bf7](https://github.com/feathersjs/feathers/commit/b701bf77fb83048aa1dffa492b3d77dd53f7b72b)) +- **core:** Improve legacy hooks integration ([08c8b40](https://github.com/feathersjs/feathers/commit/08c8b40999bf3889c61a4d4fad97a2c4f78bafc9)) +- **transport-commons:** Ability to register routes with custom params ([#2482](https://github.com/feathersjs/feathers/issues/2482)) ([497990a](https://github.com/feathersjs/feathers/commit/497990ae4a980e5a52a1f0f932db12cd0e6e254a)) -# [5.0.0-pre.8](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.7...v5.0.0-pre.8) (2021-08-09) +# [5.0.0-pre.14](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.13...v5.0.0-pre.14) (2021-10-13) **Note:** Version bump only for package @feathersjs/feathers +# [5.0.0-pre.13](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.12...v5.0.0-pre.13) (2021-10-13) +**Note:** Version bump only for package @feathersjs/feathers +# [5.0.0-pre.12](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.11...v5.0.0-pre.12) (2021-10-12) +**Note:** Version bump only for package @feathersjs/feathers -# [5.0.0-pre.7](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.6...v5.0.0-pre.7) (2021-08-09) - +# [5.0.0-pre.11](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.10...v5.0.0-pre.11) (2021-10-06) ### Bug Fixes -* **core:** Clean up readme ([eb3b4f2](https://github.com/feathersjs/feathers/commit/eb3b4f248c0816c92a2300cceed18a6f2518508a)) -* **core:** Set version back to development ([b328767](https://github.com/feathersjs/feathers/commit/b3287676cd773e164fd646ba4cffbf81983a9157)) +- **core:** Allow to return a new hook context in basic hooks ([#2462](https://github.com/feathersjs/feathers/issues/2462)) ([422b6fc](https://github.com/feathersjs/feathers/commit/422b6fc11cf9e42f4234f0823a0b06a4df50982d)) +# [5.0.0-pre.10](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.9...v5.0.0-pre.10) (2021-09-19) +**Note:** Version bump only for package @feathersjs/feathers +# [5.0.0-pre.9](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.8...v5.0.0-pre.9) (2021-08-09) +**Note:** Version bump only for package @feathersjs/feathers -# [5.0.0-pre.6](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.5...v5.0.0-pre.6) (2021-08-08) +# [5.0.0-pre.8](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.7...v5.0.0-pre.8) (2021-08-09) **Note:** Version bump only for package @feathersjs/feathers +# [5.0.0-pre.7](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.6...v5.0.0-pre.7) (2021-08-09) +### Bug Fixes +- **core:** Clean up readme ([eb3b4f2](https://github.com/feathersjs/feathers/commit/eb3b4f248c0816c92a2300cceed18a6f2518508a)) +- **core:** Set version back to development ([b328767](https://github.com/feathersjs/feathers/commit/b3287676cd773e164fd646ba4cffbf81983a9157)) +# [5.0.0-pre.6](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.5...v5.0.0-pre.6) (2021-08-08) -# [5.0.0-pre.5](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.4...v5.0.0-pre.5) (2021-06-23) +**Note:** Version bump only for package @feathersjs/feathers +# [5.0.0-pre.5](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.4...v5.0.0-pre.5) (2021-06-23) ### Bug Fixes -* **core:** Add list of protected methods that can not be used for custom methods ([#2390](https://github.com/feathersjs/feathers/issues/2390)) ([6584a21](https://github.com/feathersjs/feathers/commit/6584a216e5a7d5f2a45822be6bfcb91c35cc2252)) - - - - +- **core:** Add list of protected methods that can not be used for custom methods ([#2390](https://github.com/feathersjs/feathers/issues/2390)) ([6584a21](https://github.com/feathersjs/feathers/commit/6584a216e5a7d5f2a45822be6bfcb91c35cc2252)) # [5.0.0-pre.4](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.3...v5.0.0-pre.4) (2021-05-13) - ### Bug Fixes -* **typescript:** Move Paginated type back for better compatibility ([#2350](https://github.com/feathersjs/feathers/issues/2350)) ([2917d05](https://github.com/feathersjs/feathers/commit/2917d05fffb4716d3c4cdaa5ac6a1aee0972e8a6)) - - - - +- **typescript:** Move Paginated type back for better compatibility ([#2350](https://github.com/feathersjs/feathers/issues/2350)) ([2917d05](https://github.com/feathersjs/feathers/commit/2917d05fffb4716d3c4cdaa5ac6a1aee0972e8a6)) # [5.0.0-pre.3](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.2...v5.0.0-pre.3) (2021-04-21) - ### Bug Fixes -* **typescript:** Improve TypeScript backwards compatibility ([#2310](https://github.com/feathersjs/feathers/issues/2310)) ([f33be73](https://github.com/feathersjs/feathers/commit/f33be73fc46a533efb15df9aab0658e3240d3897)) - +- **typescript:** Improve TypeScript backwards compatibility ([#2310](https://github.com/feathersjs/feathers/issues/2310)) ([f33be73](https://github.com/feathersjs/feathers/commit/f33be73fc46a533efb15df9aab0658e3240d3897)) ### Features -* **deno:** Feathers core build for Deno ([#2299](https://github.com/feathersjs/feathers/issues/2299)) ([dece8fb](https://github.com/feathersjs/feathers/commit/dece8fbc0e7601f1505ce8bbb1e4e69cc26e8f98)) -* **dependencies:** Remove direct debug dependency ([#2296](https://github.com/feathersjs/feathers/issues/2296)) ([501d416](https://github.com/feathersjs/feathers/commit/501d4164d30c6a126906dc640cdfdc82207ba34a)) - - - - +- **deno:** Feathers core build for Deno ([#2299](https://github.com/feathersjs/feathers/issues/2299)) ([dece8fb](https://github.com/feathersjs/feathers/commit/dece8fbc0e7601f1505ce8bbb1e4e69cc26e8f98)) +- **dependencies:** Remove direct debug dependency ([#2296](https://github.com/feathersjs/feathers/issues/2296)) ([501d416](https://github.com/feathersjs/feathers/commit/501d4164d30c6a126906dc640cdfdc82207ba34a)) # [5.0.0-pre.2](https://github.com/feathersjs/feathers/compare/v5.0.0-beta.1...v5.0.0-pre.2) (2021-04-06) **Note:** Version bump only for package @feathersjs/feathers - - - - # [5.0.0-beta.1](https://github.com/feathersjs/feathers/compare/v5.0.0-beta.0...v5.0.0-beta.1) (2021-04-03) - ### Bug Fixes -* **dependencies:** Fix transport-commons dependency and update other dependencies ([#2284](https://github.com/feathersjs/feathers/issues/2284)) ([05b03b2](https://github.com/feathersjs/feathers/commit/05b03b27b40604d956047e3021d8053c3a137616)) -* **feathers:** Always enable hooks on default service methods ([#2275](https://github.com/feathersjs/feathers/issues/2275)) ([827cc9b](https://github.com/feathersjs/feathers/commit/827cc9b752eecdaf63605d7dffd86f531b7e4af3)) - - - - +- **dependencies:** Fix transport-commons dependency and update other dependencies ([#2284](https://github.com/feathersjs/feathers/issues/2284)) ([05b03b2](https://github.com/feathersjs/feathers/commit/05b03b27b40604d956047e3021d8053c3a137616)) +- **feathers:** Always enable hooks on default service methods ([#2275](https://github.com/feathersjs/feathers/issues/2275)) ([827cc9b](https://github.com/feathersjs/feathers/commit/827cc9b752eecdaf63605d7dffd86f531b7e4af3)) # [5.0.0-beta.0](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.1...v5.0.0-beta.0) (2021-03-28) - ### Bug Fixes -* Resolve some type problems ([#2260](https://github.com/feathersjs/feathers/issues/2260)) ([a3d75fa](https://github.com/feathersjs/feathers/commit/a3d75fa29490e8a19412a12bc993ee7bb573068f)) -* Update Grant usage and other dependencies ([#2264](https://github.com/feathersjs/feathers/issues/2264)) ([7b0f8fa](https://github.com/feathersjs/feathers/commit/7b0f8fad252419ed0ad0bf259cdf3104d322ab60)) - +- Resolve some type problems ([#2260](https://github.com/feathersjs/feathers/issues/2260)) ([a3d75fa](https://github.com/feathersjs/feathers/commit/a3d75fa29490e8a19412a12bc993ee7bb573068f)) +- Update Grant usage and other dependencies ([#2264](https://github.com/feathersjs/feathers/issues/2264)) ([7b0f8fa](https://github.com/feathersjs/feathers/commit/7b0f8fad252419ed0ad0bf259cdf3104d322ab60)) ### Features -* **core:** Public custom service methods ([#2270](https://github.com/feathersjs/feathers/issues/2270)) ([e65abfb](https://github.com/feathersjs/feathers/commit/e65abfb5388df6c19a11c565cf1076a29f32668d)) -* Application service types default to any ([#1566](https://github.com/feathersjs/feathers/issues/1566)) ([d93ba9a](https://github.com/feathersjs/feathers/commit/d93ba9a17edd20d3397bb00f4f6e82e804e42ed6)) -* Feathers v5 core refactoring and features ([#2255](https://github.com/feathersjs/feathers/issues/2255)) ([2dafb7c](https://github.com/feathersjs/feathers/commit/2dafb7ce14ba57406aeec13d10ca45b1e709bee9)) -* **core:** Remove Uberproto ([#2178](https://github.com/feathersjs/feathers/issues/2178)) ([ddf8821](https://github.com/feathersjs/feathers/commit/ddf8821f53317e6a378657f7d66acb03a037ee47)) - +- **core:** Public custom service methods ([#2270](https://github.com/feathersjs/feathers/issues/2270)) ([e65abfb](https://github.com/feathersjs/feathers/commit/e65abfb5388df6c19a11c565cf1076a29f32668d)) +- Application service types default to any ([#1566](https://github.com/feathersjs/feathers/issues/1566)) ([d93ba9a](https://github.com/feathersjs/feathers/commit/d93ba9a17edd20d3397bb00f4f6e82e804e42ed6)) +- Feathers v5 core refactoring and features ([#2255](https://github.com/feathersjs/feathers/issues/2255)) ([2dafb7c](https://github.com/feathersjs/feathers/commit/2dafb7ce14ba57406aeec13d10ca45b1e709bee9)) +- **core:** Remove Uberproto ([#2178](https://github.com/feathersjs/feathers/issues/2178)) ([ddf8821](https://github.com/feathersjs/feathers/commit/ddf8821f53317e6a378657f7d66acb03a037ee47)) ### BREAKING CHANGES -* **core:** Services no longer extend Uberproto objects and -`service.mixin()` is no longer available. - - - - +- **core:** Services no longer extend Uberproto objects and + `service.mixin()` is no longer available. # [5.0.0-pre.1](https://github.com/feathersjs/feathers/compare/v4.5.11...v5.0.0-pre.1) (2020-12-17) - - # [5.0.0-pre.0](https://github.com/feathersjs/feathers/compare/v4.5.4...v5.0.0-pre.0) (2020-05-19) - ### Features -* **core:** Migrate @feathersjs/feathers to TypeScript ([#1963](https://github.com/feathersjs/feathers/issues/1963)) ([7812529](https://github.com/feathersjs/feathers/commit/7812529ff0f1008e21211f1d01efbc49795dbe55)) -* **core:** use @feathers/hooks and add async type ([#1929](https://github.com/feathersjs/feathers/issues/1929)) ([a5c4756](https://github.com/feathersjs/feathers/commit/a5c47562eae8410c82fe2f6308f26f8e78b6a3e8)) - - - - +- **core:** Migrate @feathersjs/feathers to TypeScript ([#1963](https://github.com/feathersjs/feathers/issues/1963)) ([7812529](https://github.com/feathersjs/feathers/commit/7812529ff0f1008e21211f1d01efbc49795dbe55)) +- **core:** use @feathers/hooks and add async type ([#1929](https://github.com/feathersjs/feathers/issues/1929)) ([a5c4756](https://github.com/feathersjs/feathers/commit/a5c47562eae8410c82fe2f6308f26f8e78b6a3e8)) # [5.0.0-pre.0](https://github.com/feathersjs/feathers/compare/v4.5.4...v5.0.0-pre.0) (2020-05-19) - ### Features -* **core:** Migrate @feathersjs/feathers to TypeScript ([#1963](https://github.com/feathersjs/feathers/issues/1963)) ([7812529](https://github.com/feathersjs/feathers/commit/7812529ff0f1008e21211f1d01efbc49795dbe55)) -* **core:** use @feathers/hooks and add async type ([#1929](https://github.com/feathersjs/feathers/issues/1929)) ([a5c4756](https://github.com/feathersjs/feathers/commit/a5c47562eae8410c82fe2f6308f26f8e78b6a3e8)) - - +- **core:** Migrate @feathersjs/feathers to TypeScript ([#1963](https://github.com/feathersjs/feathers/issues/1963)) ([7812529](https://github.com/feathersjs/feathers/commit/7812529ff0f1008e21211f1d01efbc49795dbe55)) +- **core:** use @feathers/hooks and add async type ([#1929](https://github.com/feathersjs/feathers/issues/1929)) ([a5c4756](https://github.com/feathersjs/feathers/commit/a5c47562eae8410c82fe2f6308f26f8e78b6a3e8)) ## [4.5.11](https://github.com/feathersjs/feathers/compare/v4.5.10...v4.5.11) (2020-12-05) **Note:** Version bump only for package @feathersjs/feathers - - - - ## [4.5.10](https://github.com/feathersjs/feathers/compare/v4.5.9...v4.5.10) (2020-11-08) - ### Bug Fixes -* **typescript:** Add user property to the Params. ([#2090](https://github.com/feathersjs/feathers/issues/2090)) ([1e94265](https://github.com/feathersjs/feathers/commit/1e942651fbaaf07fc66c159225fbc992a0174bf4)) - - - - +- **typescript:** Add user property to the Params. ([#2090](https://github.com/feathersjs/feathers/issues/2090)) ([1e94265](https://github.com/feathersjs/feathers/commit/1e942651fbaaf07fc66c159225fbc992a0174bf4)) ## [4.5.9](https://github.com/feathersjs/feathers/compare/v4.5.8...v4.5.9) (2020-10-09) **Note:** Version bump only for package @feathersjs/feathers - - - - ## [4.5.8](https://github.com/feathersjs/feathers/compare/v4.5.7...v4.5.8) (2020-08-12) **Note:** Version bump only for package @feathersjs/feathers - - - - ## [4.5.7](https://github.com/feathersjs/feathers/compare/v4.5.6...v4.5.7) (2020-07-24) - ### Bug Fixes -* **typescript:** Revert add overload types for `find` service methods ([#1972](https://github.com/feathersjs/feathers/issues/1972))" ([#2025](https://github.com/feathersjs/feathers/issues/2025)) ([a9501ac](https://github.com/feathersjs/feathers/commit/a9501acb4d3ef58dfb87d62c57a9bf76569da281)) - - - - +- **typescript:** Revert add overload types for `find` service methods ([#1972](https://github.com/feathersjs/feathers/issues/1972))" ([#2025](https://github.com/feathersjs/feathers/issues/2025)) ([a9501ac](https://github.com/feathersjs/feathers/commit/a9501acb4d3ef58dfb87d62c57a9bf76569da281)) ## [4.5.5](https://github.com/feathersjs/feathers/compare/v4.5.4...v4.5.5) (2020-07-11) - ### Bug Fixes -* **typescript:** add overload types for `find` service methods ([#1972](https://github.com/feathersjs/feathers/issues/1972)) ([ef55af0](https://github.com/feathersjs/feathers/commit/ef55af088d05d9d36aba9d9f8d6c2c908a4f20dd)) - - - - +- **typescript:** add overload types for `find` service methods ([#1972](https://github.com/feathersjs/feathers/issues/1972)) ([ef55af0](https://github.com/feathersjs/feathers/commit/ef55af088d05d9d36aba9d9f8d6c2c908a4f20dd)) ## [4.5.3](https://github.com/feathersjs/feathers/compare/v4.5.2...v4.5.3) (2020-04-17) - ### Bug Fixes -* **typescript:** Use stricter type for HookContext 'method' prop ([#1896](https://github.com/feathersjs/feathers/issues/1896)) ([24a41b7](https://github.com/feathersjs/feathers/commit/24a41b74486ddadccad18f3ae63afdac5bd373c7)) - - - - +- **typescript:** Use stricter type for HookContext 'method' prop ([#1896](https://github.com/feathersjs/feathers/issues/1896)) ([24a41b7](https://github.com/feathersjs/feathers/commit/24a41b74486ddadccad18f3ae63afdac5bd373c7)) ## [4.5.2](https://github.com/feathersjs/feathers/compare/v4.5.1...v4.5.2) (2020-03-04) - ### Bug Fixes -* **typescript:** Make HookMap and HookObject generics. ([#1815](https://github.com/feathersjs/feathers/issues/1815)) ([d10145d](https://github.com/feathersjs/feathers/commit/d10145d91a09aef7bce5af80805a3c0fa9d94f26)) - - - - +- **typescript:** Make HookMap and HookObject generics. ([#1815](https://github.com/feathersjs/feathers/issues/1815)) ([d10145d](https://github.com/feathersjs/feathers/commit/d10145d91a09aef7bce5af80805a3c0fa9d94f26)) ## [4.5.1](https://github.com/feathersjs/feathers/compare/v4.5.0...v4.5.1) (2020-01-24) **Note:** Version bump only for package @feathersjs/feathers - - - - # [4.5.0](https://github.com/feathersjs/feathers/compare/v4.4.3...v4.5.0) (2020-01-18) - ### Bug Fixes -* Add `params.authentication` type, remove `hook.connection` type ([#1732](https://github.com/feathersjs/feathers/issues/1732)) ([d46b7b2](https://github.com/feathersjs/feathers/commit/d46b7b2abac8862c0e4dbfce20d71b8b8a96692f)) - - - - +- Add `params.authentication` type, remove `hook.connection` type ([#1732](https://github.com/feathersjs/feathers/issues/1732)) ([d46b7b2](https://github.com/feathersjs/feathers/commit/d46b7b2abac8862c0e4dbfce20d71b8b8a96692f)) ## [4.4.3](https://github.com/feathersjs/feathers/compare/v4.4.1...v4.4.3) (2019-12-06) **Note:** Version bump only for package @feathersjs/feathers - - - - ## [4.4.1](https://github.com/feathersjs/feathers/compare/v4.4.0...v4.4.1) (2019-11-27) **Note:** Version bump only for package @feathersjs/feathers - - - - # [4.4.0](https://github.com/feathersjs/feathers/compare/v4.3.11...v4.4.0) (2019-11-27) - ### Bug Fixes -* **core:** Improve hook missing parameter message by adding the service name ([#1703](https://github.com/feathersjs/feathers/issues/1703)) ([2331c2a](https://github.com/feathersjs/feathers/commit/2331c2a3dd70d432db7d62a76ed805d359cbbba5)) -* **typescript:** Allow specific service typings for `Hook` and `HookContext` ([#1688](https://github.com/feathersjs/feathers/issues/1688)) ([f5d0ddd](https://github.com/feathersjs/feathers/commit/f5d0ddd9724bf5778355535d2103d59daaad6294)) - - - - +- **core:** Improve hook missing parameter message by adding the service name ([#1703](https://github.com/feathersjs/feathers/issues/1703)) ([2331c2a](https://github.com/feathersjs/feathers/commit/2331c2a3dd70d432db7d62a76ed805d359cbbba5)) +- **typescript:** Allow specific service typings for `Hook` and `HookContext` ([#1688](https://github.com/feathersjs/feathers/issues/1688)) ([f5d0ddd](https://github.com/feathersjs/feathers/commit/f5d0ddd9724bf5778355535d2103d59daaad6294)) ## [4.3.11](https://github.com/feathersjs/feathers/compare/v4.3.10...v4.3.11) (2019-11-11) **Note:** Version bump only for package @feathersjs/feathers - - - - ## [4.3.10](https://github.com/feathersjs/feathers/compare/v4.3.9...v4.3.10) (2019-10-26) **Note:** Version bump only for package @feathersjs/feathers - - - - ## [4.3.9](https://github.com/feathersjs/feathers/compare/v4.3.8...v4.3.9) (2019-10-26) - ### Bug Fixes -* Small type improvements ([#1624](https://github.com/feathersjs/feathers/issues/1624)) ([50162c6](https://github.com/feathersjs/feathers/commit/50162c6e562f0a47c6a280c4f01fff7c3afee293)) - - - - +- Small type improvements ([#1624](https://github.com/feathersjs/feathers/issues/1624)) ([50162c6](https://github.com/feathersjs/feathers/commit/50162c6e562f0a47c6a280c4f01fff7c3afee293)) ## [4.3.7](https://github.com/feathersjs/feathers/compare/v4.3.6...v4.3.7) (2019-10-14) - ### Bug Fixes -* improve Service and AdapterService types ([#1567](https://github.com/feathersjs/feathers/issues/1567)) ([baad6a2](https://github.com/feathersjs/feathers/commit/baad6a26f0f543b712ccb40359b3933ad3a21392)) - - - - +- improve Service and AdapterService types ([#1567](https://github.com/feathersjs/feathers/issues/1567)) ([baad6a2](https://github.com/feathersjs/feathers/commit/baad6a26f0f543b712ccb40359b3933ad3a21392)) ## [4.3.4](https://github.com/feathersjs/feathers/compare/v4.3.3...v4.3.4) (2019-10-03) - ### Bug Fixes -* Reset version number after every publish ([#1596](https://github.com/feathersjs/feathers/issues/1596)) ([f24f82f](https://github.com/feathersjs/feathers/commit/f24f82f)) - - - - +- Reset version number after every publish ([#1596](https://github.com/feathersjs/feathers/issues/1596)) ([f24f82f](https://github.com/feathersjs/feathers/commit/f24f82f)) ## [4.3.3](https://github.com/feathersjs/feathers/compare/v4.3.2...v4.3.3) (2019-09-21) - ### Bug Fixes -* Small improvements in dependencies and code sturcture ([#1562](https://github.com/feathersjs/feathers/issues/1562)) ([42c13e2](https://github.com/feathersjs/feathers/commit/42c13e2)) - - - - +- Small improvements in dependencies and code sturcture ([#1562](https://github.com/feathersjs/feathers/issues/1562)) ([42c13e2](https://github.com/feathersjs/feathers/commit/42c13e2)) ## [4.3.2](https://github.com/feathersjs/feathers/compare/v4.3.1...v4.3.2) (2019-09-16) **Note:** Version bump only for package @feathersjs/feathers - - - - ## [4.3.1](https://github.com/feathersjs/feathers/compare/v4.3.0...v4.3.1) (2019-09-09) **Note:** Version bump only for package @feathersjs/feathers - - - - # [4.3.0](https://github.com/feathersjs/feathers/compare/v4.3.0-pre.4...v4.3.0) (2019-08-27) **Note:** Version bump only for package @feathersjs/feathers - - - - # [4.3.0-pre.4](https://github.com/feathersjs/feathers/compare/v4.3.0-pre.3...v4.3.0-pre.4) (2019-08-22) **Note:** Version bump only for package @feathersjs/feathers - - - - # [4.3.0-pre.3](https://github.com/feathersjs/feathers/compare/v4.3.0-pre.2...v4.3.0-pre.3) (2019-08-19) **Note:** Version bump only for package @feathersjs/feathers - - - - # [4.3.0-pre.2](https://github.com/feathersjs/feathers/compare/v4.3.0-pre.1...v4.3.0-pre.2) (2019-08-02) - ### Bug Fixes -* Improve Params typing ([#1474](https://github.com/feathersjs/feathers/issues/1474)) ([54a3aa7](https://github.com/feathersjs/feathers/commit/54a3aa7)) - - - - +- Improve Params typing ([#1474](https://github.com/feathersjs/feathers/issues/1474)) ([54a3aa7](https://github.com/feathersjs/feathers/commit/54a3aa7)) # [4.3.0-pre.1](https://github.com/feathersjs/feathers/compare/v4.0.0-pre.5...v4.3.0-pre.1) (2019-07-11) **Note:** Version bump only for package @feathersjs/feathers - - - - # [4.0.0-pre.5](https://github.com/feathersjs/feathers/compare/v4.0.0-pre.4...v4.0.0-pre.5) (2019-07-10) **Note:** Version bump only for package @feathersjs/feathers - - - - # [4.0.0-pre.4](https://github.com/feathersjs/feathers/compare/v4.0.0-pre.3...v4.0.0-pre.4) (2019-07-05) - ### Bug Fixes -* Clean up hooks code ([#1407](https://github.com/feathersjs/feathers/issues/1407)) ([f25c88b](https://github.com/feathersjs/feathers/commit/f25c88b)) -* Fix @feathersjs/feathers typings http import ([abbc07b](https://github.com/feathersjs/feathers/commit/abbc07b)) -* Updated typings for ServiceMethods ([#1409](https://github.com/feathersjs/feathers/issues/1409)) ([b5ee7e2](https://github.com/feathersjs/feathers/commit/b5ee7e2)) - - - - +- Clean up hooks code ([#1407](https://github.com/feathersjs/feathers/issues/1407)) ([f25c88b](https://github.com/feathersjs/feathers/commit/f25c88b)) +- Fix @feathersjs/feathers typings http import ([abbc07b](https://github.com/feathersjs/feathers/commit/abbc07b)) +- Updated typings for ServiceMethods ([#1409](https://github.com/feathersjs/feathers/issues/1409)) ([b5ee7e2](https://github.com/feathersjs/feathers/commit/b5ee7e2)) # [4.0.0-pre.3](https://github.com/feathersjs/feathers/compare/v4.0.0-pre.2...v4.0.0-pre.3) (2019-06-01) - ### Bug Fixes -* Typings fix and improvements. ([#1364](https://github.com/feathersjs/feathers/issues/1364)) ([515b916](https://github.com/feathersjs/feathers/commit/515b916)) -* Update dependencies and fix tests ([#1373](https://github.com/feathersjs/feathers/issues/1373)) ([d743a7f](https://github.com/feathersjs/feathers/commit/d743a7f)) - - - - +- Typings fix and improvements. ([#1364](https://github.com/feathersjs/feathers/issues/1364)) ([515b916](https://github.com/feathersjs/feathers/commit/515b916)) +- Update dependencies and fix tests ([#1373](https://github.com/feathersjs/feathers/issues/1373)) ([d743a7f](https://github.com/feathersjs/feathers/commit/d743a7f)) # [4.0.0-pre.2](https://github.com/feathersjs/feathers/compare/v4.0.0-pre.1...v4.0.0-pre.2) (2019-05-15) - ### Bug Fixes -* **typescript:** finally should be optional ([#1350](https://github.com/feathersjs/feathers/issues/1350)) ([f439a9e](https://github.com/feathersjs/feathers/commit/f439a9e)) -* Fix versioning tests. Closes [#1346](https://github.com/feathersjs/feathers/issues/1346) ([dd519f6](https://github.com/feathersjs/feathers/commit/dd519f6)) -* Use `export =` in TypeScript definitions ([#1285](https://github.com/feathersjs/feathers/issues/1285)) ([12d0f4b](https://github.com/feathersjs/feathers/commit/12d0f4b)) - - - - +- **typescript:** finally should be optional ([#1350](https://github.com/feathersjs/feathers/issues/1350)) ([f439a9e](https://github.com/feathersjs/feathers/commit/f439a9e)) +- Fix versioning tests. Closes [#1346](https://github.com/feathersjs/feathers/issues/1346) ([dd519f6](https://github.com/feathersjs/feathers/commit/dd519f6)) +- Use `export =` in TypeScript definitions ([#1285](https://github.com/feathersjs/feathers/issues/1285)) ([12d0f4b](https://github.com/feathersjs/feathers/commit/12d0f4b)) # [4.0.0-pre.1](https://github.com/feathersjs/feathers/compare/v4.0.0-pre.0...v4.0.0-pre.1) (2019-05-08) - ### Bug Fixes -* Update version number check ([53575c5](https://github.com/feathersjs/feathers/commit/53575c5)) -* Updated HooksObject typings ([#1300](https://github.com/feathersjs/feathers/issues/1300)) ([b28058c](https://github.com/feathersjs/feathers/commit/b28058c)) - - - - +- Update version number check ([53575c5](https://github.com/feathersjs/feathers/commit/53575c5)) +- Updated HooksObject typings ([#1300](https://github.com/feathersjs/feathers/issues/1300)) ([b28058c](https://github.com/feathersjs/feathers/commit/b28058c)) # [4.0.0-pre.0](https://github.com/feathersjs/feathers/compare/v3.2.0-pre.1...v4.0.0-pre.0) (2019-04-21) - ### Bug Fixes -* Do not inherit app object from Object prototype ([#1153](https://github.com/feathersjs/feathers/issues/1153)) ([ed8c2e4](https://github.com/feathersjs/feathers/commit/ed8c2e4)) -* Make Mocha a proper devDependency for every repository ([#1053](https://github.com/feathersjs/feathers/issues/1053)) ([9974803](https://github.com/feathersjs/feathers/commit/9974803)) -* Normalize params to object even when it is falsy ([#1012](https://github.com/feathersjs/feathers/issues/1012)) ([af97818](https://github.com/feathersjs/feathers/commit/af97818)) -* Update adapter common tests ([#1135](https://github.com/feathersjs/feathers/issues/1135)) ([8166dda](https://github.com/feathersjs/feathers/commit/8166dda)) -* Update all dependencies to latest ([#1206](https://github.com/feathersjs/feathers/issues/1206)) ([e51e0f6](https://github.com/feathersjs/feathers/commit/e51e0f6)) - +- Do not inherit app object from Object prototype ([#1153](https://github.com/feathersjs/feathers/issues/1153)) ([ed8c2e4](https://github.com/feathersjs/feathers/commit/ed8c2e4)) +- Make Mocha a proper devDependency for every repository ([#1053](https://github.com/feathersjs/feathers/issues/1053)) ([9974803](https://github.com/feathersjs/feathers/commit/9974803)) +- Normalize params to object even when it is falsy ([#1012](https://github.com/feathersjs/feathers/issues/1012)) ([af97818](https://github.com/feathersjs/feathers/commit/af97818)) +- Update adapter common tests ([#1135](https://github.com/feathersjs/feathers/issues/1135)) ([8166dda](https://github.com/feathersjs/feathers/commit/8166dda)) +- Update all dependencies to latest ([#1206](https://github.com/feathersjs/feathers/issues/1206)) ([e51e0f6](https://github.com/feathersjs/feathers/commit/e51e0f6)) ### Features -* Add TypeScript definitions ([#1275](https://github.com/feathersjs/feathers/issues/1275)) ([9dd6713](https://github.com/feathersjs/feathers/commit/9dd6713)) -* Allow registering a service at the root level ([#1115](https://github.com/feathersjs/feathers/issues/1115)) ([c73d322](https://github.com/feathersjs/feathers/commit/c73d322)) -* Allow to skip sending service events ([#1270](https://github.com/feathersjs/feathers/issues/1270)) ([b487bbd](https://github.com/feathersjs/feathers/commit/b487bbd)) -* Remove (hook, next) signature and SKIP support ([#1269](https://github.com/feathersjs/feathers/issues/1269)) ([211c0f8](https://github.com/feathersjs/feathers/commit/211c0f8)) - - - - +- Add TypeScript definitions ([#1275](https://github.com/feathersjs/feathers/issues/1275)) ([9dd6713](https://github.com/feathersjs/feathers/commit/9dd6713)) +- Allow registering a service at the root level ([#1115](https://github.com/feathersjs/feathers/issues/1115)) ([c73d322](https://github.com/feathersjs/feathers/commit/c73d322)) +- Allow to skip sending service events ([#1270](https://github.com/feathersjs/feathers/issues/1270)) ([b487bbd](https://github.com/feathersjs/feathers/commit/b487bbd)) +- Remove (hook, next) signature and SKIP support ([#1269](https://github.com/feathersjs/feathers/issues/1269)) ([211c0f8](https://github.com/feathersjs/feathers/commit/211c0f8)) ## [3.3.1](https://github.com/feathersjs/feathers/compare/@feathersjs/feathers@3.3.0...@feathersjs/feathers@3.3.1) (2019-01-02) - ### Bug Fixes -* Do not inherit app object from Object prototype ([#1153](https://github.com/feathersjs/feathers/issues/1153)) ([ed8c2e4](https://github.com/feathersjs/feathers/commit/ed8c2e4)) -* Update adapter common tests ([#1135](https://github.com/feathersjs/feathers/issues/1135)) ([8166dda](https://github.com/feathersjs/feathers/commit/8166dda)) - - - - +- Do not inherit app object from Object prototype ([#1153](https://github.com/feathersjs/feathers/issues/1153)) ([ed8c2e4](https://github.com/feathersjs/feathers/commit/ed8c2e4)) +- Update adapter common tests ([#1135](https://github.com/feathersjs/feathers/issues/1135)) ([8166dda](https://github.com/feathersjs/feathers/commit/8166dda)) -# [3.3.0](https://github.com/feathersjs/feathers/compare/@feathersjs/feathers@3.2.3...@feathersjs/feathers@3.3.0) (2018-12-16) +# [3.3.0](https://github.com/feathersjs/feathers/compare/@feathersjs/feathers@3.2.3...@feathersjs/feathers@3.3.0) (2018-12-16) ### Bug Fixes -* Make Mocha a proper devDependency for every repository ([#1053](https://github.com/feathersjs/feathers/issues/1053)) ([9974803](https://github.com/feathersjs/feathers/commit/9974803)) - +- Make Mocha a proper devDependency for every repository ([#1053](https://github.com/feathersjs/feathers/issues/1053)) ([9974803](https://github.com/feathersjs/feathers/commit/9974803)) ### Features -* Allow registering a service at the root level ([#1115](https://github.com/feathersjs/feathers/issues/1115)) ([c73d322](https://github.com/feathersjs/feathers/commit/c73d322)) - - - - +- Allow registering a service at the root level ([#1115](https://github.com/feathersjs/feathers/issues/1115)) ([c73d322](https://github.com/feathersjs/feathers/commit/c73d322)) -## [3.2.3](https://github.com/feathersjs/feathers/compare/@feathersjs/feathers@3.2.2...@feathersjs/feathers@3.2.3) (2018-09-21) +## [3.2.3](https://github.com/feathersjs/feathers/compare/@feathersjs/feathers@3.2.2...@feathersjs/feathers@3.2.3) (2018-09-21) ### Bug Fixes -* Normalize params to object even when it is falsy ([#1012](https://github.com/feathersjs/feathers/issues/1012)) ([af97818](https://github.com/feathersjs/feathers/commit/af97818)) - - - - +- Normalize params to object even when it is falsy ([#1012](https://github.com/feathersjs/feathers/issues/1012)) ([af97818](https://github.com/feathersjs/feathers/commit/af97818)) + ## [3.2.2](https://github.com/feathersjs/feathers/compare/@feathersjs/feathers@3.2.1...@feathersjs/feathers@3.2.2) (2018-09-17) **Note:** Version bump only for package @feathersjs/feathers - - - - + ## [3.2.1](https://github.com/feathersjs/feathers/compare/@feathersjs/express@1.2.4...@feathersjs/feather@3.2.1) (2018-09-02) **Note:** Version bump only for package @feathersjs/express @@ -606,6 +451,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Migrate to Monorepo ([feathers#462](https://github.com/feathersjs/feathers/issues/462)) ## [v3.2.0](https://github.com/feathersjs/feathers/tree/v3.2.0-pre.1) (2018-08-19) + [Full Changelog](https://github.com/feathersjs/feathers/compare/v3.1.7...v3.2.0-pre.1) **Merged pull requests:** @@ -615,6 +461,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Allow adding hooks to other service methods [\#924](https://github.com/feathersjs/feathers/pull/924) ([bertho-zero](https://github.com/bertho-zero)) ## [v3.1.7](https://github.com/feathersjs/feathers/tree/v3.1.7) (2018-06-16) + [Full Changelog](https://github.com/feathersjs/feathers/compare/v3.1.6...v3.1.7) **Merged pull requests:** @@ -622,6 +469,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Update to latest Uberproto and other dependencies [\#889](https://github.com/feathersjs/feathers/pull/889) ([daffl](https://github.com/daffl)) ## [v3.1.6](https://github.com/feathersjs/feathers/tree/v3.1.6) (2018-06-03) + [Full Changelog](https://github.com/feathersjs/feathers/compare/v3.1.5...v3.1.6) **Merged pull requests:** @@ -632,6 +480,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Add Greenkeeper badge 🌴 [\#867](https://github.com/feathersjs/feathers/pull/867) ([greenkeeper[bot]](https://github.com/apps/greenkeeper)) ## [v3.1.5](https://github.com/feathersjs/feathers/tree/v3.1.5) (2018-05-04) + [Full Changelog](https://github.com/feathersjs/feathers/compare/v3.1.4...v3.1.5) **Merged pull requests:** @@ -639,6 +488,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Allow methods to return a null result [\#865](https://github.com/feathersjs/feathers/pull/865) ([bertho-zero](https://github.com/bertho-zero)) ## [v3.1.4](https://github.com/feathersjs/feathers/tree/v3.1.4) (2018-03-26) + [Full Changelog](https://github.com/feathersjs/feathers/compare/v3.1.3...v3.1.4) **Merged pull requests:** @@ -646,6 +496,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Make sure error hooks always have the original context information [\#842](https://github.com/feathersjs/feathers/pull/842) ([daffl](https://github.com/daffl)) ## [v3.1.3](https://github.com/feathersjs/feathers/tree/v3.1.3) (2018-02-16) + [Full Changelog](https://github.com/feathersjs/feathers/compare/v3.1.2...v3.1.3) **Merged pull requests:** @@ -653,6 +504,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Update events to the latest version 🚀 [\#810](https://github.com/feathersjs/feathers/pull/810) ([greenkeeper[bot]](https://github.com/apps/greenkeeper)) ## [v3.1.2](https://github.com/feathersjs/feathers/tree/v3.1.2) (2018-02-10) + [Full Changelog](https://github.com/feathersjs/feathers/compare/v3.1.1...v3.1.2) **Merged pull requests:** @@ -660,6 +512,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Handle errors in error hooks properly [\#819](https://github.com/feathersjs/feathers/pull/819) ([daffl](https://github.com/daffl)) ## [v3.1.1](https://github.com/feathersjs/feathers/tree/v3.1.1) (2018-02-08) + [Full Changelog](https://github.com/feathersjs/feathers/compare/v3.1.0...v3.1.1) **Merged pull requests:** @@ -668,6 +521,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Add Russian Telegram community [\#814](https://github.com/feathersjs/feathers/pull/814) ([vodniciarv](https://github.com/vodniciarv)) ## [v3.1.0](https://github.com/feathersjs/feathers/tree/v3.1.0) (2018-01-26) + [Full Changelog](https://github.com/feathersjs/feathers/compare/v3.0.5...v3.1.0) **Merged pull requests:** @@ -676,6 +530,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Add ability to skip all following hooks [\#792](https://github.com/feathersjs/feathers/pull/792) ([sylvainlap](https://github.com/sylvainlap)) ## [v3.0.5](https://github.com/feathersjs/feathers/tree/v3.0.5) (2018-01-04) + [Full Changelog](https://github.com/feathersjs/feathers/compare/v2.2.4...v3.0.5) **Merged pull requests:** @@ -683,9 +538,11 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Add backers & sponsors from Open Collective [\#504](https://github.com/feathersjs/feathers/pull/504) ([piamancini](https://github.com/piamancini)) ## [v2.2.4](https://github.com/feathersjs/feathers/tree/v2.2.4) (2018-01-04) + [Full Changelog](https://github.com/feathersjs/feathers/compare/v3.0.4...v2.2.4) ## [v3.0.4](https://github.com/feathersjs/feathers/tree/v3.0.4) (2018-01-03) + [Full Changelog](https://github.com/feathersjs/feathers/compare/v3.0.3...v3.0.4) **Merged pull requests:** @@ -693,6 +550,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Update Readme to correspond with latest release [\#772](https://github.com/feathersjs/feathers/pull/772) ([daffl](https://github.com/daffl)) ## [v3.0.3](https://github.com/feathersjs/feathers/tree/v3.0.3) (2018-01-02) + [Full Changelog](https://github.com/feathersjs/feathers/compare/v3.0.2...v3.0.3) **Merged pull requests:** @@ -701,6 +559,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Update semistandard to the latest version 🚀 [\#768](https://github.com/feathersjs/feathers/pull/768) ([greenkeeper[bot]](https://github.com/apps/greenkeeper)) ## [v3.0.2](https://github.com/feathersjs/feathers/tree/v3.0.2) (2017-12-05) + [Full Changelog](https://github.com/feathersjs/feathers/compare/v3.0.1...v3.0.2) **Merged pull requests:** @@ -708,6 +567,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Updated to handle array emit for service results. [\#743](https://github.com/feathersjs/feathers/pull/743) ([superlazycoder](https://github.com/superlazycoder)) ## [v3.0.1](https://github.com/feathersjs/feathers/tree/v3.0.1) (2017-11-16) + [Full Changelog](https://github.com/feathersjs/feathers/compare/v3.0.0...v3.0.1) **Merged pull requests:** @@ -719,6 +579,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Rename expressify to express [\#719](https://github.com/feathersjs/feathers/pull/719) ([bertho-zero](https://github.com/bertho-zero)) ## [v3.0.0](https://github.com/feathersjs/feathers/tree/v3.0.0) (2017-11-01) + [Full Changelog](https://github.com/feathersjs/feathers/compare/v3.0.0-pre.3...v3.0.0) **Merged pull requests:** @@ -727,6 +588,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Feathers v3 core \(Buzzard\) [\#697](https://github.com/feathersjs/feathers/pull/697) ([daffl](https://github.com/daffl)) ## [v3.0.0-pre.3](https://github.com/feathersjs/feathers/tree/v3.0.0-pre.3) (2017-10-25) + [Full Changelog](https://github.com/feathersjs/feathers/compare/v3.0.0-pre.2...v3.0.0-pre.3) **Merged pull requests:** @@ -736,6 +598,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Add more inline documentation [\#703](https://github.com/feathersjs/feathers/pull/703) ([daffl](https://github.com/daffl)) ## [v3.0.0-pre.2](https://github.com/feathersjs/feathers/tree/v3.0.0-pre.2) (2017-10-20) + [Full Changelog](https://github.com/feathersjs/feathers/compare/v2.2.3...v3.0.0-pre.2) **Merged pull requests:** @@ -744,6 +607,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Also pass app object as parameter to configure callbacks [\#698](https://github.com/feathersjs/feathers/pull/698) ([daffl](https://github.com/daffl)) ## [v2.2.3](https://github.com/feathersjs/feathers/tree/v2.2.3) (2017-10-20) + [Full Changelog](https://github.com/feathersjs/feathers/compare/v2.2.2...v2.2.3) **Merged pull requests:** @@ -755,6 +619,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Update mocha to the latest version 🚀 [\#685](https://github.com/feathersjs/feathers/pull/685) ([greenkeeper[bot]](https://github.com/apps/greenkeeper)) ## [v2.2.2](https://github.com/feathersjs/feathers/tree/v2.2.2) (2017-09-30) + [Full Changelog](https://github.com/feathersjs/feathers/compare/v2.2.1...v2.2.2) **Merged pull requests:** @@ -762,6 +627,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Update to latest secure dependencies [\#684](https://github.com/feathersjs/feathers/pull/684) ([daffl](https://github.com/daffl)) ## [v2.2.1](https://github.com/feathersjs/feathers/tree/v2.2.1) (2017-09-25) + [Full Changelog](https://github.com/feathersjs/feathers/compare/v2.2.0...v2.2.1) **Merged pull requests:** @@ -770,6 +636,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Update readme.md [\#668](https://github.com/feathersjs/feathers/pull/668) ([damosse31](https://github.com/damosse31)) ## [v2.2.0](https://github.com/feathersjs/feathers/tree/v2.2.0) (2017-09-01) + [Full Changelog](https://github.com/feathersjs/feathers/compare/v3.0.0-pre.1...v2.2.0) **Merged pull requests:** @@ -779,6 +646,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Examples url is tinny \(broken\) [\#634](https://github.com/feathersjs/feathers/pull/634) ([rayfoss](https://github.com/rayfoss)) ## [v3.0.0-pre.1](https://github.com/feathersjs/feathers/tree/v3.0.0-pre.1) (2017-07-19) + [Full Changelog](https://github.com/feathersjs/feathers/compare/v2.1.7...v3.0.0-pre.1) **Merged pull requests:** @@ -786,9 +654,11 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Add a missing configure\(\) method in typescript definition [\#624](https://github.com/feathersjs/feathers/pull/624) ([jansel369](https://github.com/jansel369)) ## [v2.1.7](https://github.com/feathersjs/feathers/tree/v2.1.7) (2017-07-16) + [Full Changelog](https://github.com/feathersjs/feathers/compare/v2.1.6...v2.1.7) ## [v2.1.6](https://github.com/feathersjs/feathers/tree/v2.1.6) (2017-07-16) + [Full Changelog](https://github.com/feathersjs/feathers/compare/v2.1.4...v2.1.6) **Merged pull requests:** @@ -802,6 +672,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Update index.d.ts [\#603](https://github.com/feathersjs/feathers/pull/603) ([j2L4e](https://github.com/j2L4e)) ## [v2.1.4](https://github.com/feathersjs/feathers/tree/v2.1.4) (2017-06-26) + [Full Changelog](https://github.com/feathersjs/feathers/compare/v2.1.3...v2.1.4) **Merged pull requests:** @@ -813,6 +684,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Revert update to security links [\#590](https://github.com/feathersjs/feathers/pull/590) ([alaycock](https://github.com/alaycock)) ## [v2.1.3](https://github.com/feathersjs/feathers/tree/v2.1.3) (2017-05-29) + [Full Changelog](https://github.com/feathersjs/feathers/compare/v2.1.2...v2.1.3) **Merged pull requests:** @@ -821,6 +693,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Update feathers-socketio to the latest version 🚀 [\#576](https://github.com/feathersjs/feathers/pull/576) ([greenkeeper[bot]](https://github.com/apps/greenkeeper)) ## [v2.1.2](https://github.com/feathersjs/feathers/tree/v2.1.2) (2017-05-09) + [Full Changelog](https://github.com/feathersjs/feathers/compare/v2.1.1...v2.1.2) **Merged pull requests:** @@ -831,6 +704,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Fix pagination type definition. [\#527](https://github.com/feathersjs/feathers/pull/527) ([asdacap](https://github.com/asdacap)) ## [v2.1.1](https://github.com/feathersjs/feathers/tree/v2.1.1) (2017-03-03) + [Full Changelog](https://github.com/feathersjs/feathers/compare/v2.1.0...v2.1.1) **Merged pull requests:** @@ -838,6 +712,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - No Pagination in Typescript \#520 [\#522](https://github.com/feathersjs/feathers/pull/522) ([superbarne](https://github.com/superbarne)) ## [v2.1.0](https://github.com/feathersjs/feathers/tree/v2.1.0) (2017-03-01) + [Full Changelog](https://github.com/feathersjs/feathers/compare/v2.0.3...v2.1.0) **Merged pull requests:** @@ -847,6 +722,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - debug@2.4.0 breaks build 🚨 [\#476](https://github.com/feathersjs/feathers/pull/476) ([greenkeeperio-bot](https://github.com/greenkeeperio-bot)) ## [v2.0.3](https://github.com/feathersjs/feathers/tree/v2.0.3) (2016-12-10) + [Full Changelog](https://github.com/feathersjs/feathers/compare/v2.0.2...v2.0.3) **Merged pull requests:** @@ -862,6 +738,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - adding code coverage config, badges and LTS section [\#427](https://github.com/feathersjs/feathers/pull/427) ([ekryski](https://github.com/ekryski)) ## [v2.0.2](https://github.com/feathersjs/feathers/tree/v2.0.2) (2016-09-15) + [Full Changelog](https://github.com/feathersjs/feathers/compare/v2.0.1...v2.0.2) **Merged pull requests:** @@ -875,6 +752,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Set rejectUnauthorized explicitly [\#321](https://github.com/feathersjs/feathers/pull/321) ([daffl](https://github.com/daffl)) ## [v2.0.1](https://github.com/feathersjs/feathers/tree/v2.0.1) (2016-04-28) + [Full Changelog](https://github.com/feathersjs/feathers/compare/v2.0.0...v2.0.1) **Merged pull requests:** @@ -887,6 +765,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - New site [\#252](https://github.com/feathersjs/feathers/pull/252) ([ekryski](https://github.com/ekryski)) ## [v2.0.0](https://github.com/feathersjs/feathers/tree/v2.0.0) (2016-02-22) + [Full Changelog](https://github.com/feathersjs/feathers/compare/v2.0.0-pre.4...v2.0.0) **Merged pull requests:** @@ -897,6 +776,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Appending `nsp check` to test script. [\#205](https://github.com/feathersjs/feathers/pull/205) ([marshallswain](https://github.com/marshallswain)) ## [v2.0.0-pre.4](https://github.com/feathersjs/feathers/tree/v2.0.0-pre.4) (2016-01-16) + [Full Changelog](https://github.com/feathersjs/feathers/compare/v2.0.0-pre.3...v2.0.0-pre.4) **Merged pull requests:** @@ -904,6 +784,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Fixing .npmignore entries [\#203](https://github.com/feathersjs/feathers/pull/203) ([corymsmith](https://github.com/corymsmith)) ## [v2.0.0-pre.3](https://github.com/feathersjs/feathers/tree/v2.0.0-pre.3) (2016-01-16) + [Full Changelog](https://github.com/feathersjs/feathers/compare/v2.0.0-pre.2...v2.0.0-pre.3) **Merged pull requests:** @@ -913,6 +794,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Update feathers-commons to version 0.5.0 🚀 [\#198](https://github.com/feathersjs/feathers/pull/198) ([greenkeeperio-bot](https://github.com/greenkeeperio-bot)) ## [v2.0.0-pre.2](https://github.com/feathersjs/feathers/tree/v2.0.0-pre.2) (2016-01-10) + [Full Changelog](https://github.com/feathersjs/feathers/compare/v2.0.0-pre.1...v2.0.0-pre.2) **Merged pull requests:** @@ -921,6 +803,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Remove Lodash [\#192](https://github.com/feathersjs/feathers/pull/192) ([daffl](https://github.com/daffl)) ## [v2.0.0-pre.1](https://github.com/feathersjs/feathers/tree/v2.0.0-pre.1) (2016-01-05) + [Full Changelog](https://github.com/feathersjs/feathers/compare/v1.3.0...v2.0.0-pre.1) **Merged pull requests:** @@ -928,9 +811,11 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Migration to ES6 and API providers in separate modules [\#188](https://github.com/feathersjs/feathers/pull/188) ([daffl](https://github.com/daffl)) ## [v1.3.0](https://github.com/feathersjs/feathers/tree/v1.3.0) (2015-12-16) + [Full Changelog](https://github.com/feathersjs/feathers/compare/v1.2.1...v1.3.0) ## [v1.2.1](https://github.com/feathersjs/feathers/tree/v1.2.1) (2015-12-12) + [Full Changelog](https://github.com/feathersjs/feathers/compare/v1.2.0...v1.2.1) **Merged pull requests:** @@ -940,6 +825,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Adding tests to make sure that dispatcher context is set properly. [\#172](https://github.com/feathersjs/feathers/pull/172) ([daffl](https://github.com/daffl)) ## [v1.2.0](https://github.com/feathersjs/feathers/tree/v1.2.0) (2015-11-07) + [Full Changelog](https://github.com/feathersjs/feathers/compare/v1.1.1...v1.2.0) **Merged pull requests:** @@ -949,6 +835,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Debug should be for socket.io instead of primus [\#147](https://github.com/feathersjs/feathers/pull/147) ([marshallswain](https://github.com/marshallswain)) ## [v1.1.1](https://github.com/feathersjs/feathers/tree/v1.1.1) (2015-09-22) + [Full Changelog](https://github.com/feathersjs/feathers/compare/v1.1.0...v1.1.1) **Merged pull requests:** @@ -956,6 +843,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Fix 404 not being properly thrown by REST provider [\#146](https://github.com/feathersjs/feathers/pull/146) ([loris](https://github.com/loris)) ## [v1.1.0](https://github.com/feathersjs/feathers/tree/v1.1.0) (2015-07-22) + [Full Changelog](https://github.com/feathersjs/feathers/compare/1.1.0-pre.0...v1.1.0) **Merged pull requests:** @@ -965,6 +853,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Allow to register remote services [\#136](https://github.com/feathersjs/feathers/pull/136) ([daffl](https://github.com/daffl)) ## [1.1.0-pre.0](https://github.com/feathersjs/feathers/tree/1.1.0-pre.0) (2015-04-10) + [Full Changelog](https://github.com/feathersjs/feathers/compare/1.0.2...1.1.0-pre.0) **Merged pull requests:** @@ -983,6 +872,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Support for registering services dynamically [\#107](https://github.com/feathersjs/feathers/pull/107) ([marshallswain](https://github.com/marshallswain)) ## [1.0.2](https://github.com/feathersjs/feathers/tree/1.0.2) (2015-02-04) + [Full Changelog](https://github.com/feathersjs/feathers/compare/1.0.1...1.0.2) **Merged pull requests:** @@ -991,6 +881,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Make sure that mixins are specific to each new app [\#104](https://github.com/feathersjs/feathers/pull/104) ([daffl](https://github.com/daffl)) ## [1.0.1](https://github.com/feathersjs/feathers/tree/1.0.1) (2014-12-31) + [Full Changelog](https://github.com/feathersjs/feathers/compare/1.0.0...1.0.1) **Merged pull requests:** @@ -998,6 +889,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Rename Uberproto .create to avoid conflicts with service method [\#100](https://github.com/feathersjs/feathers/pull/100) ([daffl](https://github.com/daffl)) ## [1.0.0](https://github.com/feathersjs/feathers/tree/1.0.0) (2014-10-03) + [Full Changelog](https://github.com/feathersjs/feathers/compare/1.0.0-pre.5...1.0.0) **Merged pull requests:** @@ -1017,6 +909,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Upgrade to Express 4 [\#55](https://github.com/feathersjs/feathers/pull/55) ([daffl](https://github.com/daffl)) ## [1.0.0-pre.5](https://github.com/feathersjs/feathers/tree/1.0.0-pre.5) (2014-06-13) + [Full Changelog](https://github.com/feathersjs/feathers/compare/1.0.0-pre.1...1.0.0-pre.5) **Merged pull requests:** @@ -1024,9 +917,11 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - requiring feathers-errors in core [\#81](https://github.com/feathersjs/feathers/pull/81) ([ekryski](https://github.com/ekryski)) ## [1.0.0-pre.1](https://github.com/feathersjs/feathers/tree/1.0.0-pre.1) (2014-06-04) + [Full Changelog](https://github.com/feathersjs/feathers/compare/0.4.0...1.0.0-pre.1) ## [0.4.0](https://github.com/feathersjs/feathers/tree/0.4.0) (2014-04-08) + [Full Changelog](https://github.com/feathersjs/feathers/compare/0.3.2...0.4.0) **Merged pull requests:** @@ -1038,6 +933,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Added patch support [\#47](https://github.com/feathersjs/feathers/pull/47) ([mlaug](https://github.com/mlaug)) ## [0.3.2](https://github.com/feathersjs/feathers/tree/0.3.2) (2014-03-28) + [Full Changelog](https://github.com/feathersjs/feathers/compare/0.3.1...0.3.2) **Merged pull requests:** @@ -1046,13 +942,15 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Upgrading dependencies and switching to Lodash [\#42](https://github.com/feathersjs/feathers/pull/42) ([daffl](https://github.com/daffl)) ## [0.3.1](https://github.com/feathersjs/feathers/tree/0.3.1) (2014-02-19) + [Full Changelog](https://github.com/feathersjs/feathers/compare/0.3.0...0.3.1) **Merged pull requests:** -- Updating REST provider [\#35](https://github.com/feathersjs/feathers/pull/35) ([daffl](https://github.com/daffl)) +- Updating REST provider [\#35](https://github.com/feathersjs/feathers/pull/35) ([daffl](https://github.com/daffl)) ## [0.3.0](https://github.com/feathersjs/feathers/tree/0.3.0) (2014-01-06) + [Full Changelog](https://github.com/feathersjs/feathers/compare/0.2.0...0.3.0) **Merged pull requests:** @@ -1062,6 +960,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Remove middleware: connect.bodyParser\(\) [\#27](https://github.com/feathersjs/feathers/pull/27) ([sbruchmann](https://github.com/sbruchmann)) ## [0.2.0](https://github.com/feathersjs/feathers/tree/0.2.0) (2013-09-27) + [Full Changelog](https://github.com/feathersjs/feathers/compare/0.1.0...0.2.0) **Merged pull requests:** @@ -1070,12 +969,15 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Allows setting service params in middleware [\#17](https://github.com/feathersjs/feathers/pull/17) ([daffl](https://github.com/daffl)) ## [0.1.0](https://github.com/feathersjs/feathers/tree/0.1.0) (2013-08-27) + [Full Changelog](https://github.com/feathersjs/feathers/compare/0.0.5...0.1.0) ## [0.0.5](https://github.com/feathersjs/feathers/tree/0.0.5) (2013-08-27) + [Full Changelog](https://github.com/feathersjs/feathers/compare/0.0.4...0.0.5) ## [0.0.4](https://github.com/feathersjs/feathers/tree/0.0.4) (2013-08-27) + [Full Changelog](https://github.com/feathersjs/feathers/compare/0.0.3...0.0.4) **Merged pull requests:** @@ -1083,6 +985,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Major refactoring and simplification [\#16](https://github.com/feathersjs/feathers/pull/16) ([daffl](https://github.com/daffl)) ## [0.0.3](https://github.com/feathersjs/feathers/tree/0.0.3) (2013-08-26) + [Full Changelog](https://github.com/feathersjs/feathers/compare/0.0.2...0.0.3) **Merged pull requests:** @@ -1090,10 +993,9 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Improved Mixin organization, updated tests and examples. [\#15](https://github.com/feathersjs/feathers/pull/15) ([daffl](https://github.com/daffl)) ## [0.0.2](https://github.com/feathersjs/feathers/tree/0.0.2) (2013-07-13) + **Merged pull requests:** - Added a couple examples. Started to add a mongo adapter. [\#2](https://github.com/feathersjs/feathers/pull/2) ([ekryski](https://github.com/ekryski)) - - -\* *This Change Log was automatically generated by [github_changelog_generator](https://github.com/skywinder/Github-Changelog-Generator)* +\* _This Change Log was automatically generated by [github_changelog_generator](https://github.com/skywinder/Github-Changelog-Generator)_ diff --git a/packages/feathers/LICENSE b/packages/feathers/LICENSE index 3f395cc665..59604f46f3 100644 --- a/packages/feathers/LICENSE +++ b/packages/feathers/LICENSE @@ -1,6 +1,6 @@ The MIT License (MIT) -Copyright (c) 2021 Feathers +Copyright (c) 2022 Feathers Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated documentation files (the "Software"), to deal diff --git a/packages/feathers/README.md b/packages/feathers/README.md new file mode 100644 index 0000000000..01be1db801 --- /dev/null +++ b/packages/feathers/README.md @@ -0,0 +1,37 @@ +Feathers logo + +## A framework for real-time applications and REST APIs with JavaScript and TypeScript + +[![CI](https://github.com/feathersjs/feathers/workflows/CI/badge.svg)](https://github.com/feathersjs/feathers/actions?query=workflow%3ACI) +[![Maintainability](https://api.codeclimate.com/v1/badges/cb5ec42a2d0cc1a47a02/maintainability)](https://codeclimate.com/github/feathersjs/feathers/maintainability) +[![Test Coverage](https://api.codeclimate.com/v1/badges/cb5ec42a2d0cc1a47a02/test_coverage)](https://codeclimate.com/github/feathersjs/feathers/test_coverage) +[![Download Status](https://img.shields.io/npm/dm/@feathersjs/feathers.svg?style=flat-square)](https://www.npmjs.com/package/@feathersjs/feathers) +[![Discord](https://badgen.net/badge/icon/discord?icon=discord&label)](https://discord.gg/qa8kez8QBx) + +Feathers is a lightweight web-framework for creating real-time applications and REST APIs using JavaScript or TypeScript. + +Feathers can interact with any backend technology, supports over a dozen databases and works with any frontend technology like React, VueJS, Angular, React Native, Android or iOS. + +## Getting started + +You can build your first real-time and REST API in just 4 commands: + +```bash +$ npm install -g @feathersjs/cli +$ mkdir my-new-app +$ cd my-new-app/ +$ feathers generate app +$ npm start +``` + +To learn more about Feathers visit the website at [feathersjs.com](http://feathersjs.com) or jump right into [the Feathers guides](http://docs.feathersjs.com/guides). + +## Documentation + +The [Feathers docs](http://docs.feathersjs.com) are loaded with awesome stuff and tell you every thing you need to know about using and configuring Feathers. + +## License + +Copyright (c) 2022 [Feathers contributors](https://github.com/feathersjs/feathers/graphs/contributors) + +Licensed under the [MIT license](LICENSE). diff --git a/packages/feathers/package.json b/packages/feathers/package.json index e2060eab87..a106d087dd 100644 --- a/packages/feathers/package.json +++ b/packages/feathers/package.json @@ -1,11 +1,12 @@ { "name": "@feathersjs/feathers", "description": "A framework for real-time applications and REST API with JavaScript and TypeScript", - "version": "5.0.0-pre.16", + "version": "5.0.0-pre.31", "homepage": "http://feathersjs.com", "repository": { "type": "git", - "url": "git://github.com/feathersjs/feathers.git" + "url": "git://github.com/feathersjs/feathers.git", + "directory": "packages/feathers" }, "keywords": [ "feathers", @@ -41,14 +42,14 @@ "*.js" ], "scripts": { - "write-version": "node -e \"console.log('export default \\'' + require('./package.json').version + '\\';')\" > src/version.ts", - "reset-version": "node -e \"console.log('export default \\'development\\';')\" > src/version.ts", + "write-version": "node -e \"console.log('export default \\'' + require('./package.json').version + '\\'')\" > src/version.ts", + "reset-version": "node -e \"console.log('export default \\'development\\'')\" > src/version.ts", "prepublish": "npm run compile", "version": "npm run write-version", "publish": "npm run reset-version", - "compile": "shx rm -rf lib/ && tsc", - "test": "npm run compile && npm run mocha", - "mocha": "mocha --config ../../.mocharc.json --recursive test/" + "pack": "npm pack --pack-destination ../cli/test/build", + "compile": "shx rm -rf lib/ && tsc && npm run pack", + "test": "mocha --config ../../.mocharc.json --recursive test/" }, "engines": { "node": ">= 12" @@ -57,17 +58,17 @@ "access": "public" }, "dependencies": { - "@feathersjs/commons": "^5.0.0-pre.16", - "@feathersjs/hooks": "^0.6.5", + "@feathersjs/commons": "^5.0.0-pre.31", + "@feathersjs/hooks": "^0.7.5", "events": "^3.3.0" }, "devDependencies": { - "@types/mocha": "^9.0.0", - "@types/node": "^17.0.5", - "mocha": "^9.1.3", - "shx": "^0.3.3", - "ts-node": "^10.4.0", - "typescript": "^4.5.4" + "@types/mocha": "^10.0.0", + "@types/node": "^18.8.2", + "mocha": "^10.0.0", + "shx": "^0.3.4", + "ts-node": "^10.9.1", + "typescript": "^4.8.4" }, - "gitHead": "f0cd227a82d159b528193bd33747c97684a48773" + "gitHead": "4500dbeb8cea566678cf88b3313a88efd93a2ed9" } diff --git a/packages/feathers/src/application.ts b/packages/feathers/src/application.ts index 9676be9398..c0997d1f56 100644 --- a/packages/feathers/src/application.ts +++ b/packages/feathers/src/application.ts @@ -1,10 +1,10 @@ -import version from './version'; -import { - EventEmitter, stripSlashes, createDebug, HOOKS -} from './dependencies'; -import { eventHook, eventMixin } from './events'; -import { hookMixin } from './hooks/index'; -import { wrapService, getServiceOptions, protectedMethods } from './service'; +import version from './version' +import { EventEmitter } from 'events' +import { stripSlashes, createDebug } from '@feathersjs/commons' +import { HOOKS, hooks, middleware } from '@feathersjs/hooks' +import { eventHook, eventMixin } from './events' +import { hookMixin } from './hooks' +import { wrapService, getServiceOptions, protectedMethods } from './service' import { FeathersApplication, ServiceMixin, @@ -12,152 +12,213 @@ import { ServiceOptions, ServiceInterface, Application, - HookOptions, FeathersService, - HookMap, - RegularHookMap -} from './declarations'; -import { enableRegularHooks } from './hooks/regular'; - -const debug = createDebug('@feathersjs/feathers'); - -export class Feathers extends EventEmitter implements FeathersApplication { - services: Services = ({} as Services); - settings: Settings = ({} as Settings); - mixins: ServiceMixin>[] = [ hookMixin, eventMixin ]; - version: string = version; - _isSetup = false; - appHooks: HookMap, any> = { - [HOOKS]: [ (eventHook as any) ] - }; - - private regularHooks: (this: any, allHooks: any) => any; - - constructor () { - super(); - this.regularHooks = enableRegularHooks(this); + ApplicationHookOptions +} from './declarations' +import { enableHooks } from './hooks' + +const debug = createDebug('@feathersjs/feathers') + +export class Feathers + extends EventEmitter + implements FeathersApplication +{ + services: Services = {} as Services + settings: Settings = {} as Settings + mixins: ServiceMixin>[] = [hookMixin, eventMixin] + version: string = version + _isSetup = false + + protected registerHooks: (this: any, allHooks: any) => any + + constructor() { + super() + this.registerHooks = enableHooks(this) + this.registerHooks({ + around: [eventHook] + }) } - get (name: L): Settings[L] { - return this.settings[name]; + get(name: L): Settings[L] { + return this.settings[name] } - set (name: L, value: Settings[L]) { - this.settings[name] = value; - return this; + set(name: L, value: Settings[L]) { + this.settings[name] = value + return this } - configure (callback: (this: this, app: this) => void) { - callback.call(this, this); + configure(callback: (this: this, app: this) => void) { + callback.call(this, this) - return this; + return this } - defaultService (location: string): ServiceInterface { - throw new Error(`Can not find service '${location}'`); + defaultService(location: string): ServiceInterface { + throw new Error(`Can not find service '${location}'`) } - service ( + service( location: L ): FeathersService { - const path = (stripSlashes(location) || '/') as L; - const current = this.services[path]; + const path = (stripSlashes(location) || '/') as L + const current = this.services[path] if (typeof current === 'undefined') { - this.use(path, this.defaultService(path) as any); - return this.service(path); + this.use(path, this.defaultService(path) as any) + return this.service(path) } - return current as any; + return current as any + } + + protected _setup() { + this._isSetup = true + + return Object.keys(this.services) + .reduce( + (current, path) => + current.then(() => { + const service: any = this.service(path as any) + + if (typeof service.setup === 'function') { + debug(`Setting up service for \`${path}\``) + + return service.setup(this, path) + } + }), + Promise.resolve() + ) + .then(() => this) + } + + get setup() { + return this._setup + } + + set setup(value) { + this._setup = (value as any)[HOOKS] + ? value + : hooks( + value, + middleware().params('server').props({ + app: this + }) + ) + } + + protected _teardown() { + this._isSetup = false + + return Object.keys(this.services) + .reduce( + (current, path) => + current.then(() => { + const service: any = this.service(path as any) + + if (typeof service.teardown === 'function') { + debug(`Tearing down service for \`${path}\``) + + return service.teardown(this, path) + } + }), + Promise.resolve() + ) + .then(() => this) } - use ( + get teardown() { + return this._teardown + } + + set teardown(value) { + this._teardown = (value as any)[HOOKS] + ? value + : hooks( + value, + middleware().params('server').props({ + app: this + }) + ) + } + + use( path: L, service: keyof any extends keyof Services ? ServiceInterface | Application : Services[L], options?: ServiceOptions ): this { if (typeof path !== 'string') { - throw new Error(`'${path}' is not a valid service path.`); + throw new Error(`'${path}' is not a valid service path.`) } - const location = (stripSlashes(path) || '/') as L; - const subApp = service as Application; - const isSubApp = typeof subApp.service === 'function' && subApp.services; + const location = (stripSlashes(path) || '/') as L + const subApp = service as Application + const isSubApp = typeof subApp.service === 'function' && subApp.services if (isSubApp) { - Object.keys(subApp.services).forEach(subPath => + Object.keys(subApp.services).forEach((subPath) => this.use(`${location}/${subPath}` as any, subApp.service(subPath) as any) - ); + ) - return this; + return this } - const protoService = wrapService(location, service, options); - const serviceOptions = getServiceOptions(protoService); + const protoService = wrapService(location, service, options) + const serviceOptions = getServiceOptions(protoService) for (const name of protectedMethods) { if (serviceOptions.methods.includes(name)) { - throw new Error(`'${name}' on service '${location}' is not allowed as a custom method name`); + throw new Error(`'${name}' on service '${location}' is not allowed as a custom method name`) } } - debug(`Registering new service at \`${location}\``); + debug(`Registering new service at \`${location}\``) // Add all the mixins - this.mixins.forEach(fn => fn.call(this, protoService, location, serviceOptions)); + this.mixins.forEach((fn) => fn.call(this, protoService, location, serviceOptions)) + + this.services[location] = protoService // If we ran setup already, set this service up explicitly, this will not `await` if (this._isSetup && typeof protoService.setup === 'function') { - debug(`Setting up service for \`${location}\``); - protoService.setup(this, location); + debug(`Setting up service for \`${location}\``) + protoService.setup(this, location) } - this.services[location] = protoService; - - return this; + return this } - hooks (hookMap: HookOptions) { - const regularMap = hookMap as RegularHookMap; + async unuse( + location: L + ): Promise> { + const path = (stripSlashes(location) || '/') as L + const service = this.services[path] as Service - if (regularMap.before || regularMap.after || regularMap.error) { - return this.regularHooks(regularMap); + if (service && typeof service.teardown === 'function') { + await service.teardown(this as any, path) } - if (Array.isArray(hookMap)) { - this.appHooks[HOOKS].push(...hookMap as any); - } else { - const methodHookMap = hookMap as HookMap, any>; - - Object.keys(methodHookMap).forEach(key => { - const methodHooks = this.appHooks[key] || []; - - this.appHooks[key] = methodHooks.concat(methodHookMap[key]); - }); - } + delete this.services[path] - return this; + return service as any } - setup () { - let promise = Promise.resolve(); + hooks(hookMap: ApplicationHookOptions) { + const untypedMap = hookMap as any - // Setup each service (pass the app so that they can look up other services etc.) - for (const path of Object.keys(this.services)) { - promise = promise.then(() => { - const service: any = this.service(path as any); - - if (typeof service.setup === 'function') { - debug(`Setting up service for \`${path}\``); - - return service.setup(this, path); - } - }); + if (untypedMap.before || untypedMap.after || untypedMap.error || untypedMap.around) { + // regular hooks for all service methods + this.registerHooks(untypedMap) + } else if (untypedMap.setup || untypedMap.teardown) { + // .setup and .teardown application hooks + hooks(this, untypedMap) + } else { + // Other registration formats are just `around` hooks + this.registerHooks({ + around: untypedMap + }) } - return promise.then(() => { - this._isSetup = true; - return this; - }); + return this } } diff --git a/packages/feathers/src/declarations.ts b/packages/feathers/src/declarations.ts index 73c5228169..8a542a9640 100644 --- a/packages/feathers/src/declarations.ts +++ b/packages/feathers/src/declarations.ts @@ -1,131 +1,160 @@ -import { - EventEmitter, NextFunction, HookContext as BaseHookContext -} from './dependencies'; +import { EventEmitter } from 'events' +import { NextFunction, HookContext as BaseHookContext } from '@feathersjs/hooks' -type SelfOrArray = S | S[]; +type SelfOrArray = S | S[] type OptionalPick = Pick> -export type { NextFunction }; +export type { NextFunction } +/** + * The object returned from `.find` call by standard database adapters + */ export interface Paginated { - total: number; - limit: number; - skip: number; - data: T[]; + total: number + limit: number + skip: number + data: T[] } +/** + * Options that can be passed when registering a service via `app.use(name, service, options)` + */ export interface ServiceOptions { - events?: string[]; - methods?: string[]; - serviceEvents?: string[]; - routeParams?: { [key: string]: any }; + events?: string[] | readonly string[] + methods?: string[] | readonly string[] + serviceEvents?: string[] | readonly string[] + routeParams?: { [key: string]: any } } -export interface ServiceMethods> { - find (params?: Params): Promise; +export interface ClientService< + Result = any, + Data = Partial, + PatchData = Data, + FindResult = Paginated, + P = Params +> { + find(params?: P): Promise - get (id: Id, params?: Params): Promise; + get(id: Id, params?: P): Promise - create (data: D, params?: Params): Promise; + create(data: Data[], params?: P): Promise + create(data: Data, params?: P): Promise - update (id: NullableId, data: D, params?: Params): Promise; + update(id: Id, data: Data, params?: P): Promise + update(id: NullableId, data: Data, params?: P): Promise + update(id: null, data: Data, params?: P): Promise - patch (id: NullableId, data: D, params?: Params): Promise; + patch(id: NullableId, data: PatchData, params?: P): Promise + patch(id: Id, data: PatchData, params?: P): Promise + patch(id: null, data: PatchData, params?: P): Promise - remove (id: NullableId, params?: Params): Promise; + remove(id: NullableId, params?: P): Promise + remove(id: Id, params?: P): Promise + remove(id: null, params?: P): Promise +} + +export interface ServiceMethods, P = Params> { + find(params?: P): Promise + + get(id: Id, params?: P): Promise + + create(data: D, params?: P): Promise + + update(id: NullableId, data: D, params?: P): Promise + + patch(id: NullableId, data: D, params?: P): Promise + + remove(id: NullableId, params?: P): Promise - setup (app: Application, path: string): Promise; + setup?(app: Application, path: string): Promise + + teardown?(app: Application, path: string): Promise } -export interface ServiceOverloads> { - create? (data: D[], params?: Params): Promise; +export interface ServiceOverloads, P = Params> { + create?(data: D[], params?: P): Promise - update? (id: Id, data: D, params?: Params): Promise; + update?(id: Id, data: D, params?: P): Promise - update? (id: null, data: D, params?: Params): Promise; + update?(id: null, data: D, params?: P): Promise - patch? (id: Id, data: D, params?: Params): Promise; + patch?(id: Id, data: D, params?: P): Promise - patch? (id: null, data: D, params?: Params): Promise; + patch?(id: null, data: D, params?: P): Promise - remove? (id: Id, params?: Params): Promise; + remove?(id: Id, params?: P): Promise - remove? (id: null, params?: Params): Promise; + remove?(id: null, params?: P): Promise } -export type Service> = - ServiceMethods & - ServiceOverloads; +export type Service, P = Params> = ServiceMethods & ServiceOverloads -export type ServiceInterface> = - Partial>; +export type ServiceInterface, P = Params> = Partial> export interface ServiceAddons extends EventEmitter { - id?: string; - hooks (options: HookOptions): this; + id?: string + hooks(options: HookOptions): this } -export interface ServiceHookOverloads { - find ( - params: Params, - context: HookContext - ): Promise; +export interface ServiceHookOverloads { + find(params: P, context: HookContext): Promise - get ( - id: Id, - params: Params, - context: HookContext - ): Promise; + get(id: Id, params: P, context: HookContext): Promise - create ( + create( data: ServiceGenericData | ServiceGenericData[], - params: Params, + params: P, context: HookContext - ): Promise; + ): Promise - update ( - id: NullableId, - data: ServiceGenericData, - params: Params, - context: HookContext - ): Promise; + update(id: NullableId, data: ServiceGenericData, params: P, context: HookContext): Promise - patch ( - id: NullableId, - data: ServiceGenericData, - params: Params, - context: HookContext - ): Promise; + patch(id: NullableId, data: ServiceGenericData, params: P, context: HookContext): Promise - remove ( - id: NullableId, - params: Params, - context: HookContext - ): Promise; + remove(id: NullableId, params: P, context: HookContext): Promise } -export type FeathersService = - S & ServiceAddons & OptionalPick, keyof S>; +export type FeathersService = S & + ServiceAddons & + OptionalPick, keyof S> -export type CustomMethods = { - [K in keyof T]: (data: T[K][0], params?: Params) => Promise; +export type CustomMethods = { + [K in keyof T]: (data: T[K][0], params?: Params) => Promise } -export type ServiceMixin = (service: FeathersService, path: string, options: ServiceOptions) => void; +/** + * An interface usually use by transport clients that represents a e.g. HTTP or websocket + * connection that can be configured on the application. + */ +export type TransportConnection = { + (app: Application): void + Service: any + service: ( + name: L + ) => keyof any extends keyof Services ? ServiceInterface : Services[L] +} + +/** + * The interface for a custom service method. Can e.g. be used to type client side services. + */ +export type CustomMethod = (data: T, params?: P) => Promise + +export type ServiceMixin = (service: FeathersService, path: string, options: ServiceOptions) => void -export type ServiceGenericType = S extends ServiceInterface ? T : any; -export type ServiceGenericData = S extends ServiceInterface ? D : any; +export type ServiceGenericType = S extends ServiceInterface ? T : any +export type ServiceGenericData = S extends ServiceInterface ? D : any +export type ServiceGenericParams = S extends ServiceInterface ? P : any export interface FeathersApplication { /** * The Feathers application version */ - version: string; + version: string /** * A list of callbacks that run when a new service is registered */ - mixins: ServiceMixin>[]; + mixins: ServiceMixin>[] /** * The index of all services keyed by their path. @@ -133,30 +162,25 @@ export interface FeathersApplication { * __Important:__ Services should always be retrieved via `app.service('name')` * not via `app.services`. */ - services: Services; + services: Services /** * The application settings that can be used via * `app.get` and `app.set` */ - settings: Settings; + settings: Settings /** * A private-ish indicator if `app.setup()` has been called already */ - _isSetup: boolean; - - /** - * Contains all registered application level hooks. - */ - appHooks: HookMap, any>; + _isSetup: boolean /** * Retrieve an application setting by name * * @param name The setting name */ - get (name: L): Settings[L]; + get(name: L): Settings[L] /** * Set an application setting @@ -164,14 +188,14 @@ export interface FeathersApplication { * @param name The setting name * @param value The setting value */ - set (name: L, value: Settings[L]): this; + set(name: L, value: Settings[L]): this /** * Runs a callback configure function with the current application instance. * * @param callback The callback `(app: Application) => {}` to run */ - configure (callback: (this: this, app: this) => void): this; + configure(callback: (this: this, app: this) => void): this /** * Returns a fallback service instance that will be registered @@ -180,7 +204,7 @@ export interface FeathersApplication { * * @param location The path of the service */ - defaultService (location: string): ServiceInterface; + defaultService(location: string): ServiceInterface /** * Register a new service or a sub-app. When passed another @@ -192,11 +216,20 @@ export interface FeathersApplication { * Feathers application to use a sub-app under the `path` prefix. * @param options The options for this service */ - use ( + use( path: L, service: keyof any extends keyof Services ? ServiceInterface | Application : Services[L], options?: ServiceOptions - ): this; + ): this + + /** + * Unregister an existing service. + * + * @param path The name of the service to unregister + */ + unuse( + path: L + ): Promise> /** * Get the Feathers service instance for a path. This will @@ -205,47 +238,65 @@ export interface FeathersApplication { * * @param path The name of the service. */ - service ( + service( path: L - ): FeathersService; + ): FeathersService - setup (server?: any): Promise; + /** + * Set up the application and call all services `.setup` method if available. + * + * @param server A server instance (optional) + */ + setup(server?: any): Promise + + /** + * Tear down the application and call all services `.teardown` method if available. + * + * @param server A server instance (optional) + */ + teardown(server?: any): Promise /** * Register application level hooks. * * @param map The application hook settings. */ - hooks (map: HookOptions): this; + hooks(map: ApplicationHookOptions): this } // This needs to be an interface instead of a type // so that the declaration can be extended by other modules -export interface Application extends FeathersApplication, EventEmitter { +export interface Application + extends FeathersApplication, + EventEmitter {} -} - -export type Id = number | string; -export type NullableId = Id | null; +export type Id = number | string +export type NullableId = Id | null export interface Query { - [key: string]: any; + [key: string]: any } -export interface Params { - query?: Query; - provider?: string; - route?: { [key: string]: any }; - headers?: { [key: string]: any }; - [key: string]: any; // (JL) not sure if we want this +export interface Params { + query?: Q + provider?: string + route?: { [key: string]: any } + headers?: { [key: string]: any } } export interface Http { /** - * A writeable, optional property that allows to override the standard HTTP status - * code that should be returned. + * A writeable, optional property with status code override. + */ + status?: number + /** + * A writeable, optional property with headers. */ - statusCode?: number; + headers?: { [key: string]: string | string[] } + /** + * A writeable, optional property with `Location` header's value. + */ + location?: string } export interface HookContext extends BaseHookContext> { @@ -253,52 +304,52 @@ export interface HookContext extends BaseHookContext; + data?: ServiceGenericData /** * A writeable property with the error object that was thrown in a failed method call. * It is only available in error hooks. */ - error?: any; + error?: any /** * A writeable property and the id for a get, remove, update and patch service * method call. For remove, update and patch context.id can also be null when * modifying multiple entries. In all other cases it will be undefined. */ - id?: Id; + id?: Id /** * A writeable property that contains the service method parameters (including * params.query). */ - params: Params; + params: ServiceGenericParams /** * A writeable property containing the result of the successful service method call. * It is only available in after hooks. @@ -308,56 +359,76 @@ export interface HookContext extends BaseHookContext; + result?: ServiceGenericType /** * A writeable, optional property and contains a 'safe' version of the data that * should be sent to any client. If context.dispatch has not been set context.result * will be sent to the client instead. */ - dispatch?: ServiceGenericType; + dispatch?: ServiceGenericType /** * A writeable, optional property that allows to override the standard HTTP status * code that should be returned. * - * @deprecated Use `http.statusCode` instead. + * @deprecated Use `http.status` instead. */ - statusCode?: number; + statusCode?: number /** - * A writeable, optional property that contains options specific to HTTP transports. + * A writeable, optional property with options specific to HTTP transports. */ - http?: Http; + http?: Http /** * The event emitted by this method. Can be set to `null` to skip event emitting. */ - event: string|null; + event: string | null } // Regular hook typings -export type RegularHookFunction = - (this: S, context: HookContext) => (Promise | void> | HookContext | void); - -export type Hook = RegularHookFunction; +export type HookFunction = ( + this: S, + context: HookContext +) => Promise | void> | HookContext | void -type RegularHookMethodMap = - { [L in keyof S]?: SelfOrArray>; } & - { all?: SelfOrArray> }; +export type Hook = HookFunction -type RegularHookTypeMap = - SelfOrArray> | RegularHookMethodMap; +type HookMethodMap = { + [L in keyof S]?: SelfOrArray> +} & { all?: SelfOrArray> } -export type RegularHookMap = { - before?: RegularHookTypeMap, - after?: RegularHookTypeMap, - error?: RegularHookTypeMap -} +type HookTypeMap = SelfOrArray> | HookMethodMap // New @feathersjs/hook typings -export type HookFunction = - (context: HookContext, next: NextFunction) => Promise; +export type AroundHookFunction = ( + context: HookContext, + next: NextFunction +) => Promise + +export type AroundHookMap = { + [L in keyof S]?: AroundHookFunction[] +} & { all?: AroundHookFunction[] } export type HookMap = { - [L in keyof S]?: HookFunction[]; -}; + around?: AroundHookMap + before?: HookTypeMap + after?: HookTypeMap + error?: HookTypeMap +} + +export type HookOptions = AroundHookMap | AroundHookFunction[] | HookMap + +export interface ApplicationHookContext extends BaseHookContext { + app: A + server: any +} + +export type ApplicationHookFunction = ( + context: ApplicationHookContext, + next: NextFunction +) => Promise + +export type ApplicationHookMap = { + setup?: ApplicationHookFunction[] + teardown?: ApplicationHookFunction[] +} -export type HookOptions = - HookMap | HookFunction[] | RegularHookMap; +export type ApplicationHookOptions = HookOptions | ApplicationHookMap diff --git a/packages/feathers/src/dependencies.ts b/packages/feathers/src/dependencies.ts deleted file mode 100644 index 7363399681..0000000000 --- a/packages/feathers/src/dependencies.ts +++ /dev/null @@ -1,5 +0,0 @@ -import { EventEmitter } from 'events'; -export * from '@feathersjs/commons'; -export * from '@feathersjs/hooks'; - -export { EventEmitter }; diff --git a/packages/feathers/src/events.ts b/packages/feathers/src/events.ts index 20eb162681..50956f829d 100644 --- a/packages/feathers/src/events.ts +++ b/packages/feathers/src/events.ts @@ -1,31 +1,31 @@ -import { NextFunction, EventEmitter } from './dependencies'; -import { HookContext, FeathersService } from './declarations'; -import { getServiceOptions, defaultEventMap } from './service'; +import { EventEmitter } from 'events' +import { NextFunction } from '@feathersjs/hooks' +import { HookContext, FeathersService } from './declarations' +import { getServiceOptions, defaultEventMap } from './service' -export function eventHook (context: HookContext, next: NextFunction) { - const { events } = getServiceOptions((context as any).self); - const defaultEvent = (defaultEventMap as any)[context.method] || null; +export function eventHook(context: HookContext, next: NextFunction) { + const { events } = getServiceOptions((context as any).self) + const defaultEvent = (defaultEventMap as any)[context.method] || null - context.event = defaultEvent; + context.event = defaultEvent return next().then(() => { // Send the event only if the service does not do so already (indicated in the `events` option) // This is used for custom events and for client services receiving event from the server if (typeof context.event === 'string' && !events.includes(context.event)) { - const results = Array.isArray(context.result) ? context.result : [ context.result ]; + const results = Array.isArray(context.result) ? context.result : [context.result] - results.forEach(element => (context as any).self.emit(context.event, element, context)); + results.forEach((element) => (context as any).self.emit(context.event, element, context)) } - }); + }) } -export function eventMixin (service: FeathersService) { - const isEmitter = typeof service.on === 'function' && - typeof service.emit === 'function'; +export function eventMixin(service: FeathersService) { + const isEmitter = typeof service.on === 'function' && typeof service.emit === 'function' if (!isEmitter) { - Object.assign(service, EventEmitter.prototype); + Object.assign(service, EventEmitter.prototype) } - return service; + return service } diff --git a/packages/feathers/src/hooks.ts b/packages/feathers/src/hooks.ts new file mode 100644 index 0000000000..f69bb20059 --- /dev/null +++ b/packages/feathers/src/hooks.ts @@ -0,0 +1,215 @@ +import { + getManager, + HookContextData, + HookManager, + HookMap as BaseHookMap, + hooks, + Middleware, + collect +} from '@feathersjs/hooks' +import { + Service, + ServiceOptions, + HookContext, + FeathersService, + HookMap, + AroundHookFunction, + HookFunction +} from './declarations' +import { defaultServiceArguments, getHookMethods } from './service' + +type HookType = 'before' | 'after' | 'error' | 'around' + +type ConvertedMap = { [type in HookType]: ReturnType } + +type HookStore = { + around: { [method: string]: AroundHookFunction[] } + before: { [method: string]: HookFunction[] } + after: { [method: string]: HookFunction[] } + error: { [method: string]: HookFunction[] } + collected: { [method: string]: AroundHookFunction[] } +} + +type HookEnabled = { __hooks: HookStore } + +const types: HookType[] = ['before', 'after', 'error', 'around'] + +const isType = (value: any): value is HookType => types.includes(value) + +// Converts different hook registration formats into the +// same internal format +export function convertHookData(input: any) { + const result: { [method: string]: HookFunction[] | AroundHookFunction[] } = {} + + if (Array.isArray(input)) { + result.all = input + } else if (typeof input !== 'object') { + result.all = [input] + } else { + for (const key of Object.keys(input)) { + const value = input[key] + result[key] = Array.isArray(value) ? value : [value] + } + } + + return result +} + +export function collectHooks(target: HookEnabled, method: string) { + const { collected, around } = target.__hooks + + return [ + ...(around.all || []), + ...(around[method] || []), + ...(collected.all || []), + ...(collected[method] || []) + ] as AroundHookFunction[] +} + +// Add `.hooks` functionality to an object +export function enableHooks(object: any) { + const store: HookStore = { + around: {}, + before: {}, + after: {}, + error: {}, + collected: {} + } + + Object.defineProperty(object, '__hooks', { + configurable: true, + value: store, + writable: true + }) + + return function registerHooks(this: HookEnabled, input: HookMap) { + const store = this.__hooks + const map = Object.keys(input).reduce((map, type) => { + if (!isType(type)) { + throw new Error(`'${type}' is not a valid hook type`) + } + + map[type] = convertHookData(input[type]) + + return map + }, {} as ConvertedMap) + const types = Object.keys(map) as HookType[] + + types.forEach((type) => + Object.keys(map[type]).forEach((method) => { + const mapHooks = map[type][method] + const storeHooks: any[] = (store[type][method] ||= []) + + storeHooks.push(...mapHooks) + + if (store.before[method] || store.after[method] || store.error[method]) { + const collected = collect({ + before: store.before[method] || [], + after: store.after[method] || [], + error: store.error[method] || [] + }) + + store.collected[method] = [collected] + } + }) + ) + + return this + } +} + +export function createContext(service: Service, method: string, data: HookContextData = {}) { + const createContext = (service as any)[method].createContext + + if (typeof createContext !== 'function') { + throw new Error(`Can not create context for method ${method}`) + } + + return createContext(data) as HookContext +} + +export class FeathersHookManager extends HookManager { + constructor(public app: A, public method: string) { + super() + this._middleware = [] + } + + collectMiddleware(self: any, args: any[]): Middleware[] { + const appHooks = collectHooks(this.app as any as HookEnabled, this.method) + const middleware = super.collectMiddleware(self, args) + const methodHooks = collectHooks(self, this.method) + + return [...appHooks, ...middleware, ...methodHooks] + } + + initializeContext(self: any, args: any[], context: HookContext) { + const ctx = super.initializeContext(self, args, context) + + ctx.params = ctx.params || {} + + return ctx + } + + middleware(mw: Middleware[]) { + this._middleware.push(...mw) + return this + } +} + +export function hookMixin(this: A, service: FeathersService, path: string, options: ServiceOptions) { + if (typeof service.hooks === 'function') { + return service + } + + const hookMethods = getHookMethods(service, options) + + const serviceMethodHooks = hookMethods.reduce((res, method) => { + const params = (defaultServiceArguments as any)[method] || ['data', 'params'] + + res[method] = new FeathersHookManager(this, method).params(...params).props({ + app: this, + path, + method, + service, + event: null, + type: null, + get statusCode() { + return this.http?.status + }, + set statusCode(value: number) { + this.http = this.http || {} + this.http.status = value + } + }) + + return res + }, {} as BaseHookMap) + + const registerHooks = enableHooks(service) + + hooks(service, serviceMethodHooks) + + service.hooks = function (this: any, hookOptions: any) { + if (hookOptions.before || hookOptions.after || hookOptions.error || hookOptions.around) { + return registerHooks.call(this, hookOptions) + } + + if (Array.isArray(hookOptions)) { + return hooks(this, hookOptions) + } + + Object.keys(hookOptions).forEach((method) => { + const manager = getManager(this[method]) + + if (!(manager instanceof FeathersHookManager)) { + throw new Error(`Method ${method} is not a Feathers hooks enabled service method`) + } + + manager.middleware(hookOptions[method]) + }) + + return this + } + + return service +} diff --git a/packages/feathers/src/hooks/index.ts b/packages/feathers/src/hooks/index.ts deleted file mode 100644 index 5324178580..0000000000 --- a/packages/feathers/src/hooks/index.ts +++ /dev/null @@ -1,122 +0,0 @@ -import { - getManager, HookContextData, HookManager, HookMap, HOOKS, hooks, Middleware -} from '../dependencies'; -import { - Service, ServiceOptions, HookContext, FeathersService, Application -} from '../declarations'; -import { defaultServiceArguments, getHookMethods } from '../service'; -import { - collectRegularHooks, - enableRegularHooks -} from './regular'; - -export { - fromBeforeHook, - fromBeforeHooks, - fromAfterHook, - fromAfterHooks, - fromErrorHook, - fromErrorHooks -} from './regular'; - -export function createContext (service: Service, method: string, data: HookContextData = {}) { - const createContext = (service as any)[method].createContext; - - if (typeof createContext !== 'function') { - throw new Error(`Can not create context for method ${method}`); - } - - return createContext(data) as HookContext; -} - -export class FeathersHookManager extends HookManager { - constructor (public app: A, public method: string) { - super(); - this._middleware = []; - } - - collectMiddleware (self: any, args: any[]): Middleware[] { - const app = this.app as any as Application; - const appHooks = app.appHooks[HOOKS].concat(app.appHooks[this.method] || []); - const regularAppHooks = collectRegularHooks(this.app, this.method); - const middleware = super.collectMiddleware(self, args); - const regularHooks = collectRegularHooks(self, this.method); - - return [...appHooks, ...regularAppHooks, ...middleware, ...regularHooks]; - } - - initializeContext (self: any, args: any[], context: HookContext) { - const ctx = super.initializeContext(self, args, context); - - ctx.params = ctx.params || {}; - - return ctx; - } - - middleware (mw: Middleware[]) { - this._middleware.push(...mw); - return this; - } -} - -export function hookMixin ( - this: A, service: FeathersService, path: string, options: ServiceOptions -) { - if (typeof service.hooks === 'function') { - return service; - } - - const app = this; - const hookMethods = getHookMethods(service, options); - - const serviceMethodHooks = hookMethods.reduce((res, method) => { - const params = (defaultServiceArguments as any)[method] || [ 'data', 'params' ]; - - res[method] = new FeathersHookManager(app, method) - .params(...params) - .props({ - app, - path, - method, - service, - event: null, - type: null, - get statusCode () { - return this.http?.statusCode; - }, - set statusCode (value: number) { - (this.http ||= {}).statusCode = value; - } - }); - - return res; - }, {} as HookMap); - - const handleRegularHooks = enableRegularHooks(service, hookMethods); - - hooks(service, serviceMethodHooks); - - service.hooks = function (this: any, hookOptions: any) { - if (hookOptions.before || hookOptions.after || hookOptions.error) { - return handleRegularHooks.call(this, hookOptions); - } - - if (Array.isArray(hookOptions)) { - return hooks(this, hookOptions); - } - - Object.keys(hookOptions).forEach(method => { - const manager = getManager(this[method]); - - if (!(manager instanceof FeathersHookManager)) { - throw new Error(`Method ${method} is not a Feathers hooks enabled service method`); - } - - manager.middleware(hookOptions[method]); - }); - - return this; - } - - return service; -} diff --git a/packages/feathers/src/hooks/regular.ts b/packages/feathers/src/hooks/regular.ts deleted file mode 100644 index ff01715184..0000000000 --- a/packages/feathers/src/hooks/regular.ts +++ /dev/null @@ -1,207 +0,0 @@ -import { HookFunction, RegularHookFunction, RegularHookMap } from '../declarations'; -import { defaultServiceMethods } from '../service'; - -const runHook = (hook: RegularHookFunction, context: any, type?: string) => { - if (type) context.type = type; - return Promise.resolve(hook.call(context.self, context)) - .then((res: any) => { - if (type) context.type = null; - if (res && res !== context) { - Object.assign(context, res); - } - }); -}; - -export function fromBeforeHook (hook: RegularHookFunction): HookFunction { - return (context, next) => { - return runHook(hook, context, 'before').then(next); - }; -} - -export function fromAfterHook (hook: RegularHookFunction): HookFunction { - return (context, next) => { - return next().then(() => runHook(hook, context, 'after')); - } -} - -export function fromErrorHook (hook: RegularHookFunction): HookFunction { - return (context, next) => { - return next().catch((error: any) => { - if (context.error !== error || context.result !== undefined) { - (context as any).original = { ...context }; - context.error = error; - delete context.result; - } - - return runHook(hook, context, 'error').then(() => { - if (context.result === undefined && context.error !== undefined) { - throw context.error; - } - }); - }); - } -} - -const RunHooks = (hooks: RegularHookFunction[]) => (context: any) => { - return hooks.reduce((promise, hook) => { - return promise.then(() => runHook(hook, context)) - }, Promise.resolve(undefined)); -}; - -export function fromBeforeHooks (hooks: RegularHookFunction[]) { - return fromBeforeHook(RunHooks(hooks)); -} - -export function fromAfterHooks (hooks: RegularHookFunction[]) { - return fromAfterHook(RunHooks(hooks)); -} - -export function fromErrorHooks (hooks: RegularHookFunction[]) { - return fromErrorHook(RunHooks(hooks)); -} - -export function collectRegularHooks (target: any, method: string) { - return target.__hooks.hooks[method] || []; -} - -// Converts different hook registration formats into the -// same internal format -export function convertHookData (input: any) { - const result: { [ method: string ]: RegularHookFunction[] } = {}; - - if (Array.isArray(input)) { - result.all = input; - } else if (typeof input !== 'object') { - result.all = [ input ]; - } else { - for (const key of Object.keys(input)) { - const value = input[key]; - result[key] = Array.isArray(value) ? value : [ value ]; - } - } - - return result; -} - -type RegularType = 'before' | 'after' | 'error'; - -type RegularMap = { [ type in RegularType ]: ReturnType< typeof convertHookData > }; - -type RegularAdapter = HookFunction & { hooks: RegularHookFunction[] }; - -type RegularStore = { - before: { [ method: string ]: RegularAdapter }, - after: { [ method: string ]: RegularAdapter }, - error: { [ method: string ]: RegularAdapter }, - hooks: { [ method: string ]: HookFunction[] } -}; - -const types: RegularType[] = ['before', 'after', 'error']; - -const isType = (value: any): value is RegularType => types.includes(value); - -const wrappers = { - before: fromBeforeHooks, - after: fromAfterHooks, - error: fromErrorHooks -}; - -const createStore = (methods: string[]) => { - const store: RegularStore = { - before: {}, - after: {}, - error: {}, - hooks: {} - }; - - for (const method of methods) { - store.hooks[method] = []; - } - - return store; -}; - -const setStore = (object: any, store: RegularStore) => { - Object.defineProperty(object, '__hooks', { - configurable: true, - value: store, - writable: true - }); -}; - -const getStore = (object: any): RegularStore => object.__hooks; - -const createMap = (input: RegularHookMap, methods: string[]) => { - const map = {} as RegularMap; - - Object.keys(input).forEach((type) => { - if (!isType(type)) { - throw new Error(`'${type}' is not a valid hook type`); - } - - const data = convertHookData(input[type]); - - Object.keys(data).forEach((method) => { - if (method !== 'all' && !methods.includes(method)) { - throw new Error(`'${method}' is not a valid hook method`); - } - }); - - map[type] = data; - }); - - return map; -}; - -const createAdapter = (type: RegularType) => { - const hooks: RegularHookFunction[] = []; - const hook = wrappers[type](hooks); - const adapter = Object.assign(hook, { hooks }); - - return adapter; -}; - -const updateStore = (store: RegularStore, map: RegularMap) => { - Object.keys(store.hooks).forEach((method) => { - let adapted = false; - - Object.keys(map).forEach((key) => { - const type = key as RegularType; - const allHooks = map[type].all || []; - const methodHooks = map[type][method] || []; - - if (allHooks.length || methodHooks.length) { - const adapter = store[type][method] ||= (adapted = true, createAdapter(type)); - - adapter.hooks.push(...allHooks, ...methodHooks); - } - }); - - if (adapted) { - store.hooks[method] = [ - store.error[method], - store.before[method], - store.after[method] - ].filter(hook => hook); - } - }); -}; - -// Add `.hooks` functionality to an object -export function enableRegularHooks ( - object: any, - methods: string[] = defaultServiceMethods -) { - const store = createStore(methods); - - setStore(object, store); - - return function regularHooks (this: any, input: RegularHookMap) { - const store = getStore(this); - const map = createMap(input, methods); - - updateStore(store, map); - - return this; - } -} diff --git a/packages/feathers/src/index.ts b/packages/feathers/src/index.ts index 0280adc2e9..c37bfef951 100644 --- a/packages/feathers/src/index.ts +++ b/packages/feathers/src/index.ts @@ -1,19 +1,20 @@ -import { setDebug } from './dependencies'; -import version from './version'; -import { Feathers } from './application'; -import { Application } from './declarations'; +import { setDebug } from '@feathersjs/commons' -export function feathers () { - return new Feathers() as Application; +import version from './version' +import { Feathers } from './application' +import { Application } from './declarations' + +export function feathers() { + return new Feathers() as Application } -feathers.setDebug = setDebug; +feathers.setDebug = setDebug -export { version, Feathers }; -export * from './hooks/index'; -export * from './declarations'; -export * from './service'; +export { version, Feathers } +export * from './hooks' +export * from './declarations' +export * from './service' if (typeof module !== 'undefined') { - module.exports = Object.assign(feathers, module.exports); + module.exports = Object.assign(feathers, module.exports) } diff --git a/packages/feathers/src/service.ts b/packages/feathers/src/service.ts index bf0bb7a25a..269cf2bf3b 100644 --- a/packages/feathers/src/service.ts +++ b/packages/feathers/src/service.ts @@ -1,18 +1,18 @@ -import { createSymbol, EventEmitter } from './dependencies'; -import { ServiceOptions } from './declarations'; +import { EventEmitter } from 'events' +import { createSymbol } from '@feathersjs/commons' +import { ServiceOptions } from './declarations' -export const SERVICE = createSymbol('@feathersjs/service'); +export const SERVICE = createSymbol('@feathersjs/service') export const defaultServiceArguments = { - find: [ 'params' ], - get: [ 'id', 'params' ], - create: [ 'data', 'params' ], - update: [ 'id', 'data', 'params' ], - patch: [ 'id', 'data', 'params' ], - remove: [ 'id', 'params' ] + find: ['params'], + get: ['id', 'params'], + create: ['data', 'params'], + update: ['id', 'data', 'params'], + patch: ['id', 'data', 'params'], + remove: ['id', 'params'] } - -export const defaultServiceMethods = Object.keys(defaultServiceArguments); +export const defaultServiceMethods = ['find', 'get', 'create', 'update', 'patch', 'remove'] export const defaultEventMap = { create: 'created', @@ -23,69 +23,53 @@ export const defaultEventMap = { export const protectedMethods = Object.keys(Object.prototype) .concat(Object.keys(EventEmitter.prototype)) - .concat([ - 'all', - 'before', - 'after', - 'error', - 'hooks', - 'setup', - 'publish' - ]); + .concat(['all', 'around', 'before', 'after', 'error', 'hooks', 'setup', 'teardown', 'publish']) -export function getHookMethods (service: any, options: ServiceOptions) { - const { methods } = options; +export function getHookMethods(service: any, options: ServiceOptions) { + const { methods } = options - return defaultServiceMethods.filter(m => - typeof service[m] === 'function' && !methods.includes(m) - ).concat(methods); + return (defaultServiceMethods as any as string[]) + .filter((m) => typeof service[m] === 'function' && !methods.includes(m)) + .concat(methods) } -export function getServiceOptions ( - service: any, options: ServiceOptions = {} -): ServiceOptions { - const existingOptions = service[SERVICE]; +export function getServiceOptions(service: any, options: ServiceOptions = {}): ServiceOptions { + const existingOptions = service[SERVICE] if (existingOptions) { - return existingOptions; + return existingOptions } const { - methods = defaultServiceMethods.filter(method => - typeof service[method] === 'function' - ), + methods = defaultServiceMethods.filter((method) => typeof service[method] === 'function'), events = service.events || [] - } = options; - const { - serviceEvents = Object.values(defaultEventMap).concat(events) - } = options; + } = options + const { serviceEvents = Object.values(defaultEventMap).concat(events) } = options return { ...options, events, methods, serviceEvents - }; + } } -export function wrapService ( - location: string, service: any, options: ServiceOptions -) { +export function wrapService(location: string, service: any, options: ServiceOptions) { // Do nothing if this is already an initialized if (service[SERVICE]) { - return service; + return service } - const protoService = Object.create(service); - const serviceOptions = getServiceOptions(service, options); + const protoService = Object.create(service) + const serviceOptions = getServiceOptions(service, options) if (Object.keys(serviceOptions.methods).length === 0 && typeof service.setup !== 'function') { - throw new Error(`Invalid service object passed for path \`${location}\``); + throw new Error(`Invalid service object passed for path \`${location}\``) } Object.defineProperty(protoService, SERVICE, { value: serviceOptions - }); + }) - return protoService; + return protoService } diff --git a/packages/feathers/src/version.ts b/packages/feathers/src/version.ts index a54d824540..e47b8144bf 100644 --- a/packages/feathers/src/version.ts +++ b/packages/feathers/src/version.ts @@ -1 +1 @@ -export default 'development'; +export default 'development' diff --git a/packages/feathers/test/application.test.ts b/packages/feathers/test/application.test.ts index ee65d134f2..ec2e642564 100644 --- a/packages/feathers/test/application.test.ts +++ b/packages/feathers/test/application.test.ts @@ -1,437 +1,535 @@ -import assert from 'assert'; +/* eslint-disable @typescript-eslint/ban-ts-comment, @typescript-eslint/no-empty-function */ +import assert from 'assert' import { feathers, Feathers, getServiceOptions, Id, version } from '../src' describe('Feathers application', () => { it('initializes', () => { - const app = feathers(); + const app = feathers() - assert.ok(app instanceof Feathers); - }); + assert.ok(app instanceof Feathers) + }) it('sets the version on main and app instance', () => { - const app = feathers(); + const app = feathers() - assert.ok(version > '5.0.0'); - assert.ok(app.version > '5.0.0'); - }); + assert.ok(version > '5.0.0') + assert.ok(app.version > '5.0.0') + }) - it('is an event emitter', done => { - const app = feathers(); - const original = { hello: 'world' }; + it('is an event emitter', (done) => { + const app = feathers() + const original = { hello: 'world' } app.on('test', (data: any) => { - assert.deepStrictEqual(original, data); - done(); - }); + assert.deepStrictEqual(original, data) + done() + }) - app.emit('test', original); - }); + app.emit('test', original) + }) it('uses .defaultService if available', async () => { - const app = feathers(); + const app = feathers() assert.throws(() => app.service('/todos/'), { - message: 'Can not find service \'todos\'' - }); + message: "Can not find service 'todos'" + }) app.defaultService = function (location: string) { - assert.strictEqual(location, 'todos'); + assert.strictEqual(location, 'todos') return { - async get (id: string) { + async get(id: string) { return { - id, description: `You have to do ${id}!` - }; + id, + description: `You have to do ${id}!` + } } - }; - }; + } + } - const data = await app.service('/todos/').get('dishes'); + const data = await app.service('/todos/').get('dishes') assert.deepStrictEqual(data, { id: 'dishes', description: 'You have to do dishes!' - }); - }); + }) + }) - it('additionally passes `app` as .configure parameter (#558)', done => { + it('additionally passes `app` as .configure parameter (#558)', (done) => { feathers().configure(function (app) { - assert.strictEqual(this, app); - done(); - }); - }); + assert.strictEqual(this, app) + done() + }) + }) describe('Services', () => { it('calling .use with invalid path throws', () => { - const app = feathers(); + const app = feathers() assert.throws(() => app.use(null, {}), { - message: '\'null\' is not a valid service path.' - }); + message: "'null' is not a valid service path." + }) // @ts-ignore assert.throws(() => app.use({}, {}), { - message: '\'[object Object]\' is not a valid service path.' - }); - }); + message: "'[object Object]' is not a valid service path." + }) + }) it('calling .use with a non service object throws', () => { - const app = feathers(); + const app = feathers() // @ts-ignore assert.throws(() => app.use('/bla', function () {}), { message: 'Invalid service object passed for path `bla`' }) - }); + }) - it('registers and wraps a new service', async () => { + it('registers and wraps a new service and can unregister (#2035)', async () => { const dummyService = { - async setup (this: any, _app: any, path: string) { - this.path = path; + async setup(this: any, _app: any, path: string) { + this.path = path }, - async create (data: any) { - return data; + async teardown(this: any, _app: any, path: string) { + this.path = path + }, + + async create(data: any) { + return data } - }; + } - const app = feathers().use('/dummy', dummyService); - const wrappedService = app.service('dummy'); + const app = feathers<{ dummy: typeof dummyService }>().use('dummy', dummyService) + const wrappedService = app.service('dummy') - assert.strictEqual(Object.getPrototypeOf(wrappedService), dummyService, 'Object points to original service prototype'); + assert.strictEqual( + Object.getPrototypeOf(wrappedService), + dummyService, + 'Object points to original service prototype' + ) const data = await wrappedService.create({ message: 'Test message' - }); + }) + + assert.strictEqual(data.message, 'Test message') - assert.strictEqual(data.message, 'Test message'); - }); + await app.unuse('dummy') + + assert.strictEqual(Object.keys(app.services).length, 0) + assert.throws(() => app.service('dummy'), { + message: "Can not find service 'dummy'" + }) + }) it('can not register custom methods on a protected methods', async () => { const dummyService = { - async create (data: any) { - return data; + async create(data: any) { + return data }, - async removeListener (data: any) { - return data; + async removeListener(data: any) { + return data }, - async setup () {} - }; - - assert.throws(() => feathers().use('/dummy', dummyService, { - methods: ['create', 'removeListener'] - }), { - message: '\'removeListener\' on service \'dummy\' is not allowed as a custom method name' - }); - assert.throws(() => feathers().use('/dummy', dummyService, { - methods: ['create', 'setup'] - }), { - message: '\'setup\' on service \'dummy\' is not allowed as a custom method name' - }); - }); + async setup() {}, + + async teardown() {} + } + + assert.throws( + () => + feathers().use('/dummy', dummyService, { + methods: ['create', 'removeListener'] + }), + { + message: "'removeListener' on service 'dummy' is not allowed as a custom method name" + } + ) + assert.throws( + () => + feathers().use('/dummy', dummyService, { + methods: ['create', 'setup'] + }), + { + message: "'setup' on service 'dummy' is not allowed as a custom method name" + } + ) + assert.throws( + () => + feathers().use('/dummy', dummyService, { + methods: ['create', 'teardown'] + }), + { + message: "'teardown' on service 'dummy' is not allowed as a custom method name" + } + ) + }) it('can use a root level service', async () => { const app = feathers().use('/', { - async get (id: string) { - return { id }; + async get(id: string) { + return { id } } - }); + }) - const result = await app.service('/').get('test'); + const result = await app.service('/').get('test') - assert.deepStrictEqual(result, { id: 'test' }); - }); + assert.deepStrictEqual(result, { id: 'test' }) + }) - it('services can be re-used (#566)', done => { - const app1 = feathers(); - const app2 = feathers(); + it('services can be re-used (#566)', (done) => { + const app1 = feathers() + const app2 = feathers() app2.use('/dummy', { - async create (data: any) { - return data; + async create(data: any) { + return data } - }); + }) - const dummy = app2.service('dummy'); + const dummy = app2.service('dummy') dummy.hooks({ before: { - create: [hook => { - hook.data.fromHook = true; - }] + create: [ + (hook) => { + hook.data.fromHook = true + } + ] } - }); + }) dummy.on('created', (data: any) => { assert.deepStrictEqual(data, { message: 'Hi', fromHook: true - }); - done(); - }); + }) + done() + }) - app1.use('/testing', app2.service('dummy')); + app1.use('/testing', app2.service('dummy')) - app1.service('testing').create({ message: 'Hi' }); - }); + app1.service('testing').create({ message: 'Hi' }) + }) it('async hooks run before regular hooks', async () => { - const app = feathers(); + const app = feathers() app.use('/dummy', { - async create (data: any) { - return data; + async create(data: any) { + return data } - }); + }) - const dummy = app.service('dummy'); + const dummy = app.service('dummy') dummy.hooks({ before: { - create (ctx) { - ctx.data.order.push('before'); + create(ctx) { + ctx.data.order.push('before') } } - }); + }) - dummy.hooks([async (ctx: any, next: any) => { - ctx.data.order = [ 'async' ]; - await next(); - }]); + dummy.hooks([ + async (ctx: any, next: any) => { + ctx.data.order = ['async'] + await next() + } + ]) const result = await dummy.create({ message: 'hi' - }); + }) assert.deepStrictEqual(result, { message: 'hi', order: ['async', 'before'] - }); - }); + }) + }) it('services conserve Symbols', () => { - const TEST = Symbol('test'); + const TEST = Symbol('test') const dummyService = { [TEST]: true, - async setup (this: any, _app: any, path: string) { - this.path = path; + async setup(this: any, _app: any, path: string) { + this.path = path }, - async create (data: any) { - return data; + async create(data: any) { + return data } - }; + } - const app = feathers().use('/dummy', dummyService); - const wrappedService = app.service('dummy'); + const app = feathers().use('/dummy', dummyService) + const wrappedService = app.service('dummy') - assert.ok((wrappedService as any)[TEST]); - }); + assert.ok((wrappedService as any)[TEST]) + }) it('methods conserve Symbols', () => { - const TEST = Symbol('test'); + const TEST = Symbol('test') const dummyService = { - async setup (this: any, _app: any, path: string) { - this.path = path; + async setup(this: any, _app: any, path: string) { + this.path = path }, - async create (data: any) { - return data; + async create(data: any) { + return data } - }; + } - (dummyService.create as any)[TEST] = true; + ;(dummyService.create as any)[TEST] = true - const app = feathers().use('/dummy', dummyService); - const wrappedService = app.service('dummy'); + const app = feathers().use('/dummy', dummyService) + const wrappedService = app.service('dummy') - assert.ok((wrappedService.create as any)[TEST]); - }); - }); + assert.ok((wrappedService.create as any)[TEST]) + }) + }) describe('Express app options compatibility', function () { describe('.set()', () => { it('should set a value', () => { - const app = feathers(); - app.set('foo', 'bar'); - assert.strictEqual(app.get('foo'), 'bar'); - }); + const app = feathers() + app.set('foo', 'bar') + assert.strictEqual(app.get('foo'), 'bar') + }) it('should return the app', () => { - const app = feathers(); - assert.strictEqual(app.set('foo', 'bar'), app); - }); + const app = feathers() + assert.strictEqual(app.set('foo', 'bar'), app) + }) it('should return the app when undefined', () => { - const app = feathers(); - assert.strictEqual(app.set('foo', undefined), app); - }); - }); + const app = feathers() + assert.strictEqual(app.set('foo', undefined), app) + }) + }) describe('.get()', () => { it('should return undefined when unset', () => { - const app = feathers(); - assert.strictEqual(app.get('foo'), undefined); - }); + const app = feathers() + assert.strictEqual(app.get('foo'), undefined) + }) it('should otherwise return the value', () => { - const app = feathers(); - app.set('foo', 'bar'); - assert.strictEqual(app.get('foo'), 'bar'); - }); - }); - }); - - describe('.setup', () => { - it('app.setup calls .setup on all services', async () => { - const app = feathers(); - let setupCount = 0; + const app = feathers() + app.set('foo', 'bar') + assert.strictEqual(app.get('foo'), 'bar') + }) + }) + }) + + describe('.setup and .teardown', () => { + it('app.setup and app.teardown calls .setup and .teardown on all services', async () => { + const app = feathers() + let setupCount = 0 + let teardownCount = 0 app.use('/dummy', { - async setup (appRef: any, path: any) { - setupCount++; - assert.strictEqual(appRef, app); - assert.strictEqual(path, 'dummy'); + async setup(appRef: any, path: any) { + setupCount++ + assert.strictEqual(appRef, app) + assert.strictEqual(path, 'dummy') + }, + + async teardown(appRef: any, path: any) { + teardownCount++ + assert.strictEqual(appRef, app) + assert.strictEqual(path, 'dummy') } - }); + }) app.use('/simple', { - get (id: string) { - return Promise.resolve({ id }); + get(id: string) { + return Promise.resolve({ id }) } - }); + }) app.use('/dummy2', { - async setup (appRef: any, path: any) { - setupCount++; - assert.strictEqual(appRef, app); - assert.strictEqual(path, 'dummy2'); + async setup(appRef: any, path: any) { + setupCount++ + assert.strictEqual(appRef, app) + assert.strictEqual(path, 'dummy2') + }, + + async teardown(appRef: any, path: any) { + teardownCount++ + assert.strictEqual(appRef, app) + assert.strictEqual(path, 'dummy2') } - }); + }) - await app.setup(); + await app.setup() - assert.ok((app as any)._isSetup); - assert.strictEqual(setupCount, 2); - }); + assert.ok((app as any)._isSetup) + assert.strictEqual(setupCount, 2) - it('registering a service after app.setup will be set up', done => { - const app = feathers(); + await app.teardown() - app.setup().then(() => { - app.use('/dummy', { - async setup (appRef: any, path: any) { - assert.ok((app as any)._isSetup); - assert.strictEqual(appRef, app); - assert.strictEqual(path, 'dummy'); - done(); - } - }); - }); - }); - }); + assert.ok(!(app as any)._isSetup) + assert.strictEqual(teardownCount, 2) + }) + + it('registering app.setup but while still pending will be set up', (done) => { + const app = feathers() + + app.setup() + + app.use('/dummy', { + async setup(appRef: any, path: any) { + assert.ok((app as any)._isSetup) + assert.strictEqual(appRef, app) + assert.strictEqual(path, 'dummy') + done() + } + }) + }) + }) + + describe('.teardown', () => { + it('app.teardown calls .teardown on all services', async () => { + const app = feathers() + let teardownCount = 0 + + app.use('/dummy', { + async setup() {}, + async teardown(appRef: any, path: any) { + teardownCount++ + assert.strictEqual(appRef, app) + assert.strictEqual(path, 'dummy') + } + }) + + app.use('/simple', { + get(id: string) { + return Promise.resolve({ id }) + } + }) + + app.use('/dummy2', { + async setup() {}, + async teardown(appRef: any, path: any) { + teardownCount++ + assert.strictEqual(appRef, app) + assert.strictEqual(path, 'dummy2') + } + }) + + await app.setup() + await app.teardown() + + assert.equal((app as any)._isSetup, false) + assert.strictEqual(teardownCount, 2) + }) + }) describe('mixins', () => { class Dummy { - dummy = true; - async get (id: Id) { - return { id }; + dummy = true + async get(id: Id) { + return { id } } } it('are getting called with a service and default options', () => { - const app = feathers(); - let mixinRan = false; + const app = feathers() + let mixinRan = false app.mixins.push(function (service: any, location: any, options: any) { - assert.ok(service.dummy); - assert.strictEqual(location, 'dummy'); - assert.deepStrictEqual(options, getServiceOptions(new Dummy())); - mixinRan = true; - }); + assert.ok(service.dummy) + assert.strictEqual(location, 'dummy') + assert.deepStrictEqual(options, getServiceOptions(new Dummy())) + mixinRan = true + }) - app.use('/dummy', new Dummy()); + app.use('/dummy', new Dummy()) - assert.ok(mixinRan); + assert.ok(mixinRan) - app.setup(); - }); + app.setup() + }) it('are getting called with a service and service options', () => { - const app = feathers(); - const opts = { events: ['bla'] }; + const app = feathers() + const opts = { events: ['bla'] } - let mixinRan = false; + let mixinRan = false app.mixins.push(function (service: any, location: any, options: any) { - assert.ok(service.dummy); - assert.strictEqual(location, 'dummy'); - assert.deepStrictEqual(options, getServiceOptions(new Dummy(), opts)); - mixinRan = true; - }); + assert.ok(service.dummy) + assert.strictEqual(location, 'dummy') + assert.deepStrictEqual(options, getServiceOptions(new Dummy(), opts)) + mixinRan = true + }) - app.use('/dummy', new Dummy(), opts); + app.use('/dummy', new Dummy(), opts) - assert.ok(mixinRan); + assert.ok(mixinRan) - app.setup(); - }); - }); + app.setup() + }) + }) describe('sub apps', () => { - it('re-registers sub-app services with prefix', done => { - const app = feathers(); - const subApp = feathers(); - - subApp.use('/service1', { - async get (id: string) { - return { - id, name: 'service1' - }; - } - }).use('/service2', { - async get (id: string) { - return { - id, name: 'service2' - }; - }, - - async create (data: any) { - return data; - } - }); + it('re-registers sub-app services with prefix', (done) => { + const app = feathers() + const subApp = feathers() + + subApp + .use('/service1', { + async get(id: string) { + return { + id, + name: 'service1' + } + } + }) + .use('/service2', { + async get(id: string) { + return { + id, + name: 'service2' + } + }, + + async create(data: any) { + return data + } + }) - app.use('/api/', subApp); + app.use('/api/', subApp) app.service('/api/service2').once('created', (data: any) => { assert.deepStrictEqual(data, { message: 'This is a test' - }); + }) subApp.service('service2').once('created', (data: any) => { assert.deepStrictEqual(data, { message: 'This is another test' - }); + }) - done(); - }); + done() + }) app.service('api/service2').create({ message: 'This is another test' - }); - }); - - (async () => { - let data = await app.service('/api/service1').get(10); - assert.strictEqual(data.name, 'service1'); + }) + }) + ;(async () => { + let data = await app.service('/api/service1').get(10) + assert.strictEqual(data.name, 'service1') - data = await app.service('/api/service2').get(1); - assert.strictEqual(data.name, 'service2'); + data = await app.service('/api/service2').get(1) + assert.strictEqual(data.name, 'service2') await subApp.service('service2').create({ message: 'This is a test' - }); - })(); - }); - }); -}); + }) + })() + }) + }) +}) diff --git a/packages/feathers/test/declarations.test.ts b/packages/feathers/test/declarations.test.ts index 86e61bb189..acca57b7f2 100644 --- a/packages/feathers/test/declarations.test.ts +++ b/packages/feathers/test/declarations.test.ts @@ -1,111 +1,111 @@ -import assert from 'assert'; -import { hooks } from '@feathersjs/hooks'; -import { - feathers, ServiceInterface, Application, HookContext, NextFunction -} from '../src'; +import assert from 'assert' +import { hooks } from '@feathersjs/hooks' +import { feathers, ServiceInterface, Application, HookContext, NextFunction } from '../src' interface Todo { - id: number; - message: string; - completed: boolean; + id: number + message: string + completed: boolean } interface TodoData { - message: string; - completed?: boolean; + message: string + completed?: boolean } class TodoService implements ServiceInterface { - constructor (public todos: Todo[] = []) {} + constructor(public todos: Todo[] = []) {} - async find () { - return this.todos; + async find() { + return this.todos } - async create (data: TodoData) { - const { completed = false } = data; + async create(data: TodoData) { + const { completed = false } = data const todo: Todo = { id: this.todos.length, completed, message: data.message - }; + } - this.todos.push(todo); + this.todos.push(todo) - return todo; + return todo } - async setup (app: Application) { - assert.ok(app); + async setup(app: Application) { + assert.ok(app) } } interface Configuration { - port: number; + port: number } interface Services { - todos: TodoService; - v2: Application<{}, Configuration> + todos: TodoService + v2: Application, Configuration> } -type MainApp = Application; +type MainApp = Application const myHook = async (context: HookContext, next: NextFunction) => { - assert.ok(context.app.service('todos')); - await next(); + assert.ok(context.app.service('todos')) + await next() } hooks(TodoService.prototype, [ async (_ctx: HookContext, next) => { - await next(); + await next() } -]); +]) hooks(TodoService, { - create: [ myHook ] -}); + create: [myHook] +}) describe('Feathers typings', () => { it('initializes the app with proper types', async () => { - const app: MainApp = feathers(); - const app2 = feathers<{}, Configuration> (); + const app: MainApp = feathers() + const app2 = feathers, Configuration>() - app.set('port', 80); - app.use('todos', new TodoService()); - app.use('v2', app2); + app.set('port', 80) + app.use('todos', new TodoService()) + app.use('v2', app2) - const service = app.service('todos'); + const service = app.service('todos') - service.on('created', data => { - assert.ok(data); - }); + service.on('created', (data) => { + assert.ok(data) + }) service.hooks({ before: { all: [], - create: [async context => { - const { result, data } = context; - - assert.ok(result); - assert.ok(data); - assert.ok(context.app.service('todos')); - }] + create: [ + async (context) => { + const { result, data } = context + + assert.ok(result) + assert.ok(data) + assert.ok(context.app.service('todos')) + } + ] } - }); + }) service.hooks({ create: [ async (context, next) => { - assert.ok(context); - await next(); + assert.ok(context) + await next() }, async (context, next) => { - assert.ok(context); - await next(); + assert.ok(context) + await next() }, myHook ] - }); - }); -}); + }) + }) +}) diff --git a/packages/feathers/test/events.test.ts b/packages/feathers/test/events.test.ts index 1b6e5def09..235b6598f5 100644 --- a/packages/feathers/test/events.test.ts +++ b/packages/feathers/test/events.test.ts @@ -1,323 +1,321 @@ -import assert from 'assert'; -import { EventEmitter } from 'events'; +import assert from 'assert' +import { EventEmitter } from 'events' -import { feathers } from '../src'; +import { feathers } from '../src' describe('Service events', () => { - it('app is an event emitter', done => { - const app = feathers(); + it('app is an event emitter', (done) => { + const app = feathers() - assert.strictEqual(typeof app.on, 'function'); + assert.strictEqual(typeof app.on, 'function') app.on('test', (data: any) => { - assert.deepStrictEqual(data, { message: 'app' }); - done(); - }); - app.emit('test', { message: 'app' }); - }); + assert.deepStrictEqual(data, { message: 'app' }) + done() + }) + app.emit('test', { message: 'app' }) + }) - it('works with service that is already an EventEmitter', done => { - const app = feathers(); - const service: any = new EventEmitter(); + it('works with service that is already an EventEmitter', (done) => { + const app = feathers() + const service: any = new EventEmitter() service.create = async function (data: any) { - return data; - }; + return data + } service.on('created', (data: any) => { assert.deepStrictEqual(data, { message: 'testing' - }); - done(); - }); + }) + done() + }) - app.use('/emitter', service); + app.use('/emitter', service) app.service('emitter').create({ message: 'testing' - }); - }); + }) + }) describe('emits event data on a service', () => { - it('.create and created', done => { + it('.create and created', (done) => { const app = feathers().use('/creator', { - async create (data: any) { - return data; + async create(data: any) { + return data } - }); + }) - const service = app.service('creator'); + const service = app.service('creator') service.on('created', (data: any) => { - assert.deepStrictEqual(data, { message: 'Hello' }); - done(); - }); + assert.deepStrictEqual(data, { message: 'Hello' }) + done() + }) - service.create({ message: 'Hello' }); - }); + service.create({ message: 'Hello' }) + }) - it('allows to skip event emitting', done => { + it('allows to skip event emitting', (done) => { const app = feathers().use('/creator', { - async create (data: any) { - return data; + async create(data: any) { + return data } - }); + }) - const service = app.service('creator'); + const service = app.service('creator') service.hooks({ before: { - create (context: any) { - context.event = null; + create(context: any) { + context.event = null - return context; + return context } } - }); + }) service.on('created', () => { - done(new Error('Should never get here')); - }); + done(new Error('Should never get here')) + }) - service.create({ message: 'Hello' }).then(() => done()); - }); + service.create({ message: 'Hello' }).then(() => done()) + }) - it('.update and updated', done => { + it('.update and updated', (done) => { const app = feathers().use('/creator', { - async update (id: any, data: any) { - return Object.assign({ id }, data); + async update(id: any, data: any) { + return Object.assign({ id }, data) } - }); + }) - const service = app.service('creator'); + const service = app.service('creator') service.on('updated', (data: any) => { - assert.deepStrictEqual(data, { id: 10, message: 'Hello' }); - done(); - }); + assert.deepStrictEqual(data, { id: 10, message: 'Hello' }) + done() + }) - service.update(10, { message: 'Hello' }); - }); + service.update(10, { message: 'Hello' }) + }) - it('.patch and patched', done => { + it('.patch and patched', (done) => { const app = feathers().use('/creator', { - async patch (id: any, data: any) { - return Object.assign({ id }, data); + async patch(id: any, data: any) { + return Object.assign({ id }, data) } - }); + }) - const service = app.service('creator'); + const service = app.service('creator') service.on('patched', (data: any) => { - assert.deepStrictEqual(data, { id: 12, message: 'Hello' }); - done(); - }); + assert.deepStrictEqual(data, { id: 12, message: 'Hello' }) + done() + }) - service.patch(12, { message: 'Hello' }); - }); + service.patch(12, { message: 'Hello' }) + }) - it('.remove and removed', done => { + it('.remove and removed', (done) => { const app = feathers().use('/creator', { - async remove (id: any) { - return { id }; + async remove(id: any) { + return { id } } - }); + }) - const service = app.service('creator'); + const service = app.service('creator') service.on('removed', (data: any) => { - assert.deepStrictEqual(data, { id: 22 }); - done(); - }); + assert.deepStrictEqual(data, { id: 22 }) + done() + }) - service.remove(22); - }); - }); + service.remove(22) + }) + }) describe('emits event data arrays on a service', () => { it('.create and created with array', async () => { const app = feathers().use('/creator', { - async create (data: any) { + async create(data: any) { if (Array.isArray(data)) { - return Promise.all(data.map(current => - (this as any).create(current)) - ); + return Promise.all(data.map((current) => (this as any).create(current))) } - return data; + return data } - }); - - const service = app.service('creator'); - const createItems = [ - { message: 'Hello 0' }, - { message: 'Hello 1' } - ]; - - const events = Promise.all(createItems.map((element, index) => { - return new Promise((resolve) => { - service.on('created', (data: any) => { - if (data.message === element.message) { - assert.deepStrictEqual(data, { message: `Hello ${index}` }); - resolve(); - } - }); - }); - })); - - await service.create(createItems); - await events; - }); + }) + + const service = app.service('creator') + const createItems = [{ message: 'Hello 0' }, { message: 'Hello 1' }] + + const events = Promise.all( + createItems.map((element, index) => { + return new Promise((resolve) => { + service.on('created', (data: any) => { + if (data.message === element.message) { + assert.deepStrictEqual(data, { message: `Hello ${index}` }) + resolve() + } + }) + }) + }) + ) + + await service.create(createItems) + await events + }) it('.update and updated with array', async () => { const app = feathers().use('/creator', { - async update (id: any, data: any) { + async update(id: any, data: any) { if (Array.isArray(data)) { - return Promise.all(data.map((current, index) => - (this as any).update(index, current)) - ); + return Promise.all(data.map((current, index) => (this as any).update(index, current))) } - return Object.assign({ id }, data); + return Object.assign({ id }, data) } - }); - - const service = app.service('creator'); - const updateItems = [ - { message: 'Hello 0' }, - { message: 'Hello 1' } - ]; - - const events = Promise.all(updateItems.map((element, index) => { - return new Promise((resolve) => { - service.on('updated', (data: any) => { - if (data.message === element.message) { - assert.deepStrictEqual(data, { id: index, message: `Hello ${index}` }); - resolve(); - } - }); - }); - })); - - await service.update(null, updateItems); - await events; - }); + }) + + const service = app.service('creator') + const updateItems = [{ message: 'Hello 0' }, { message: 'Hello 1' }] + + const events = Promise.all( + updateItems.map((element, index) => { + return new Promise((resolve) => { + service.on('updated', (data: any) => { + if (data.message === element.message) { + assert.deepStrictEqual(data, { + id: index, + message: `Hello ${index}` + }) + resolve() + } + }) + }) + }) + ) + + await service.update(null, updateItems) + await events + }) it('.patch and patched with array', async () => { const app = feathers().use('/creator', { - async patch (id: any, data: any) { + async patch(id: any, data: any) { if (Array.isArray(data)) { - return Promise.all(data.map((current, index) => - (this as any).patch(index, current)) - ); + return Promise.all(data.map((current, index) => (this as any).patch(index, current))) } - return Object.assign({ id }, data); + return Object.assign({ id }, data) } - }); - - const service = app.service('creator'); - const patchItems = [ - { message: 'Hello 0' }, - { message: 'Hello 1' } - ]; - - const events = Promise.all(patchItems.map((element, index) => { - return new Promise((resolve) => { - service.on('patched', (data: any) => { - if (data.message === element.message) { - assert.deepStrictEqual(data, { id: index, message: `Hello ${index}` }); - resolve(); - } - }); - }); - })); - - await service.patch(null, patchItems); - await events; - }); + }) + + const service = app.service('creator') + const patchItems = [{ message: 'Hello 0' }, { message: 'Hello 1' }] + + const events = Promise.all( + patchItems.map((element, index) => { + return new Promise((resolve) => { + service.on('patched', (data: any) => { + if (data.message === element.message) { + assert.deepStrictEqual(data, { + id: index, + message: `Hello ${index}` + }) + resolve() + } + }) + }) + }) + ) + + await service.patch(null, patchItems) + await events + }) it('.remove and removed with array', async () => { + const removeItems = [{ message: 'Hello 0' }, { message: 'Hello 1' }] + const app = feathers().use('/creator', { - async remove (id: any, data: any) { - if (Array.isArray(data)) { - return Promise.all(data.map((current, index) => - (this as any).remove(index, current)) - ); + async remove(id: any, data: any) { + if (id === null) { + return Promise.all(removeItems.map((current, index) => (this as any).remove(index, current))) } - return Object.assign({ id }, data); + return Object.assign({ id }, data) } - }); - - const service = app.service('creator'); - const removeItems = [ - { message: 'Hello 0' }, - { message: 'Hello 1' } - ]; - - const events = Promise.all(removeItems.map((element, index) => { - return new Promise((resolve) => { - service.on('removed', (data: any) => { - if (data.message === element.message) { - assert.deepStrictEqual(data, { id: index, message: `Hello ${index}` }); - resolve(); - } - }); - }); - })); - - await service.remove(null, removeItems); - await events; - }); - }); + }) + + const service = app.service('creator') + + const events = Promise.all( + removeItems.map((element, index) => { + return new Promise((resolve) => { + service.on('removed', (data: any) => { + if (data.message === element.message) { + assert.deepStrictEqual(data, { + id: index, + message: `Hello ${index}` + }) + resolve() + } + }) + }) + }) + ) + + await service.remove(null) + await events + }) + }) describe('event format', () => { - it('also emits the actual hook object', done => { + it('also emits the actual hook object', (done) => { const app = feathers().use('/creator', { - async create (data: any) { - return data; + async create(data: any) { + return data } - }); + }) - const service = app.service('creator'); + const service = app.service('creator') service.hooks({ - after (hook: any) { - hook.changed = true; + after(hook: any) { + hook.changed = true } - }); + }) service.on('created', (data: any, hook: any) => { try { - assert.deepStrictEqual(data, { message: 'Hi' }); - assert.ok(hook.changed); - assert.strictEqual(hook.service, service); - assert.strictEqual(hook.method, 'create'); - assert.strictEqual(hook.type, null); - done(); + assert.deepStrictEqual(data, { message: 'Hi' }) + assert.ok(hook.changed) + assert.strictEqual(hook.service, service) + assert.strictEqual(hook.method, 'create') + assert.strictEqual(hook.type, null) + done() } catch (error: any) { - done(error); + done(error) } - }); + }) - service.create({ message: 'Hi' }); - }); + service.create({ message: 'Hi' }) + }) - it('events indicated by the service are not sent automatically', done => { + it('events indicated by the service are not sent automatically', (done) => { class Creator { - events = [ 'created' ]; - async create (data: any) { - return data; + events = ['created'] + async create(data: any) { + return data } } - const app = feathers().use('/creator', new Creator()); - const service = app.service('creator'); + const app = feathers().use('/creator', new Creator()) + const service = app.service('creator') service.on('created', (data: any) => { - assert.deepStrictEqual(data, { message: 'custom event' }); - done(); - }); - - service.create({ message: 'hello' }); - service.emit('created', { message: 'custom event' }); - }); - }); -}); + assert.deepStrictEqual(data, { message: 'custom event' }) + done() + }) + + service.create({ message: 'hello' }) + service.emit('created', { message: 'custom event' }) + }) + }) +}) diff --git a/packages/feathers/test/hooks/after.test.ts b/packages/feathers/test/hooks/after.test.ts index 9e35b2e3d6..29a1810420 100644 --- a/packages/feathers/test/hooks/after.test.ts +++ b/packages/feathers/test/hooks/after.test.ts @@ -1,374 +1,384 @@ -import assert from 'assert'; -import { feathers, Id } from '../../src'; +import assert from 'assert' +import { feathers, Id } from '../../src' describe('`after` hooks', () => { it('.after hooks can return a promise', async () => { const app = feathers().use('/dummy', { - async get (id: Id) { + async get(id: Id) { return { - id, description: `You have to do ${id}` - }; + id, + description: `You have to do ${id}` + } }, - async find () { - return []; + async find() { + return [] } - }); - const service = app.service('dummy'); + }) + const service = app.service('dummy') service.hooks({ after: { - async get (hook) { - hook.result.ran = true; - return hook; + async get(hook) { + hook.result.ran = true + return hook }, - async find () { - throw new Error('You can not see this'); + async find() { + throw new Error('You can not see this') } } - }); + }) - const data = await service.get('laundry', {}); + const data = await service.get('laundry', {}) assert.deepStrictEqual(data, { id: 'laundry', description: 'You have to do laundry', ran: true - }); + }) await assert.rejects(() => service.find({}), { message: 'You can not see this' - }); - }); + }) + }) it('.after hooks do not need to return anything', async () => { const app = feathers().use('/dummy', { - async get (id: Id) { + async get(id: Id) { return { - id, description: `You have to do ${id}` - }; + id, + description: `You have to do ${id}` + } }, - async find () { - return []; + async find() { + return [] } - }); - const service = app.service('dummy'); + }) + const service = app.service('dummy') service.hooks({ after: { - get (context) { - context.result.ran = true; + get(context) { + context.result.ran = true }, - find () { - throw new Error('You can not see this'); + find() { + throw new Error('You can not see this') } } - }); + }) - const data = await service.get('laundry'); + const data = await service.get('laundry') assert.deepStrictEqual(data, { id: 'laundry', description: 'You have to do laundry', ran: true - }); + }) await assert.rejects(() => service.find(), { message: 'You can not see this' - }); - }); + }) + }) it('gets mixed into a service and modifies data', async () => { const dummyService = { - async create (data: any) { - return data; + async create(data: any) { + return data } - }; + } - const app = feathers().use('/dummy', dummyService); - const service = app.service('dummy'); + const app = feathers().use('/dummy', dummyService) + const service = app.service('dummy') service.hooks({ after: { - create (context) { - assert.strictEqual(context.type, 'after'); + create(context) { + assert.strictEqual(context.type, 'after') - context.result.some = 'thing'; + context.result.some = 'thing' - return context; + return context } } - }); + }) - const data = await service.create({ my: 'data' }); + const data = await service.create({ my: 'data' }) - assert.deepStrictEqual({ my: 'data', some: 'thing' }, data, 'Got modified data'); - }); + assert.deepStrictEqual({ my: 'data', some: 'thing' }, data, 'Got modified data') + }) it('also makes the app available at hook.app', async () => { const dummyService = { - async create (data: any) { - return data; + async create(data: any) { + return data } - }; + } - const app = feathers().use('/dummy', dummyService); - const service = app.service('dummy'); + const app = feathers().use('/dummy', dummyService) + const service = app.service('dummy') service.hooks({ after: { - create (context) { - context.result.appPresent = typeof context.app !== 'undefined'; - assert.strictEqual(context.result.appPresent, true); + create(context) { + context.result.appPresent = typeof context.app !== 'undefined' + assert.strictEqual(context.result.appPresent, true) - return context; + return context } } - }); + }) - const data = await service.create({ my: 'data' }); + const data = await service.create({ my: 'data' }) - assert.deepStrictEqual({ my: 'data', appPresent: true }, data, 'The app was present in the hook.'); - }); + assert.deepStrictEqual({ my: 'data', appPresent: true }, data, 'The app was present in the hook.') + }) it('returns errors', async () => { const dummyService = { - async update (_id: any, data: any) { - return data; + async update(_id: any, data: any) { + return data } - }; + } - const app = feathers().use('/dummy', dummyService); - const service = app.service('dummy'); + const app = feathers().use('/dummy', dummyService) + const service = app.service('dummy') service.hooks({ after: { - update () { - throw new Error('This did not work'); + update() { + throw new Error('This did not work') } } - }); + }) await assert.rejects(() => service.update(1, { my: 'data' }), { message: 'This did not work' - }); - }); + }) + }) it('does not run after hook when there is an error', async () => { const dummyService = { - async remove () { - throw new Error('Error removing item'); + async remove() { + throw new Error('Error removing item') } - }; + } - const app = feathers().use('/dummy', dummyService); - const service = app.service('dummy'); + const app = feathers().use('/dummy', dummyService) + const service = app.service('dummy') service.hooks({ after: { - remove () { - assert.ok(false, 'This should never get called'); + remove() { + assert.ok(false, 'This should never get called') } } - }); + }) await assert.rejects(() => service.remove(1, {}), { message: 'Error removing item' - }); - }); + }) + }) it('adds .after() and chains multiple hooks for the same method', async () => { const dummyService = { - async create (data: any) { - return data; + async create(data: any) { + return data } - }; + } - const app = feathers().use('/dummy', dummyService); - const service = app.service('dummy'); + const app = feathers().use('/dummy', dummyService) + const service = app.service('dummy') service.hooks({ after: { - create (context) { - context.result.some = 'thing'; + create(context) { + context.result.some = 'thing' - return context; + return context } } - }); + }) service.hooks({ after: { - create (context) { - context.result.other = 'stuff'; + create(context) { + context.result.other = 'stuff' } } - }); + }) - const data = await service.create({ my: 'data' }); + const data = await service.create({ my: 'data' }) - assert.deepStrictEqual({ - my: 'data', - some: 'thing', - other: 'stuff' - }, data, 'Got modified data'); - }); + assert.deepStrictEqual( + { + my: 'data', + some: 'thing', + other: 'stuff' + }, + data, + 'Got modified data' + ) + }) it('chains multiple after hooks using array syntax', async () => { const dummyService = { - async create (data: any) { - return data; + async create(data: any) { + return data } - }; + } - const app = feathers().use('/dummy', dummyService); - const service = app.service('dummy'); + const app = feathers().use('/dummy', dummyService) + const service = app.service('dummy') service.hooks({ after: { create: [ function (context) { - context.result.some = 'thing'; + context.result.some = 'thing' - return context; + return context }, function (context) { - context.result.other = 'stuff'; + context.result.other = 'stuff' - return context; + return context } ] } - }); + }) - const data = await service.create({ my: 'data' }); + const data = await service.create({ my: 'data' }) - assert.deepStrictEqual({ - my: 'data', - some: 'thing', - other: 'stuff' - }, data, 'Got modified data'); - }); + assert.deepStrictEqual( + { + my: 'data', + some: 'thing', + other: 'stuff' + }, + data, + 'Got modified data' + ) + }) it('.after hooks run in the correct order (#13)', async () => { const app = feathers().use('/dummy', { - async get (id: any) { - return { id }; + async get(id: any) { + return { id } } - }); - const service = app.service('dummy'); + }) + const service = app.service('dummy') service.hooks({ after: { - get (context) { - context.result.items = ['first']; + get(context) { + context.result.items = ['first'] - return context; + return context } } - }); + }) service.hooks({ after: { get: [ function (context) { - context.result.items.push('second'); + context.result.items.push('second') - return context; + return context }, function (context) { - context.result.items.push('third'); + context.result.items.push('third') - return context; + return context } ] } - }); + }) - const data = await service.get(10); + const data = await service.get(10) - assert.deepStrictEqual(data.items, ['first', 'second', 'third']); - }); + assert.deepStrictEqual(data.items, ['first', 'second', 'third']) + }) it('after all hooks (#11)', async () => { const app = feathers().use('/dummy', { - async get (id: any) { - const items: any[] = []; + async get(id: any) { + const items: any[] = [] - return { id, items }; + return { id, items } }, - async find () { - return []; + async find() { + return [] } - }); + }) - const service = app.service('dummy'); + const service = app.service('dummy') service.hooks({ after: { - all (context) { - context.result.afterAllObject = true; + all(context) { + context.result.afterAllObject = true - return context; + return context } } - }); + }) service.hooks({ after: [ function (context) { - context.result.afterAllMethodArray = true; + context.result.afterAllMethodArray = true - return context; + return context } ] - }); + }) - let data = await service.find({}); + let data = await service.find({}) - assert.ok(data.afterAllObject); - assert.ok(data.afterAllMethodArray); + assert.ok(data.afterAllObject) + assert.ok(data.afterAllMethodArray) - data = await service.get(1, {}); + data = await service.get(1, {}) - assert.ok(data.afterAllObject); - assert.ok(data.afterAllMethodArray); - }); + assert.ok(data.afterAllObject) + assert.ok(data.afterAllMethodArray) + }) it('after hooks have service as context and keep it in service method (#17)', async () => { class Dummy { - number = 42; - async get (id: any) { + number = 42 + async get(id: any) { return { id, number: this.number - }; + } } } - const app = feathers().use('/dummy', new Dummy()); + const app = feathers().use('/dummy', new Dummy()) - const service = app.service('dummy'); + const service = app.service('dummy') service.hooks({ after: { - get (this: any, hook) { - hook.result.test = this.number + 1; + get(this: any, hook) { + hook.result.test = this.number + 1 - return hook; + return hook } } - }); + }) - const data = await service.get(10); + const data = await service.get(10) assert.deepStrictEqual(data, { id: 10, number: 42, test: 43 - }); - }); -}); + }) + }) +}) diff --git a/packages/feathers/test/hooks/app.test.ts b/packages/feathers/test/hooks/app.test.ts index e6b7c6ce33..2ad8ca0e35 100644 --- a/packages/feathers/test/hooks/app.test.ts +++ b/packages/feathers/test/hooks/app.test.ts @@ -1,231 +1,326 @@ -import assert from 'assert'; +import assert from 'assert' -import { feathers, Application } from '../../src'; +import { feathers, Application, ApplicationHookMap, ServiceInterface, Params } from '../../src' + +type Todo = { + id?: string + params?: TodoParams + data?: any + test?: string + order?: string[] +} + +interface TodoParams extends Params { + order: string[] + ran: boolean +} + +type TodoService = ServiceInterface & { + customMethod(data: any, params?: TodoParams): Promise +} + +type App = Application<{ todos: TodoService }> describe('app.hooks', () => { - let app: Application; + let app: App beforeEach(() => { - app = feathers().use('/todos', { - async get (id: any, params: any) { - if (id === 'error') { - throw new Error('Something went wrong'); + app = feathers<{ todos: TodoService }>().use( + 'todos', + { + async get(id: any, params: any) { + if (id === 'error') { + throw new Error('Something went wrong') + } + + return { id, params } + }, + + async create(data: any, params: any) { + return { data, params } + }, + + async customMethod(data: any, params: TodoParams) { + return { data, params } } - - return { id, params }; }, - - async create (data: any, params: any) { - return { data, params }; + { + methods: ['get', 'create', 'customMethod'] } - }); - }); + ) + }) it('app has the .hooks method', () => { - assert.strictEqual(typeof app.hooks, 'function'); - }); + assert.strictEqual(typeof app.hooks, 'function') + }) + + it('.setup and .teardown special hooks', async () => { + const app = feathers() + + // Test that setup and teardown can be overwritten + const oldSetup = app.setup + app.setup = function (arg: any) { + return oldSetup.call(this, arg) + } + const oldTeardown = app.teardown + app.teardown = function (arg: any) { + return oldTeardown.call(this, arg) + } + + const order: string[] = [] + const hooks: ApplicationHookMap = { + setup: [ + async (context, next) => { + assert.strictEqual(context.app, app) + order.push('setup 1') + await next() + }, + async (_context, next) => { + order.push('setup 2') + await next() + order.push('setup after') + } + ], + teardown: [ + async (context, next) => { + assert.strictEqual(context.app, app) + order.push('teardown 1') + await next() + }, + async (_context, next) => { + order.push('teardown 2') + await next() + } + ] + } + + app.hooks(hooks) + + await app.setup() + await app.teardown() + + assert.deepStrictEqual(order, ['setup 1', 'setup 2', 'setup after', 'teardown 1', 'teardown 2']) + }) describe('app.hooks([ async ])', () => { - it('basic app async hook', async () => { - const service = app.service('todos'); + it('basic app async hook, works with custom method', async () => { + const service = app.service('todos') app.hooks([ async (context, next) => { - assert.strictEqual(context.app, app); - await next(); - context.params.ran = true; + assert.strictEqual(context.app, app) + await next() + context.params.ran = true } - ]); + ]) - let result = await service.get('test'); + let result = await service.get('test') assert.deepStrictEqual(result, { id: 'test', params: { ran: true } - }); + }) + + const data = { test: 'hi' } + + result = await service.create(data) - const data = { test: 'hi' }; + assert.deepStrictEqual(result, { + data, + params: { ran: true } + }) - result = await service.create(data); + result = await service.customMethod('custom test') assert.deepStrictEqual(result, { - data, params: { ran: true } - }); - }); - }); + data: 'custom test', + params: { ran: true } + }) + }) + }) describe('app.hooks({ method: [ async ] })', () => { it('basic app async method hook', async () => { - const service = app.service('todos'); + const service = app.service('todos') app.hooks({ - get: [async (context, next) => { - assert.strictEqual(context.app, app); - await next(); - context.params.ran = true; - }] - }); + get: [ + async (context, next) => { + assert.strictEqual(context.app, app) + await next() + context.params.ran = true + } + ] + }) - const result = await service.get('test'); + const result = await service.get('test') assert.deepStrictEqual(result, { id: 'test', params: { ran: true } - }); - }); - }); + }) + }) + }) describe('app.hooks({ before })', () => { - it('basic app before hook', async () => { - const service = app.service('todos'); + it('basic app before hook, works with custom method', async () => { + const service = app.service('todos') app.hooks({ - before (context) { - assert.strictEqual(context.app, app); - context.params.ran = true; + before(context) { + assert.strictEqual(context.app, app) + context.params.ran = true } - }); + }) - let result = await service.get('test'); + let result = await service.get('test') assert.deepStrictEqual(result, { id: 'test', params: { ran: true } - }); + }) - const data = { test: 'hi' }; + const data = { test: 'hi' } - result = await service.create(data); + result = await service.create(data) assert.deepStrictEqual(result, { - data, params: { ran: true } - }); - }); + data, + params: { ran: true } + }) + + result = await service.customMethod('custom with before') + + assert.deepStrictEqual(result, { + data: 'custom with before', + params: { ran: true } + }) + }) it('app before hooks always run first', async () => { app.service('todos').hooks({ - before (context) { - assert.strictEqual(context.app, app); - context.params.order.push('service.before'); + before(context) { + assert.strictEqual(context.app, app) + context.params.order.push('service.before') } - }); + }) app.service('todos').hooks({ - before (context) { - assert.strictEqual(context.app, app); - context.params.order.push('service.before 1'); + before(context) { + assert.strictEqual(context.app, app) + context.params.order.push('service.before 1') } - }); + }) app.hooks({ - before (context) { - assert.strictEqual(context.app, app); - context.params.order = []; - context.params.order.push('app.before'); + before(context) { + assert.strictEqual(context.app, app) + context.params.order = [] + context.params.order.push('app.before') } - }); + }) - const result = await app.service('todos').get('test'); + const result = await app.service('todos').get('test') assert.deepStrictEqual(result, { id: 'test', params: { - order: [ 'app.before', 'service.before', 'service.before 1' ] + order: ['app.before', 'service.before', 'service.before 1'] } - }); - }); - }); + }) + }) + }) describe('app.hooks({ after })', () => { it('basic app after hook', async () => { app.hooks({ - after (context) { - assert.strictEqual(context.app, app); - context.result.ran = true; + after(context) { + assert.strictEqual(context.app, app) + context.result.ran = true } - }); + }) - const result = await app.service('todos').get('test'); + const result = await app.service('todos').get('test') assert.deepStrictEqual(result, { id: 'test', params: {}, ran: true - }); - }); + }) + }) it('app after hooks always run last', async () => { app.hooks({ - after (context) { - assert.strictEqual(context.app, app); - context.result.order.push('app.after'); + after(context) { + assert.strictEqual(context.app, app) + context.result.order.push('app.after') } - }); + }) app.service('todos').hooks({ - after (context) { - assert.strictEqual(context.app, app); - context.result.order = []; - context.result.order.push('service.after'); + after(context) { + assert.strictEqual(context.app, app) + context.result.order = [] + context.result.order.push('service.after') } - }); + }) app.service('todos').hooks({ - after (context) { - assert.strictEqual(context.app, app); - context.result.order.push('service.after 1'); + after(context) { + assert.strictEqual(context.app, app) + context.result.order.push('service.after 1') } - }); + }) - const result = await app.service('todos').get('test'); + const result = await app.service('todos').get('test') assert.deepStrictEqual(result, { id: 'test', params: {}, - order: [ 'service.after', 'service.after 1', 'app.after' ] - }); - }); - }); + order: ['service.after', 'service.after 1', 'app.after'] + }) + }) + }) describe('app.hooks({ error })', () => { it('basic app error hook', async () => { app.hooks({ - error (context) { - assert.strictEqual(context.app, app); - context.error = new Error('App hook ran'); + error(context) { + assert.strictEqual(context.app, app) + context.error = new Error('App hook ran') } - }); + }) await assert.rejects(() => app.service('todos').get('error'), { message: 'App hook ran' - }); - }); + }) + }) it('app error hooks always run last', async () => { app.hooks({ - error (context) { - assert.strictEqual(context.app, app); - context.error = new Error(`${context.error.message} app.after`); + error(context) { + assert.strictEqual(context.app, app) + context.error = new Error(`${context.error.message} app.after`) } - }); + }) app.service('todos').hooks({ - error (context) { - assert.strictEqual(context.app, app); - context.error = new Error(`${context.error.message} service.after`); + error(context) { + assert.strictEqual(context.app, app) + context.error = new Error(`${context.error.message} service.after`) } - }); + }) app.service('todos').hooks({ - error (context) { - assert.strictEqual(context.app, app); - context.error = new Error(`${context.error.message} service.after 1`); + error(context) { + assert.strictEqual(context.app, app) + context.error = new Error(`${context.error.message} service.after 1`) } - }); + }) await assert.rejects(() => app.service('todos').get('error'), { message: 'Something went wrong service.after service.after 1 app.after' - }); - }); - }); -}); + }) + }) + }) +}) diff --git a/packages/feathers/test/hooks/around.test.ts b/packages/feathers/test/hooks/around.test.ts new file mode 100644 index 0000000000..5a1a209b9b --- /dev/null +++ b/packages/feathers/test/hooks/around.test.ts @@ -0,0 +1,397 @@ +import assert from 'assert' +import { feathers, Params, ServiceInterface } from '../../src' + +describe('`around` hooks', () => { + it('around hooks can set hook.result which will skip service method', async () => { + const app = feathers().use('/dummy', { + async get() { + assert.ok(false, 'This should never run') + } + }) + const service = app.service('dummy') + + service.hooks({ + get: [ + async (hook, next) => { + hook.result = { + id: hook.id, + message: 'Set from hook' + } + + await next() + } + ] + }) + + const data = await service.get(10, {}) + + assert.deepStrictEqual(data, { + id: 10, + message: 'Set from hook' + }) + }) + + it('works with traditional registration format, all syntax and app hooks', async () => { + const app = feathers().use('/dummy', { + async get() { + assert.ok(false, 'This should never run') + } + }) + const service = app.service('dummy') + + app.hooks([ + async function (this: any, hook, next) { + hook.result = { + id: hook.id, + app: 'Set from app around all' + } + + await next() + } + ]) + + service.hooks({ + around: { + all: [ + async (hook, next) => { + hook.result = { + ...hook.result, + all: 'Set from around all' + } + + await next() + } + ], + get: [ + async (hook, next) => { + hook.result = { + ...hook.result, + get: 'Set from around get' + } + + await next() + } + ] + } + }) + + const data = await service.get(10, {}) + + assert.deepStrictEqual(data, { + id: 10, + app: 'Set from app around all', + all: 'Set from around all', + get: 'Set from around get' + }) + }) + + it('gets mixed into a service and modifies data', async () => { + const dummyService = { + async create(data: any, params: any) { + assert.deepStrictEqual( + data, + { + some: 'thing', + modified: 'data' + }, + 'Data modified' + ) + + assert.deepStrictEqual( + params, + { + modified: 'params' + }, + 'Params modified' + ) + + return data + } + } + const app = feathers().use('/dummy', dummyService) + const service = app.service('dummy') + + service.hooks({ + create: [ + async (hook, next) => { + assert.strictEqual(hook.type, null) + + hook.data.modified = 'data' + + Object.assign(hook.params, { + modified: 'params' + }) + + await next() + } + ] + }) + + const data = await service.create({ some: 'thing' }) + + assert.deepStrictEqual( + data, + { + some: 'thing', + modified: 'data' + }, + 'Data got modified' + ) + }) + + it('contains the app object at hook.app', async () => { + const someServiceConfig = { + async create(data: any) { + return data + } + } + const app = feathers().use('/some-service', someServiceConfig) + const someService = app.service('some-service') + + someService.hooks({ + create: [ + async (hook, next) => { + hook.data.appPresent = typeof hook.app !== 'undefined' + assert.strictEqual(hook.data.appPresent, true) + return next() + } + ] + }) + + const data = await someService.create({ some: 'thing' }) + + assert.deepStrictEqual( + data, + { + some: 'thing', + appPresent: true + }, + 'App object was present' + ) + }) + + it('passes errors', async () => { + const dummyService = { + update() { + assert.ok(false, 'Never should be called') + } + } + const app = feathers().use('/dummy', dummyService) + const service = app.service('dummy') + + service.hooks({ + update: [ + async () => { + throw new Error('You are not allowed to update') + } + ] + }) + + await assert.rejects(() => service.update(1, {}), { + message: 'You are not allowed to update' + }) + }) + + it('does not run after hook when there is an error', async () => { + const dummyService = { + async remove() { + throw new Error('Error removing item') + } + } + const app = feathers().use('/dummy', dummyService) + const service = app.service('dummy') + + service.hooks({ + remove: [ + async (_context, next) => { + await next() + + assert.ok(false, 'This should never get called') + } + ] + }) + + await assert.rejects(() => service.remove(1, {}), { + message: 'Error removing item' + }) + }) + + it('adds .hooks() and chains multiple hooks for the same method', async () => { + interface DummyParams extends Params { + modified: string + } + + class DummyService implements ServiceInterface { + create(data: any, params?: any) { + assert.deepStrictEqual( + data, + { + some: 'thing', + modified: 'second data' + }, + 'Data modified' + ) + + assert.deepStrictEqual( + params, + { + modified: 'params' + }, + 'Params modified' + ) + + return Promise.resolve(data) + } + } + + const app = feathers<{ dummy: DummyService }>().use('dummy', new DummyService()) + const service = app.service('dummy') + + service.hooks({ + create: [ + async (hook, next) => { + hook.params.modified = 'params' + + await next() + }, + async (hook, next) => { + hook.data.modified = 'second data' + + next() + } + ] + }) + + await service.create({ some: 'thing' }) + }) + + it('around hooks run in the correct order', async () => { + interface DummyParams extends Params<{ name: string }> { + items: string[] + } + + class DummyService implements ServiceInterface { + async get(id: any, params?: DummyParams) { + assert.deepStrictEqual(params.items, ['first', 'second', 'third']) + + return { + id, + items: [] as string[] + } + } + } + + const app = feathers<{ dummy: DummyService }>().use('dummy', new DummyService()) + const service = app.service('dummy') + + service.hooks({ + get: [ + async (hook, next) => { + hook.params.items = ['first'] + await next() + } + ] + }) + + service.hooks({ + get: [ + async function (hook, next) { + hook.params.items.push('second') + next() + }, + async function (hook, next) { + hook.params.items.push('third') + next() + } + ] + }) + + await service.get(10) + }) + + it('around all hooks (#11)', async () => { + interface DummyParams extends Params { + asyncAllObject: boolean + asyncAllMethodArray: boolean + } + + type DummyService = ServiceInterface + + const app = feathers<{ dummy: DummyService }>().use('dummy', { + async get(id: any, params: any) { + assert.ok(params.asyncAllObject) + assert.ok(params.asyncAllMethodArray) + + return { + id, + items: [] + } + }, + + async find(params: any) { + assert.ok(params.asyncAllObject) + assert.ok(params.asyncAllMethodArray) + + return [] + } + }) + + const service = app.service('dummy') + + service.hooks([ + async (hook, next) => { + hook.params.asyncAllObject = true + next() + } + ]) + + service.hooks([ + async function (hook, next) { + hook.params.asyncAllMethodArray = true + next() + } + ]) + + await service.find() + }) + + it('around hooks have service as context and keep it in service method (#17)', async () => { + interface DummyParams extends Params { + test: number + } + + class Dummy implements ServiceInterface { + number = 42 + + async get(id: any, params?: DummyParams) { + return { + id, + number: (this as any).number, + test: params.test + } + } + } + + const app = feathers<{ dummy: Dummy }>().use('dummy', new Dummy()) + + const service = app.service('dummy') + + service.hooks({ + get: [ + async function (this: any, hook, next) { + hook.params.test = this.number + 2 + + await next() + } + ] + }) + + const data = await service.get(10) + + assert.deepStrictEqual(data, { + id: 10, + number: 42, + test: 44 + }) + }) +}) diff --git a/packages/feathers/test/hooks/async.test.ts b/packages/feathers/test/hooks/async.test.ts deleted file mode 100644 index 90e28ffaab..0000000000 --- a/packages/feathers/test/hooks/async.test.ts +++ /dev/null @@ -1,280 +0,0 @@ -import assert from 'assert'; -import { feathers } from '../../src'; - -describe('`async` hooks', () => { - it('async hooks can set hook.result which will skip service method', async () => { - const app = feathers().use('/dummy', { - async get () { - assert.ok(false, 'This should never run'); - } - }); - const service = app.service('dummy'); - - service.hooks({ - get: [async (hook, next) => { - hook.result = { - id: hook.id, - message: 'Set from hook' - }; - - await next(); - }] - }); - - const data = await service.get(10, {}); - - assert.deepStrictEqual(data, { - id: 10, - message: 'Set from hook' - }); - }); - - it('gets mixed into a service and modifies data', async () => { - const dummyService = { - async create (data: any, params: any) { - assert.deepStrictEqual(data, { - some: 'thing', - modified: 'data' - }, 'Data modified'); - - assert.deepStrictEqual(params, { - modified: 'params' - }, 'Params modified'); - - return data; - } - }; - const app = feathers().use('/dummy', dummyService); - const service = app.service('dummy'); - - service.hooks({ - create: [async (hook, next) => { - assert.strictEqual(hook.type, null); - - hook.data.modified = 'data'; - - Object.assign(hook.params, { - modified: 'params' - }); - - await next(); - }] - }); - - const data = await service.create({ some: 'thing' }); - - assert.deepStrictEqual(data, { - some: 'thing', - modified: 'data' - }, 'Data got modified'); - }); - - it('contains the app object at hook.app', async () => { - const someServiceConfig = { - async create (data: any) { - return data; - } - }; - const app = feathers().use('/some-service', someServiceConfig); - const someService = app.service('some-service'); - - someService.hooks({ - create: [async (hook, next) => { - hook.data.appPresent = typeof hook.app !== 'undefined'; - assert.strictEqual(hook.data.appPresent, true); - return next(); - }] - }); - - const data = await someService.create({ some: 'thing' }); - - assert.deepStrictEqual(data, { - some: 'thing', - appPresent: true - }, 'App object was present'); - }); - - it('passes errors', async () => { - const dummyService = { - update () { - assert.ok(false, 'Never should be called'); - } - }; - const app = feathers().use('/dummy', dummyService); - const service = app.service('dummy'); - - service.hooks({ - update: [async () => { - throw new Error('You are not allowed to update'); - }] - }); - - await assert.rejects(() => service.update(1, {}), { - message: 'You are not allowed to update' - }); - }); - - it('does not run after hook when there is an error', async () => { - const dummyService = { - async remove () { - throw new Error('Error removing item'); - } - }; - const app = feathers().use('/dummy', dummyService); - const service = app.service('dummy'); - - service.hooks({ - remove: [async (_context, next) => { - await next(); - - assert.ok(false, 'This should never get called'); - }] - }); - - await assert.rejects(() => service.remove(1, {}), { - message: 'Error removing item' - }); - }); - - it('adds .hooks() and chains multiple hooks for the same method', async () => { - const dummyService = { - create (data: any, params: any) { - assert.deepStrictEqual(data, { - some: 'thing', - modified: 'second data' - }, 'Data modified'); - - assert.deepStrictEqual(params, { - modified: 'params' - }, 'Params modified'); - - return Promise.resolve(data); - } - }; - const app = feathers().use('/dummy', dummyService); - const service = app.service('dummy'); - - service.hooks({ - create: [async (hook, next) => { - hook.params.modified = 'params'; - - await next(); - }, async (hook, next) => { - hook.data.modified = 'second data'; - - next(); - }] - }); - - await service.create({ some: 'thing' }); - }); - - it('async hooks run in the correct order', async () => { - const app = feathers().use('/dummy', { - async get (id: any, params: any) { - assert.deepStrictEqual(params.items, ['first', 'second', 'third']); - - return { - id, - items: [] - }; - } - }); - const service = app.service('dummy'); - - service.hooks({ - get: [async (hook, next) => { - hook.params.items = ['first']; - await next(); - }] - }); - - service.hooks({ - get: [ - async function (hook, next) { - hook.params.items.push('second'); - next(); - }, - async function (hook, next) { - hook.params.items.push('third'); - next(); - } - ] - }); - - await service.get(10); - }); - - it('async all hooks (#11)', async () => { - const app = feathers().use('/dummy', { - async get (id: any, params: any) { - assert.ok(params.asyncAllObject); - assert.ok(params.asyncAllMethodArray); - - return { - id, - items: [] - }; - }, - - async find (params: any) { - assert.ok(params.asyncAllObject); - assert.ok(params.asyncAllMethodArray); - - return []; - } - }); - - const service = app.service('dummy'); - - service.hooks([ - async (hook, next) => { - hook.params.asyncAllObject = true; - next(); - } - ]); - - service.hooks([ - async function (hook, next) { - hook.params.asyncAllMethodArray = true; - next(); - } - ]); - - await service.find(); - }); - - it('async hooks have service as context and keep it in service method (#17)', async () => { - class Dummy { - number= 42; - - async get (id: any, params: any) { - return { - id, - number: (this as any).number, - test: params.test - }; - } - } - - const app = feathers().use('/dummy', new Dummy()); - - const service = app.service('dummy'); - - service.hooks({ - get: [async function (this: any, hook, next) { - hook.params.test = this.number + 2; - - await next(); - }] - }); - - const data = await service.get(10); - - assert.deepStrictEqual(data, { - id: 10, - number: 42, - test: 44 - }); - }); -}); diff --git a/packages/feathers/test/hooks/before.test.ts b/packages/feathers/test/hooks/before.test.ts index 8042656208..b2b999534a 100644 --- a/packages/feathers/test/hooks/before.test.ts +++ b/packages/feathers/test/hooks/before.test.ts @@ -1,425 +1,506 @@ -import assert from 'assert'; -import { feathers } from '../../src'; +import assert from 'assert' +import { feathers, Params, ServiceInterface } from '../../src' describe('`before` hooks', () => { it('.before hooks can return a promise', async () => { - const app = feathers().use('/dummy', { - async get (id: any, params: any) { - assert.ok(params.ran, 'Ran through promise hook'); + interface DummyParams extends Params { + ran: boolean + } + + type DummyService = ServiceInterface + + const app = feathers<{ dummy: DummyService }>().use('dummy', { + async get(id: any, params: DummyParams) { + assert.ok(params.ran, 'Ran through promise hook') return { id, description: `You have to do ${id}` - }; + } }, - async remove () { - assert.ok(false, 'Should never get here'); + async remove() { + assert.ok(false, 'Should never get here') } - }); - const service = app.service('dummy'); + }) + const service = app.service('dummy') service.hooks({ before: { - get (context) { - return new Promise(resolve => { - context.params.ran = true; - resolve(); - }); + get(context) { + return new Promise((resolve) => { + context.params.ran = true + resolve() + }) }, - remove () { + remove() { return new Promise((_resolve, reject) => { - reject(new Error('This did not work')); - }); - } + reject(new Error('This did not work')) + }) + }, + + find: [] } - }); + }) await service.get('dishes') await assert.rejects(() => service.remove(10), { message: 'This did not work' - }); - }); + }) + }) it('.before hooks do not need to return anything', async () => { - const app = feathers().use('/dummy', { - async get (id: any, params: any) { - assert.ok(params.ran, 'Ran through promise hook'); + interface DummyParams extends Params { + ran: boolean + } + + type DummyService = ServiceInterface + + const app = feathers<{ dummy: DummyService }>().use('dummy', { + async get(id: any, params: any) { + assert.ok(params.ran, 'Ran through promise hook') return { id, description: `You have to do ${id}` - }; + } }, - async remove () { - assert.ok(false, 'Should never get here'); + async remove() { + assert.ok(false, 'Should never get here') } - }); - const service = app.service('dummy'); + }) + const service = app.service('dummy') service.hooks({ before: { - get (context) { - context.params.ran = true; + get(context) { + context.params.ran = true }, - remove () { - throw new Error('This did not work'); + remove() { + throw new Error('This did not work') } } - }); + }) - await service.get('dishes'); + await service.get('dishes') await assert.rejects(() => service.remove(10), { message: 'This did not work' - }); - }); + }) + }) it('.before hooks can set context.result which will skip service method', async () => { const app = feathers().use('/dummy', { - async get () { - assert.ok(false, 'This should never run'); + async get() { + assert.ok(false, 'This should never run') } - }); - const service = app.service('dummy'); + }) + const service = app.service('dummy') service.hooks({ before: { - get (context) { + get(context) { context.result = { id: context.id, message: 'Set from hook' - }; + } } } - }); + }) - const data = await service.get(10, {}); + const data = await service.get(10, {}) assert.deepStrictEqual(data, { id: 10, message: 'Set from hook' - }); - }); + }) + }) it('gets mixed into a service and modifies data', async () => { const dummyService = { - async create (data: any, params: any) { - assert.deepStrictEqual(data, { - some: 'thing', - modified: 'data' - }, 'Data modified'); + async create(data: any, params: any) { + assert.deepStrictEqual( + data, + { + some: 'thing', + modified: 'data' + }, + 'Data modified' + ) - assert.deepStrictEqual(params, { - modified: 'params' - }, 'Params modified'); + assert.deepStrictEqual( + params, + { + modified: 'params' + }, + 'Params modified' + ) - return data; + return data } - }; - const app = feathers().use('/dummy', dummyService); - const service = app.service('dummy'); + } + const app = feathers().use('/dummy', dummyService) + const service = app.service('dummy') service.hooks({ before: { - create (context) { - assert.strictEqual(context.type, 'before'); + create(context) { + assert.strictEqual(context.type, 'before') - context.data.modified = 'data'; + context.data.modified = 'data' Object.assign(context.params, { modified: 'params' - }); + }) - return context; + return context } } - }); + }) - const data = await service.create({ some: 'thing' }); + const data = await service.create({ some: 'thing' }) - assert.deepStrictEqual(data, { - some: 'thing', - modified: 'data' - }, 'Data got modified'); - }); + assert.deepStrictEqual( + data, + { + some: 'thing', + modified: 'data' + }, + 'Data got modified' + ) + }) it('contains the app object at context.app', async () => { const someServiceConfig = { - async create (data: any) { - return data; + async create(data: any) { + return data } - }; - const app = feathers().use('/some-service', someServiceConfig); - const someService = app.service('some-service'); + } + const app = feathers().use('/some-service', someServiceConfig) + const someService = app.service('some-service') someService.hooks({ before: { - create (context) { - context.data.appPresent = typeof context.app !== 'undefined'; - assert.strictEqual(context.data.appPresent, true); + create(context) { + context.data.appPresent = typeof context.app !== 'undefined' + assert.strictEqual(context.data.appPresent, true) - return context; + return context } } - }); + }) - const data = await someService.create({ some: 'thing' }); + const data = await someService.create({ some: 'thing' }) - assert.deepStrictEqual(data, { - some: 'thing', - appPresent: true - }, 'App object was present'); - }); + assert.deepStrictEqual( + data, + { + some: 'thing', + appPresent: true + }, + 'App object was present' + ) + }) it('passes errors', async () => { const dummyService = { - update () { - assert.ok(false, 'Never should be called'); + update() { + assert.ok(false, 'Never should be called') } - }; + } - const app = feathers().use('/dummy', dummyService); - const service = app.service('dummy'); + const app = feathers().use('/dummy', dummyService) + const service = app.service('dummy') service.hooks({ before: { - update () { - throw new Error('You are not allowed to update'); + update() { + throw new Error('You are not allowed to update') } } - }); + }) await assert.rejects(() => service.update(1, {}), { message: 'You are not allowed to update' - }); - }); + }) + }) it('calling back with no arguments uses the old ones', async () => { + interface DummyParams extends Params { + my: string + } + + type DummyService = ServiceInterface + const dummyService = { - async remove (id: any, params: any) { - assert.strictEqual(id, 1, 'Got id'); - assert.deepStrictEqual(params, { my: 'param' }); + async remove(id: any, params: any) { + assert.strictEqual(id, 1, 'Got id') + assert.deepStrictEqual(params, { my: 'param' }) - return { id }; + return { id } } - }; - const app = feathers().use('/dummy', dummyService); - const service = app.service('dummy'); + } + const app = feathers<{ dummy: DummyService }>().use('dummy', dummyService) + const service = app.service('dummy') service.hooks({ before: { - remove (context) { - return context; + remove(context) { + return context } } - }); + }) - await service.remove(1, { my: 'param' }); - }); + await service.remove(1, { my: 'param' }) + }) it('adds .hooks() and chains multiple hooks for the same method', async () => { + interface DummyParams extends Params { + modified: string + } + + type DummyService = ServiceInterface + const dummyService = { - async create (data: any, params: any) { - assert.deepStrictEqual(data, { - some: 'thing', - modified: 'second data' - }, 'Data modified'); + async create(data: any, params: any) { + assert.deepStrictEqual( + data, + { + some: 'thing', + modified: 'second data' + }, + 'Data modified' + ) - assert.deepStrictEqual(params, { - modified: 'params' - }, 'Params modified'); + assert.deepStrictEqual( + params, + { + modified: 'params' + }, + 'Params modified' + ) - return data; + return data } - }; - const app = feathers().use('/dummy', dummyService); - const service = app.service('dummy'); + } + const app = feathers<{ dummy: DummyService }>().use('dummy', dummyService) + const service = app.service('dummy') service.hooks({ before: { - create (context) { - context.params.modified = 'params'; + create(context) { + context.params.modified = 'params' - return context; + return context } } - }); + }) service.hooks({ before: { - create (context) { - context.data.modified = 'second data'; + create(context) { + context.data.modified = 'second data' - return context; + return context } } - }); + }) - await service.create({ some: 'thing' }); - }); + await service.create({ some: 'thing' }) + }) it('chains multiple before hooks using array syntax', async () => { + interface DummyParams extends Params { + modified: string + } + + type DummyService = ServiceInterface + const dummyService = { - async create (data: any, params: any) { - assert.deepStrictEqual(data, { - some: 'thing', - modified: 'second data' - }, 'Data modified'); + async create(data: any, params: any) { + assert.deepStrictEqual( + data, + { + some: 'thing', + modified: 'second data' + }, + 'Data modified' + ) - assert.deepStrictEqual(params, { - modified: 'params' - }, 'Params modified'); + assert.deepStrictEqual( + params, + { + modified: 'params' + }, + 'Params modified' + ) - return data; + return data } - }; + } - const app = feathers().use('/dummy', dummyService); - const service = app.service('dummy'); + const app = feathers<{ dummy: DummyService }>().use('dummy', dummyService) + const service = app.service('dummy') service.hooks({ before: { create: [ function (context) { - context.params.modified = 'params'; + context.params.modified = 'params' - return context; + return context }, function (context) { - context.data.modified = 'second data'; + context.data.modified = 'second data' - return context; + return context } ] } - }); + }) - await service.create({ some: 'thing' }); - }); + await service.create({ some: 'thing' }) + }) it('.before hooks run in the correct order (#13)', async () => { - const app = feathers().use('/dummy', { - async get (id: any, params: any) { - assert.deepStrictEqual(params.items, ['first', 'second', 'third']); + interface DummyParams extends Params { + items: string[] + } + + type DummyService = ServiceInterface + + const app = feathers<{ dummy: DummyService }>().use('dummy', { + async get(id: any, params: any) { + assert.deepStrictEqual(params.items, ['first', 'second', 'third']) return { id, items: [] - }; + } } - }); - const service = app.service('dummy'); + }) + const service = app.service('dummy') service.hooks({ before: { - get (context) { - context.params.items = ['first']; + get(context) { + context.params.items = ['first'] - return context; + return context } } - }); + }) service.hooks({ before: { get: [ function (context) { - context.params.items.push('second'); + context.params.items.push('second') - return context; + return context }, function (context) { - context.params.items.push('third'); + context.params.items.push('third') - return context; + return context } ] } - }); + }) - await service.get(10); - }); + await service.get(10) + }) it('before all hooks (#11)', async () => { - const app = feathers().use('/dummy', { - async get (id: any, params: any) { - assert.ok(params.beforeAllObject); - assert.ok(params.beforeAllMethodArray); + interface DummyParams extends Params { + beforeAllObject: boolean + beforeAllMethodArray: boolean + } + + type DummyService = ServiceInterface + + const app = feathers<{ dummy: DummyService }>().use('dummy', { + async get(id: any, params: any) { + assert.ok(params.beforeAllObject) + assert.ok(params.beforeAllMethodArray) return { id, items: [] - }; + } }, - async find (params: any) { - assert.ok(params.beforeAllObject); - assert.ok(params.beforeAllMethodArray); + async find(params: any) { + assert.ok(params.beforeAllObject) + assert.ok(params.beforeAllMethodArray) - return []; + return [] } - }); + }) - const service = app.service('dummy'); + const service = app.service('dummy') service.hooks({ before: { - all (context) { - context.params.beforeAllObject = true; + all(context) { + context.params.beforeAllObject = true - return context; + return context } } - }); + }) service.hooks({ before: [ function (context) { - context.params.beforeAllMethodArray = true; + context.params.beforeAllMethodArray = true - return context; + return context } ] - }); + }) - await service.find(); - }); + await service.find() + }) it('before hooks have service as context and keep it in service method (#17)', async () => { - class Dummy { - number = 42; + interface DummyParams extends Params { + test: number + } + + class Dummy implements ServiceInterface { + number = 42 - async get (id: any, params: any) { + async get(id: any, params?: DummyParams) { return { id, number: this.number, test: params.test - }; + } } } - const app = feathers().use('/dummy', new Dummy()); - const service = app.service('dummy'); + const app = feathers<{ dummy: Dummy }>().use('dummy', new Dummy()) + const service = app.service('dummy') service.hooks({ before: { - get (this: any, context) { - context.params.test = this.number + 2; + get(this: any, context) { + context.params.test = this.number + 2 - return context; + return context } } - }); + }) - const data = await service.get(10); + const data = await service.get(10) assert.deepStrictEqual(data, { id: 10, number: 42, test: 44 - }); - }); -}); + }) + }) +}) diff --git a/packages/feathers/test/hooks/error.test.ts b/packages/feathers/test/hooks/error.test.ts index 824f2b4185..4c42d266cf 100644 --- a/packages/feathers/test/hooks/error.test.ts +++ b/packages/feathers/test/hooks/error.test.ts @@ -1,299 +1,299 @@ -import assert from 'assert'; -import { feathers, Application, FeathersService } from '../../src'; +import assert from 'assert' +import { feathers, Application, FeathersService } from '../../src' describe('`error` hooks', () => { describe('on direct service method errors', () => { - const errorMessage = 'Something else went wrong'; + const errorMessage = 'Something else went wrong' const app = feathers().use('/dummy', { - async get () { - throw new Error('Something went wrong'); + async get() { + throw new Error('Something went wrong') } - }); - const service = app.service('dummy'); + }) + const service = app.service('dummy') afterEach(() => { - (service as any).__hooks.error.get = undefined; - (service as any).__hooks.hooks.get = []; - }); + const s = service as any + + s.__hooks.error.get = undefined + s.__hooks.collected.get = [] + }) it('basic error hook', async () => { service.hooks({ error: { - get (context) { - assert.strictEqual(context.type, 'error'); - assert.strictEqual(context.id, 'test'); - assert.strictEqual(context.method, 'get'); - assert.strictEqual(context.app, app); - assert.strictEqual(context.error.message, 'Something went wrong'); + get(context) { + assert.strictEqual(context.type, 'error') + assert.strictEqual(context.id, 'test') + assert.strictEqual(context.method, 'get') + assert.strictEqual(context.app, app) + assert.strictEqual(context.error.message, 'Something went wrong') } } - }); + }) await assert.rejects(() => service.get('test'), { message: 'Something went wrong' - }); - }); + }) + }) it('can change the error', async () => { service.hooks({ error: { - get (context) { - context.error = new Error(errorMessage); + get(context) { + context.error = new Error(errorMessage) } } - }); + }) await assert.rejects(() => service.get('test'), { message: errorMessage - }); - }); + }) + }) it('throwing an error', async () => { service.hooks({ error: { - get () { - throw new Error(errorMessage); + get() { + throw new Error(errorMessage) } } - }); + }) await assert.rejects(() => service.get('test'), { message: errorMessage - }); - }); + }) + }) it('rejecting a promise', async () => { service.hooks({ error: { - async get () { - throw new Error(errorMessage); + async get() { + throw new Error(errorMessage) } } - }); + }) await assert.rejects(() => service.get('test'), { message: errorMessage - }); - }); + }) + }) it('can chain multiple hooks', async () => { service.hooks({ error: { get: [ function (context) { - context.error = new Error(errorMessage); - context.error.first = true; + context.error = new Error(errorMessage) + context.error.first = true }, function (context) { - context.error.second = true; + context.error.second = true - return Promise.resolve(context); + return Promise.resolve(context) }, function (context) { - context.error.third = true; + context.error.third = true - return context; + return context } ] } - }); + }) await assert.rejects(() => service.get('test'), { message: errorMessage, first: true, second: true, third: true - }); - }); + }) + }) it('setting `context.result` will return result', async () => { const data = { message: 'It worked' - }; + } service.hooks({ error: { - get (context) { - context.result = data; + get(context) { + context.result = data } } - }); + }) - const result = await service.get(10); + const result = await service.get(10) - assert.deepStrictEqual(result, data); - }); + assert.deepStrictEqual(result, data) + }) it('allows to set `context.result = null` in error hooks (#865)', async () => { const app = feathers().use('/dummy', { - async get () { - throw new Error('Damnit'); + async get() { + throw new Error('Damnit') } - }); + }) app.service('dummy').hooks({ error: { - get (context: any) { - context.result = null; + get(context: any) { + context.result = null } } - }); + }) - const result = await app.service('dummy').get(1); + const result = await app.service('dummy').get(1) - assert.strictEqual(result, null); - }); + assert.strictEqual(result, null) + }) it('uses the current hook object if thrown in a service method', async () => { const app = feathers().use('/dummy', { - async get () { - throw new Error('Something went wrong'); + async get() { + throw new Error('Something went wrong') } - }); - const service = app.service('dummy'); + }) + const service = app.service('dummy') service.hooks({ - before (context) { - context.id = 42; + before(context) { + context.id = 42 }, - error (context) { - assert.strictEqual(context.id, 42); + error(context) { + assert.strictEqual(context.id, 42) } - }); + }) await assert.rejects(() => service.get(1), { message: 'Something went wrong' - }); - }); - }); + }) + }) + }) describe('error in hooks', () => { - const errorMessage = 'before hook broke'; + const errorMessage = 'before hook broke' - let app: Application; - let service: FeathersService; + let app: Application + let service: FeathersService beforeEach(() => { app = feathers().use('/dummy', { - async get (id: any) { + async get(id: any) { return { id, text: `You have to do ${id}` - }; + } } - }); + }) - service = app.service('dummy'); - }); + service = app.service('dummy') + }) it('in before hook', async () => { - service.hooks({ - before () { - throw new Error(errorMessage); - } - }).hooks({ - error (context) { - assert.strictEqual(context.original.type, 'before', - 'Original hook still set' - ); - assert.strictEqual(context.id, 'dishes'); - assert.strictEqual(context.error.message, errorMessage); - } - }); + service + .hooks({ + before() { + throw new Error(errorMessage) + } + }) + .hooks({ + error(context) { + assert.strictEqual(context.original.type, 'before', 'Original hook still set') + assert.strictEqual(context.id, 'dishes') + assert.strictEqual(context.error.message, errorMessage) + } + }) await assert.rejects(() => service.get('dishes'), { message: errorMessage - }); - }); + }) + }) it('in after hook', async () => { service.hooks({ - after () { - throw new Error(errorMessage); + after() { + throw new Error(errorMessage) }, - error (context) { - assert.strictEqual(context.original.type, 'after', - 'Original hook still set' - ); - assert.strictEqual(context.id, 'dishes'); + error(context) { + assert.strictEqual(context.original.type, 'after', 'Original hook still set') + assert.strictEqual(context.id, 'dishes') assert.deepStrictEqual(context.original.result, { id: 'dishes', text: 'You have to do dishes' - }); - assert.strictEqual(context.error.message, errorMessage); + }) + assert.strictEqual(context.error.message, errorMessage) } - }); + }) await assert.rejects(() => service.get('dishes'), { message: errorMessage - }); - }); + }) + }) it('uses the current hook object if thrown in a hook and sets context.original', async () => { service.hooks({ - after (context) { - context.modified = true; + after(context) { + context.modified = true - throw new Error(errorMessage); + throw new Error(errorMessage) }, - error (context) { - assert.ok(context.modified); - assert.strictEqual(context.original.type, 'after'); + error(context) { + assert.ok(context.modified) + assert.strictEqual(context.original.type, 'after') } - }); + }) await assert.rejects(() => service.get('laundry'), { message: errorMessage - }); - }); - }); + }) + }) + }) it('Error in before hook causes inter-service calls to have wrong hook context (#841)', async () => { - const app = feathers(); + const app = feathers() - let service1Params: any; - let service2Params: any; + let service1Params: any + let service2Params: any app.use('/service1', { - async find () { - return { message: 'service1 success' }; + async find() { + return { message: 'service1 success' } } - }); + }) app.service('service1').hooks({ - before (context: any) { - service1Params = context.params; - throw new Error('Error in service1 before hook'); + before(context: any) { + service1Params = context.params + throw new Error('Error in service1 before hook') } - }); + }) app.use('/service2', { - async find () { - await app.service('/service1').find({}); + async find() { + await app.service('/service1').find({}) - return { message: 'service2 success' }; + return { message: 'service2 success' } } - }); + }) app.service('service2').hooks({ - before (context: any) { - service2Params = context.params; - context.params.foo = 'bar'; + before(context: any) { + service2Params = context.params + context.params.foo = 'bar' }, - error (context: any) { - assert.ok(service1Params !== context.params); - assert.ok(service2Params === context.params); - assert.strictEqual(context.path, 'service2'); - assert.strictEqual(context.params.foo, 'bar'); + error(context: any) { + assert.ok(service1Params !== context.params) + assert.ok(service2Params === context.params) + assert.strictEqual(context.path, 'service2') + assert.strictEqual(context.params.foo, 'bar') } - }); + }) await assert.rejects(() => app.service('/service2').find(), { message: 'Error in service1 before hook' - }); - }); -}); + }) + }) +}) diff --git a/packages/feathers/test/hooks/hooks.test.ts b/packages/feathers/test/hooks/hooks.test.ts index f463c6feab..ddef928227 100644 --- a/packages/feathers/test/hooks/hooks.test.ts +++ b/packages/feathers/test/hooks/hooks.test.ts @@ -1,87 +1,102 @@ -import assert from 'assert'; -import { hooks, NextFunction } from '@feathersjs/hooks'; -import { HookContext, createContext, feathers, Id, Params } from '../../src'; +import assert from 'assert' +import { hooks, NextFunction } from '@feathersjs/hooks' +import { HookContext, createContext, feathers, Id, Params, ServiceInterface } from '../../src' describe('hooks basics', () => { it('mix @feathersjs/hooks and .hooks', async () => { + interface SimpleParams extends Params { + chain: string[] + } class SimpleService { - async get (id: Id, params: Params) { - return { id, chain: params.chain }; + async get(id: Id, params: SimpleParams) { + return { id, chain: params.chain } } } - hooks(SimpleService.prototype, [async (ctx: HookContext, next: NextFunction) => { - ctx.params.chain.push('@hooks all before'); - await next(); - ctx.params.chain.push('@hooks all after'); - }]); + hooks(SimpleService.prototype, [ + async (ctx: HookContext, next: NextFunction) => { + ctx.params.chain.push('@hooks all before') + await next() + ctx.params.chain.push('@hooks all after') + } + ]) hooks(SimpleService, { - get: [async (ctx: HookContext, next: NextFunction) => { - assert.ok(ctx.app); - assert.ok(ctx.service); - ctx.params.chain.push('@hooks get before'); - await next(); - ctx.params.chain.push('@hooks get after'); - }] - }); - - const app = feathers().use('/dummy', new SimpleService()); - const service = app.service('dummy'); - - app.hooks([async function appHook (ctx: HookContext, next: NextFunction) { - assert.ok(ctx.app); - assert.ok(ctx.service); - - ctx.params.chain = [ 'app.hooks before']; - await next(); - ctx.params.chain.push('app.hooks after'); - }]); + get: [ + async (ctx: HookContext, next: NextFunction) => { + assert.ok(ctx.app) + assert.ok(ctx.service) + ctx.params.chain.push('@hooks get before') + await next() + ctx.params.chain.push('@hooks get after') + } + ] + }) + + const app = feathers().use('/dummy', new SimpleService()) + const service = app.service('dummy') + + app.hooks([ + async function appHook(ctx: HookContext, next: NextFunction) { + assert.ok(ctx.app) + assert.ok(ctx.service) + + ctx.params.chain = ['app.hooks before'] + await next() + ctx.params.chain.push('app.hooks after') + } + ]) app.hooks({ - before: [(ctx: HookContext) => { - ctx.params.chain.push('app.hooks regular before'); - }], - after: [(ctx: HookContext) => { - ctx.params.chain.push('app.hooks regular after'); - }] - }); + before: [ + (ctx: HookContext) => { + ctx.params.chain.push('app.hooks regular before') + } + ], + after: [ + (ctx: HookContext) => { + ctx.params.chain.push('app.hooks regular after') + } + ] + }) service.hooks({ before: { get: (ctx: HookContext) => { - ctx.params.chain.push('service.hooks regular before'); + ctx.params.chain.push('service.hooks regular before') } }, after: { get: (ctx: HookContext) => { - ctx.params.chain.push('service.hooks regular after'); + ctx.params.chain.push('service.hooks regular after') } } - }); + }) service.hooks({ - get: [async (ctx: HookContext, next: NextFunction) => { - ctx.params.chain.push('service.hooks get before'); - await next(); - ctx.params.chain.push('service.hooks get after'); - }] - }); + get: [ + async (ctx: HookContext, next: NextFunction) => { + ctx.params.chain.push('service.hooks get before') + await next() + ctx.params.chain.push('service.hooks get after') + } + ] + }) service.hooks({ before: { get: (ctx: HookContext) => { - ctx.params.chain.push('service.hooks 2 regular before'); + ctx.params.chain.push('service.hooks 2 regular before') } }, after: { get: (ctx: HookContext) => { - ctx.params.chain.push('service.hooks 2 regular after'); + ctx.params.chain.push('service.hooks 2 regular after') } } - }); + }) - const { chain } = await service.get(1, {}); + const { chain } = await service.get(1, {}) assert.deepStrictEqual(chain, [ 'app.hooks before', @@ -99,7 +114,7 @@ describe('hooks basics', () => { 'app.hooks regular after', 'app.hooks after' ]) - }); + }) // it('validates arguments', async () => { // const app = feathers().use('/dummy', { @@ -121,122 +136,125 @@ describe('hooks basics', () => { // }); it('works with services that return a promise (feathers-hooks#28)', async () => { - const app = feathers().use('/dummy', { - async get (id: any, params: any) { - return { id, user: params.user }; + interface DummyParams extends Params { + user: string + } + + const app = feathers<{ dummy: ServiceInterface }>().use('dummy', { + async get(id: any, params: any) { + return { id, user: params.user } } - }); - const service = app.service('dummy'); + }) + const service = app.service('dummy') service.hooks({ before: { - get (context) { - context.params.user = 'David'; + get(context) { + context.params.user = 'David' } }, after: { - get (context) { - context.result.after = true; + get(context) { + context.result.after = true } } - }); + }) - const data = await service.get(10); + const data = await service.get(10) - assert.deepStrictEqual(data, { id: 10, user: 'David', after: true }); - }); + assert.deepStrictEqual(data, { id: 10, user: 'David', after: true }) + }) it('has context.app, context.service and context.path', async () => { const app = feathers().use('/dummy', { - async get (id: any) { - return { id }; + async get(id: any) { + return { id } } - }); - const service = app.service('dummy'); + }) + const service = app.service('dummy') service.hooks({ - before (context) { - assert.strictEqual(this, service); - assert.strictEqual(context.service, service); - assert.strictEqual(context.app, app); - assert.strictEqual(context.path, 'dummy'); + before(context) { + assert.strictEqual(this, service) + assert.strictEqual(context.service, service) + assert.strictEqual(context.app, app) + assert.strictEqual(context.path, 'dummy') } - }); + }) - await service.get('test'); - }); + await service.get('test') + }) it('does not error when result is null', async () => { const app = feathers().use('/dummy', { - async get (id: any) { - return { id }; + async get(id: any) { + return { id } } - }); - const service = app.service('dummy'); + }) + const service = app.service('dummy') service.hooks({ after: { get: [ function (context) { - context.result = null; - return context; + context.result = null + return context } ] } - }); - - const result = await service.get(1); + }) - assert.strictEqual(result, null); - }); + const result = await service.get(1) + assert.strictEqual(result, null) + }) it('registering an already hooked service works (#154)', () => { const app = feathers().use('/dummy', { - async get (id: any, params: any) { - return { id, params }; + async get(id: any, params: any) { + return { id, params } } - }); + }) - app.use('/dummy2', app.service('dummy')); - }); + app.use('/dummy2', app.service('dummy')) + }) describe('returns the context when passing it as last parameter', () => { it('on normal method call', async () => { const app = feathers().use('/dummy', { - async get (id: any, params: any) { - return { id, params }; + async get(id: any, params: any) { + return { id, params } } - }); - const service = app.service('dummy'); - const context = createContext(service, 'get'); - const returnedContext = await app.service('dummy').get(10, {}, context); - - assert.strictEqual(returnedContext.service, app.service('dummy')); - assert.strictEqual(returnedContext.type, null); - assert.strictEqual(returnedContext.path, 'dummy'); + }) + const service = app.service('dummy') + const context = createContext(service, 'get') + const returnedContext = await app.service('dummy').get(10, {}, context) + + assert.strictEqual(returnedContext.service, app.service('dummy')) + assert.strictEqual(returnedContext.type, null) + assert.strictEqual(returnedContext.path, 'dummy') assert.deepStrictEqual(returnedContext.result, { id: 10, params: {} - }); - }); + }) + }) it.skip('on error', async () => { const app = feathers().use('/dummy', { - get () { - throw new Error('Something went wrong'); + get() { + throw new Error('Something went wrong') } - }); + }) - const service = app.service('dummy'); - const context = createContext(service, 'get'); + const service = app.service('dummy') + const context = createContext(service, 'get') await assert.rejects(() => service.get(10, {}, context), { service: app.service('dummy'), type: null, path: 'dummy' - }); - }); + }) + }) // it('on argument validation error (https://github.com/feathersjs/express/issues/19)', async () => { // const app = feathers().use('/dummy', { @@ -281,115 +299,122 @@ describe('hooks basics', () => { // }); it('still swallows error if context.result is set', async () => { - const result = { message: 'this is a test' }; + const result = { message: 'this is a test' } const app = feathers().use('/dummy', { - async get () { - throw new Error('Something went wrong'); + async get() { + throw new Error('Something went wrong') } - }); + }) app.service('dummy').hooks({ - error (context: any) { - context.result = result; + error(context: any) { + context.result = result } - }); + }) - const service = app.service('dummy'); - const context = createContext(service, 'get'); - const returnedContext = await service.get(10, {}, context); + const service = app.service('dummy') + const context = createContext(service, 'get') + const returnedContext = await service.get(10, {}, context) - assert.ok(returnedContext.error); - assert.deepStrictEqual(returnedContext.result, result); - }); - }); + assert.ok(returnedContext.error) + assert.deepStrictEqual(returnedContext.result, result) + }) + }) it('can register hooks on a custom method, still adds hooks to default methods', async () => { class Dummy { - async get (id: Id) { - return { id }; + async get(id: Id) { + return { id } } - async create (data: any) { - return data; + async create(data: any) { + return data } - async custom (data: any) { - return data; + async custom(data: any) { + return data } } const app = feathers<{ dummy: Dummy }>().use('dummy', new Dummy(), { - methods: [ 'get', 'custom' ] - }); + methods: ['get', 'custom'] + }) app.service('dummy').hooks({ - custom: [async (context, next) => { - context.data.fromHook = true; - await next(); - }], + custom: [ + async (context, next) => { + context.data.fromHook = true + await next() + } + ], create: [async (_context, next) => next()] - }); - - assert.deepStrictEqual(await app.service('dummy').custom({ - message: 'testing' - }), { - message: 'testing', - fromHook: true - }); - }); + }) + + assert.deepStrictEqual( + await app.service('dummy').custom({ + message: 'testing' + }), + { + message: 'testing', + fromHook: true + } + ) + }) it('normalizes params to object even when it is falsy (#1001)', async () => { const app = feathers().use('/dummy', { - async get (id: Id, params: Params) { - return { id, params }; + async get(id: Id, params: Params) { + return { id, params } } - }); + }) - const result = await app.service('dummy').get('test', null); + const result = await app.service('dummy').get('test', null) assert.deepStrictEqual(result, { id: 'test', params: {} - }); - }); + }) + }) it('allows to return new context in basic hooks (#2451)', async () => { const app = feathers().use('/dummy', { - async get () { - return {}; + async get() { + return {} } - }); - const service = app.service('dummy'); + }) + const service = app.service('dummy') service.hooks({ before: { get: [ - context => { + (context) => { return { ...context, value: 'something' - }; + } }, - context => { - assert.strictEqual(context.value, 'something'); + (context) => { + assert.strictEqual(context.value, 'something') } ] }, after: { - get: [context => { - context.result = { - value: context.value + get: [ + (context) => { + context.result = { + value: context.value + } } - }] + ] } - }); + }) - const data = await service.get(10); + const data = await service.get(10) assert.deepStrictEqual(data, { value: 'something' - }); - }); -}); + }) + }) +}) diff --git a/packages/feathers/tsconfig.json b/packages/feathers/tsconfig.json index 316fd41336..b184375928 100644 --- a/packages/feathers/tsconfig.json +++ b/packages/feathers/tsconfig.json @@ -4,6 +4,6 @@ "src/**/*.ts" ], "compilerOptions": { - "outDir": "lib" + "outDir": "lib" } } diff --git a/packages/knex/CHANGELOG.md b/packages/knex/CHANGELOG.md new file mode 100644 index 0000000000..6955f7de4c --- /dev/null +++ b/packages/knex/CHANGELOG.md @@ -0,0 +1,48 @@ +# Change Log + +All notable changes to this project will be documented in this file. +See [Conventional Commits](https://conventionalcommits.org) for commit guidelines. + +# [5.0.0-pre.31](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.30...v5.0.0-pre.31) (2022-10-12) + +### Features + +- **cli:** Generate full client test suite and improve typed client ([#2788](https://github.com/feathersjs/feathers/issues/2788)) ([57119b6](https://github.com/feathersjs/feathers/commit/57119b6bb2797f7297cf054268a248c093ecd538)) +- **cli:** Improve generated schema definitions ([#2783](https://github.com/feathersjs/feathers/issues/2783)) ([474a9fd](https://github.com/feathersjs/feathers/commit/474a9fda2107e9bcf357746320a8e00cda8182b6)) + +# [5.0.0-pre.30](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.29...v5.0.0-pre.30) (2022-10-07) + +### Features + +- **core:** Allow to unregister services at runtime ([#2756](https://github.com/feathersjs/feathers/issues/2756)) ([d16601f](https://github.com/feathersjs/feathers/commit/d16601f2277dca5357866ffdefba2a611f6dc7fa)) + +# [5.0.0-pre.29](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.28...v5.0.0-pre.29) (2022-09-16) + +**Note:** Version bump only for package @feathersjs/knex + +# [5.0.0-pre.28](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.27...v5.0.0-pre.28) (2022-08-03) + +### Bug Fixes + +- **cli:** Improve generated application and client ([#2701](https://github.com/feathersjs/feathers/issues/2701)) ([bd55ffb](https://github.com/feathersjs/feathers/commit/bd55ffb812e89bf215f4515e7f137656ea888c3f)) +- **knex:** Fix PostgreSQL integration issues and run CI tests against pg ([#2698](https://github.com/feathersjs/feathers/issues/2698)) ([1f71d78](https://github.com/feathersjs/feathers/commit/1f71d7884656c1494004931f4979ad59d23e4ee6)) + +# [5.0.0-pre.27](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.26...v5.0.0-pre.27) (2022-07-13) + +**Note:** Version bump only for package @feathersjs/knex + +# [5.0.0-pre.26](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.25...v5.0.0-pre.26) (2022-06-22) + +**Note:** Version bump only for package @feathersjs/knex + +# [5.0.0-pre.25](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.24...v5.0.0-pre.25) (2022-06-22) + +### Bug Fixes + +- **cli:** Generator fixes to work with the new guide ([#2674](https://github.com/feathersjs/feathers/issues/2674)) ([b773fa5](https://github.com/feathersjs/feathers/commit/b773fa5dbd7ff450cfb2f7b93e64882592262712)) + +# [5.0.0-pre.24](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.23...v5.0.0-pre.24) (2022-06-21) + +### Features + +- **knex:** Add KnexJS SQL database adapter to core ([#2671](https://github.com/feathersjs/feathers/issues/2671)) ([9380fff](https://github.com/feathersjs/feathers/commit/9380fff58596e8bb90b8bb098d2795b7eadfec20)) diff --git a/packages/knex/LICENSE b/packages/knex/LICENSE new file mode 100644 index 0000000000..59604f46f3 --- /dev/null +++ b/packages/knex/LICENSE @@ -0,0 +1,22 @@ +The MIT License (MIT) + +Copyright (c) 2022 Feathers + +Permission is hereby granted, free of charge, to any person obtaining a copy +of this software and associated documentation files (the "Software"), to deal +in the Software without restriction, including without limitation the rights +to use, copy, modify, merge, publish, distribute, sublicense, and/or sell +copies of the Software, and to permit persons to whom the Software is +furnished to do so, subject to the following conditions: + +The above copyright notice and this permission notice shall be included in all +copies or substantial portions of the Software. + +THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE +AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, +OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE +SOFTWARE. + diff --git a/packages/knex/README.md b/packages/knex/README.md new file mode 100644 index 0000000000..4e9adac6a5 --- /dev/null +++ b/packages/knex/README.md @@ -0,0 +1,22 @@ +# @feathersjs/knex + +[![CI](https://github.com/feathersjs/feathers/workflows/CI/badge.svg)](https://github.com/feathersjs/feathers/actions?query=workflow%3ACI) +[![Download Status](https://img.shields.io/npm/dm/@feathersjs/mongodb.svg?style=flat-square)](https://www.npmjs.com/package/@feathersjs/mongodb) + +> Feathers SQL service adapter using KnexJS + +## Installation + +``` +npm install @feathersjs/knex --save +``` + +## Documentation + +Refer to the [Feathers documentation](https://docs.feathersjs.com) for more details. + +## License + +Copyright (c) 2022 [Feathers contributors](https://github.com/feathersjs/feathers/graphs/contributors) + +Licensed under the [MIT license](LICENSE). diff --git a/packages/knex/package.json b/packages/knex/package.json new file mode 100644 index 0000000000..2a73adcd38 --- /dev/null +++ b/packages/knex/package.json @@ -0,0 +1,74 @@ +{ + "name": "@feathersjs/knex", + "description": "Feathers SQL service adapter using KnexJS", + "version": "5.0.0-pre.31", + "homepage": "https://feathersjs.com", + "main": "lib/", + "keywords": [ + "feathers", + "feathers-plugin" + ], + "license": "MIT", + "funding": { + "type": "github", + "url": "https://github.com/sponsors/daffl" + }, + "repository": { + "type": "git", + "url": "git://github.com/feathersjs/feathers.git" + }, + "author": { + "name": "Feathers contributors", + "email": "hello@feathersjs.com", + "url": "https://feathersjs.com" + }, + "contributors": [], + "bugs": { + "url": "https://github.com/feathersjs/feathers/issues" + }, + "engines": { + "node": ">= 14" + }, + "files": [ + "CHANGELOG.md", + "LICENSE", + "README.md", + "src/**", + "lib/**", + "*.d.ts", + "*.js" + ], + "scripts": { + "prepublish": "npm run compile", + "pack": "npm pack --pack-destination ../cli/test/build", + "compile": "shx rm -rf lib/ && tsc && npm run pack", + "test": "mocha --config ../../.mocharc.json --recursive test/**.test.ts test/**/*.test.ts" + }, + "directories": { + "lib": "lib" + }, + "publishConfig": { + "access": "public" + }, + "dependencies": { + "@feathersjs/adapter-commons": "^5.0.0-pre.31", + "@feathersjs/commons": "^5.0.0-pre.31", + "@feathersjs/errors": "^5.0.0-pre.31", + "@feathersjs/feathers": "^5.0.0-pre.31" + }, + "peerDependencies": { + "knex": "^2.3.0" + }, + "devDependencies": { + "@feathersjs/adapter-tests": "^5.0.0-pre.31", + "@types/mocha": "^10.0.0", + "@types/node": "^18.8.2", + "knex": "^2.3.0", + "mocha": "^10.0.0", + "pg": "^8.8.0", + "shx": "^0.3.4", + "sqlite3": "^5.1.2", + "typescript": "^4.8.4" + }, + "gitHead": "4500dbeb8cea566678cf88b3313a88efd93a2ed9" +} diff --git a/packages/knex/src/adapter.ts b/packages/knex/src/adapter.ts new file mode 100644 index 0000000000..bb99b25ffe --- /dev/null +++ b/packages/knex/src/adapter.ts @@ -0,0 +1,318 @@ +import { Id, NullableId, Paginated, Query } from '@feathersjs/feathers' +import { _ } from '@feathersjs/commons' +import { AdapterBase, PaginationOptions, filterQuery } from '@feathersjs/adapter-commons' +import { NotFound } from '@feathersjs/errors' +import { Knex } from 'knex' + +import { errorHandler } from './error-handler' +import { KnexAdapterOptions, KnexAdapterParams } from './declarations' +const METHODS = { + $ne: 'whereNot', + $in: 'whereIn', + $nin: 'whereNotIn', + $or: 'orWhere', + $and: 'andWhere' +} + +const OPERATORS = { + $lt: '<', + $lte: '<=', + $gt: '>', + $gte: '>=', + $like: 'like', + $notlike: 'not like', + $ilike: 'ilike' +} + +const RETURNING_CLIENTS = ['postgresql', 'pg', 'oracledb', 'mssql'] + +export class KnexAdapter< + T, + D = Partial, + P extends KnexAdapterParams = KnexAdapterParams +> extends AdapterBase { + table: string + schema?: string + + constructor(options: KnexAdapterOptions) { + if (!options || !options.Model) { + throw new Error('You must provide a Model (the initialized knex object)') + } + + if (typeof options.name !== 'string') { + throw new Error('No table name specified.') + } + + super({ + id: 'id', + ...options, + filters: { + ...options.filters, + $and: (value: any) => value + }, + operators: [...(options.operators || []), '$like', '$notlike', '$ilike', '$and', '$or'] + }) + + this.table = options.name + this.schema = options.schema + } + + get Model() { + return this.options.Model + } + + get fullName() { + return this.schema ? `${this.schema}.${this.table}` : this.table + } + + db(params?: P) { + const { Model, table, schema } = this + + if (params && params.transaction && params.transaction.trx) { + const { trx } = params.transaction + // debug('ran %s with transaction %s', fullName, id) + return schema ? (trx.withSchema(schema).table(table) as Knex.QueryBuilder) : trx(table) + } + return schema ? (Model.withSchema(schema).table(table) as Knex.QueryBuilder) : Model(table) + } + + knexify(knexQuery: Knex.QueryBuilder, query: Query = {}, parentKey?: string): Knex.QueryBuilder { + const knexify = this.knexify.bind(this) + + return Object.keys(query || {}).reduce((currentQuery, key) => { + const value = query[key] + + if (_.isObject(value)) { + return knexify(currentQuery, value, key) + } + + const column = parentKey || key + const method = METHODS[key as keyof typeof METHODS] + + if (method) { + if (key === '$or' || key === '$and') { + // This will create a nested query + currentQuery.where(function (this: any) { + for (const condition of value) { + this[method](function (this: Knex.QueryBuilder) { + knexify(this, condition) + }) + } + }) + + return currentQuery + } + + return (currentQuery as any)[method](column, value) + } + + const operator = OPERATORS[key as keyof typeof OPERATORS] || '=' + + return operator === '=' + ? currentQuery.where(column, value) + : currentQuery.where(column, operator, value) + }, knexQuery) + } + + createQuery(params: P) { + const { table, id } = this + const { filters, query } = this.filterQuery(params) + const builder = this.db(params) + + // $select uses a specific find syntax, so it has to come first. + if (filters.$select) { + // always select the id field, but make sure we only select it once + builder.select(...new Set([...filters.$select, `${table}.${id}`])) + } else { + builder.select(`${table}.*`) + } + + // build up the knex query out of the query params, include $and and $or filters + this.knexify(builder, { + ...query, + ..._.pick(filters, '$and', '$or') + }) + + // Handle $sort + if (filters.$sort) { + return Object.keys(filters.$sort).reduce( + (currentQuery, key) => currentQuery.orderBy(key, filters.$sort[key] === 1 ? 'asc' : 'desc'), + builder + ) + } + + return builder + } + + filterQuery(params: P) { + const options = this.getOptions(params) + const { filters, query } = filterQuery(params?.query || {}, options) + + return { filters, query, paginate: options.paginate } + } + + async $find(params?: P & { paginate?: PaginationOptions }): Promise> + async $find(params?: P & { paginate: false }): Promise + async $find(params?: P): Promise | T[]> + async $find(params: P = {} as P): Promise | T[]> { + const { filters, paginate } = this.filterQuery(params) + const builder = params.knex ? params.knex.clone() : this.createQuery(params) + const countBuilder = builder.clone().clearSelect().clearOrder().count(`${this.table}.${this.id} as total`) + + // Handle $limit + if (filters.$limit) { + builder.limit(filters.$limit) + } + + // Handle $skip + if (filters.$skip) { + builder.offset(filters.$skip) + } + + // provide default sorting if its not set + if (!filters.$sort) { + builder.orderBy(`${this.table}.${this.id}`, 'asc') + } + + const data = filters.$limit === 0 ? [] : await builder.catch(errorHandler) + + if (paginate && paginate.default) { + const total = await countBuilder.then((count) => parseInt(count[0] ? count[0].total : 0)) + + return { + total, + limit: filters.$limit, + skip: filters.$skip || 0, + data + } + } + + return data + } + + async _findOrGet(id: NullableId, params?: P) { + const findParams = { + ...params, + paginate: false, + query: { + ...params?.query, + ...(id !== null ? { [`${this.table}.${this.id}`]: id } : {}) + } + } + + return this.$find(findParams as any) as any as Promise + } + + async $get(id: Id, params: P = {} as P): Promise { + const data = await this._findOrGet(id, params) + + if (data.length !== 1) { + throw new NotFound(`No record found for id '${id}'`) + } + + return data[0] + } + + async $create(data: D, params?: P): Promise + async $create(data: D[], params?: P): Promise + async $create(data: D | D[], _params?: P): Promise + async $create(_data: D | D[], params: P = {} as P): Promise { + const data = _data as any + + if (Array.isArray(data)) { + return Promise.all(data.map((current) => this.$create(current, params))) + } + + const client = this.db(params).client.config.client + const returning = RETURNING_CLIENTS.includes(client as string) ? [this.id] : [] + const rows: any = await this.db(params).insert(data, returning).catch(errorHandler) + const id = data[this.id] || rows[0][this.id] || rows[0] + + if (!id) { + return rows as T[] + } + + return this.$get(id, params) + } + + async $patch(id: null, data: Partial, params?: P): Promise + async $patch(id: Id, data: Partial, params?: P): Promise + async $patch(id: NullableId, data: Partial, _params?: P): Promise + async $patch(id: NullableId, raw: Partial, params: P = {} as P): Promise { + const data = _.omit(raw, this.id) + const results = await this._findOrGet(id, { + ...params, + query: { + ...params?.query, + $select: [`${this.table}.${this.id}`] + } + }) + const idList = results.map((current: any) => current[this.id]) + const updateParams = { + ...params, + query: { + [`${this.table}.${this.id}`]: { $in: idList }, + ...(params?.query?.$select ? { $select: params?.query?.$select } : {}) + } + } + const builder = this.createQuery(updateParams) + + await builder.update(data) + + const items = await this._findOrGet(null, updateParams) + + if (id !== null) { + if (items.length === 1) { + return items[0] + } else { + throw new NotFound(`No record found for id '${id}'`) + } + } + + return items + } + + async $update(id: Id, _data: D, params: P = {} as P): Promise { + const data = _.omit(_data, this.id) + const oldData = await this.$get(id, params) + const newObject = Object.keys(oldData).reduce((result: any, key) => { + if (key !== this.id) { + // We don't want the id field to be changed + result[key] = data[key] === undefined ? null : data[key] + } + + return result + }, {}) + + await this.db(params).update(newObject, '*').where(this.id, id) + + return this.$get(id, params) + } + + async $remove(id: null, params?: P): Promise + async $remove(id: Id, params?: P): Promise + async $remove(id: NullableId, _params?: P): Promise + async $remove(id: NullableId, params: P = {} as P): Promise { + const items = await this._findOrGet(id, params) + const { query } = this.filterQuery(params) + const q = this.db(params) + const idList = items.map((current: any) => current[this.id]) + + query[this.id] = { $in: idList } + + // build up the knex query out of the query params + this.knexify(q, query) + + await q.del().catch(errorHandler) + + if (id !== null) { + if (items.length === 1) { + return items[0] + } + + throw new NotFound(`No record found for id '${id}'`) + } + + return items + } +} diff --git a/packages/knex/src/declarations.ts b/packages/knex/src/declarations.ts new file mode 100644 index 0000000000..4e30ba6a0a --- /dev/null +++ b/packages/knex/src/declarations.ts @@ -0,0 +1,23 @@ +import { Knex } from 'knex' +import { AdapterServiceOptions, AdapterParams, AdapterQuery } from '@feathersjs/adapter-commons' + +export interface KnexAdapterOptions extends AdapterServiceOptions { + Model: Knex + name: string + schema?: string +} + +export interface KnexAdapterTransaction { + starting: boolean + parent?: KnexAdapterTransaction + committed?: any + resolve?: any + trx?: Knex.Transaction + id?: number + promise?: Promise +} + +export interface KnexAdapterParams extends AdapterParams> { + knex?: Knex.QueryBuilder + transaction?: KnexAdapterTransaction +} diff --git a/packages/knex/src/error-handler.ts b/packages/knex/src/error-handler.ts new file mode 100644 index 0000000000..97ec4873a6 --- /dev/null +++ b/packages/knex/src/error-handler.ts @@ -0,0 +1,97 @@ +import { errors } from '@feathersjs/errors' + +export const ERROR = Symbol('@feathersjs/knex/error') + +export function errorHandler(error: any) { + const { message } = error + let feathersError = error + + if (error.sqlState && error.sqlState.length) { + // remove SQLSTATE marker (#) and pad/truncate SQLSTATE to 5 chars + const sqlState = ('00000' + error.sqlState.replace('#', '')).slice(-5) + + switch (sqlState.slice(0, 2)) { + case '02': + feathersError = new errors.NotFound(message) + break + case '28': + feathersError = new errors.Forbidden(message) + break + case '08': + case '0A': + case '0K': + feathersError = new errors.Unavailable(message) + break + case '20': + case '21': + case '22': + case '23': + case '24': + case '25': + case '40': + case '42': + case '70': + feathersError = new errors.BadRequest(message) + break + default: + feathersError = new errors.GeneralError(message) + } + } else if (error.code === 'SQLITE_ERROR') { + // NOTE (EK): Error codes taken from + // https://www.sqlite.org/c3ref/c_abort.html + switch (error.errno) { + case 1: + case 8: + case 18: + case 19: + case 20: + feathersError = new errors.BadRequest(message) + break + case 2: + feathersError = new errors.Unavailable(message) + break + case 3: + case 23: + feathersError = new errors.Forbidden(message) + break + case 12: + feathersError = new errors.NotFound(message) + break + default: + feathersError = new errors.GeneralError(message) + break + } + } else if (typeof error.code === 'string' && error.severity && error.routine) { + // NOTE: Error codes taken from + // https://www.postgresql.org/docs/9.6/static/errcodes-appendix.html + // Omit query information + const messages = error.message.split('-') + error.message = messages[messages.length - 1] + + switch (error.code.slice(0, 2)) { + case '22': + feathersError = new errors.NotFound(message) + break + case '23': + feathersError = new errors.BadRequest(message) + break + case '28': + feathersError = new errors.Forbidden(message) + break + case '3D': + case '3F': + case '42': + feathersError = new errors.Unprocessable(message) + break + default: + feathersError = new errors.GeneralError(message) + break + } + } else if (!(error instanceof errors.FeathersError)) { + feathersError = new errors.GeneralError(message) + } + + feathersError[ERROR] = error + + throw feathersError +} diff --git a/packages/knex/src/hooks.ts b/packages/knex/src/hooks.ts new file mode 100644 index 0000000000..1ef169570c --- /dev/null +++ b/packages/knex/src/hooks.ts @@ -0,0 +1,101 @@ +import { createDebug } from '@feathersjs/commons' +import { HookContext } from '@feathersjs/feathers' +import { Knex } from 'knex' +import { KnexAdapterTransaction } from './declarations' + +const debug = createDebug('feathers-knex-transaction') + +const ROLLBACK = { rollback: true } + +export const getKnex = (context: HookContext): Knex => { + const knex = context.service.Model + + return knex && typeof knex.transaction === 'function' ? knex : undefined +} + +export const start = + () => + async (context: HookContext): Promise => { + const { transaction } = context.params + const parent = transaction + const knex: Knex = transaction ? transaction.trx : getKnex(context) + + if (!knex) { + return + } + + return new Promise((resolve, reject) => { + const transaction: KnexAdapterTransaction = { + starting: true + } + + if (parent) { + transaction.parent = parent + transaction.committed = parent.committed + } else { + transaction.committed = new Promise((resolve) => { + transaction.resolve = resolve + }) + } + + transaction.starting = true + transaction.promise = knex + .transaction((trx) => { + transaction.trx = trx + transaction.id = Date.now() + + context.params = { ...context.params, transaction } + + debug('started a new transaction %s', transaction.id) + + resolve() + }) + .catch((error) => { + if (transaction.starting) { + reject(error) + } else if (error !== ROLLBACK) { + throw error + } + }) + }) + } + +export const end = () => (context: HookContext) => { + const { transaction } = context.params + + if (!transaction) { + return + } + + const { trx, id, promise, parent } = transaction + + context.params = { ...context.params, transaction: parent } + transaction.starting = false + + return trx + .commit() + .then(() => promise) + .then(() => transaction.resolve && transaction.resolve(true)) + .then(() => debug('ended transaction %s', id)) + .then(() => context) +} + +export const rollback = () => (context: HookContext) => { + const { transaction } = context.params + + if (!transaction) { + return + } + + const { trx, id, promise, parent } = transaction + + context.params = { ...context.params, transaction: parent } + transaction.starting = false + + return trx + .rollback(ROLLBACK) + .then(() => promise) + .then(() => transaction.resolve && transaction.resolve(false)) + .then(() => debug('rolled back transaction %s', id)) + .then(() => context) +} diff --git a/packages/knex/src/index.ts b/packages/knex/src/index.ts new file mode 100644 index 0000000000..2ff516207c --- /dev/null +++ b/packages/knex/src/index.ts @@ -0,0 +1,47 @@ +import { PaginationOptions } from '@feathersjs/adapter-commons' +import { Paginated, ServiceMethods, Id, NullableId, Params } from '@feathersjs/feathers' +import { KnexAdapter } from './adapter' +import { KnexAdapterParams } from './declarations' + +export * from './declarations' +export * from './adapter' +export * from './error-handler' +export * as transaction from './hooks' + +export class KnexService, P extends Params = KnexAdapterParams> + extends KnexAdapter + implements ServiceMethods, D, P> +{ + async find(params?: P & { paginate?: PaginationOptions }): Promise> + async find(params?: P & { paginate: false }): Promise + async find(params?: P): Promise | T[]> + async find(params?: P): Promise | T[]> { + return this._find(params) as any + } + + async get(id: Id, params?: P): Promise { + return this._get(id, params) + } + + async create(data: D, params?: P): Promise + async create(data: D[], params?: P): Promise + async create(data: D | D[], params?: P): Promise { + return this._create(data, params) + } + + async update(id: Id, data: D, params?: P): Promise { + return this._update(id, data, params) + } + + async patch(id: Id, data: Partial, params?: P): Promise + async patch(id: null, data: Partial, params?: P): Promise + async patch(id: NullableId, data: Partial, params?: P): Promise { + return this._patch(id, data, params) + } + + async remove(id: Id, params?: P): Promise + async remove(id: null, params?: P): Promise + async remove(id: NullableId, params?: P): Promise { + return this._remove(id, params) + } +} diff --git a/packages/knex/test/connection.ts b/packages/knex/test/connection.ts new file mode 100644 index 0000000000..a471fa235b --- /dev/null +++ b/packages/knex/test/connection.ts @@ -0,0 +1,32 @@ +export default (DB: string) => { + if (DB === 'mysql') { + return { + client: 'mysql', + connection: { + host: '127.0.0.1', + user: 'root', + password: '', + database: 'feathers_knex' + } + } + } + + if (DB === 'postgres') { + return { + client: 'postgresql', + connection: { + host: 'localhost', + database: 'feathers', + user: 'postgres', + password: 'postgres' + } + } + } + + return { + client: 'sqlite3', + connection: { + filename: './db.sqlite' + } + } +} diff --git a/packages/knex/test/index.test.ts b/packages/knex/test/index.test.ts new file mode 100644 index 0000000000..c82820f316 --- /dev/null +++ b/packages/knex/test/index.test.ts @@ -0,0 +1,610 @@ +import knex, { Knex } from 'knex' +import assert from 'assert' +import { feathers, HookContext, Service } from '@feathersjs/feathers' +import adapterTests from '@feathersjs/adapter-tests' +import { errors } from '@feathersjs/errors' + +import connection from './connection' +import { KnexService, transaction } from '../src/index' + +const testSuite = adapterTests([ + '.options', + '.events', + '._get', + '._find', + '._create', + '._update', + '._patch', + '._remove', + '.$get', + '.$find', + '.$create', + '.$update', + '.$patch', + '.$remove', + '.get', + '.get + $select', + '.get + id + query', + '.get + NotFound', + '.get + id + query id', + '.find', + '.remove', + '.remove + $select', + '.remove + id + query', + '.remove + multi', + '.remove + multi no pagination', + '.remove + id + query id', + '.update', + '.update + $select', + '.update + id + query', + '.update + NotFound', + '.update + query + NotFound', + '.update + id + query id', + '.patch', + '.patch + $select', + '.patch + id + query', + '.patch multiple', + '.patch multiple no pagination', + '.patch multi query same', + '.patch multi query changed', + '.patch + NotFound', + '.patch + query + NotFound', + '.patch + id + query id', + '.create', + '.create + $select', + '.create multi', + 'internal .find', + 'internal .get', + 'internal .create', + 'internal .update', + 'internal .patch', + 'internal .remove', + '.find + equal', + '.find + equal multiple', + '.find + $sort', + '.find + $sort + string', + '.find + $limit', + '.find + $limit 0', + '.find + $skip', + '.find + $select', + '.find + $or', + '.find + $in', + '.find + $nin', + '.find + $lt', + '.find + $lte', + '.find + $gt', + '.find + $gte', + '.find + $ne', + '.find + $gt + $lt + $sort', + '.find + $or nested + $sort', + 'params.adapter + paginate', + 'params.adapter + multi', + '.find + paginate', + '.find + paginate + query', + '.find + paginate + $limit + $skip', + '.find + paginate + $limit 0', + '.find + paginate + params' +]) + +const TYPE = process.env.TEST_DB || 'sqlite' +const db = knex(connection(TYPE) as any) + +// Create a public database to mimic a "schema" +const schemaName = 'public' + +function clean() { + return Promise.all([ + db.schema.dropTableIfExists(people.fullName).then(() => { + return db.schema.createTable(people.fullName, (table) => { + table.increments('id') + table.string('name').notNullable() + table.integer('age') + table.integer('time') + table.boolean('created') + return table + }) + }), + db.schema.dropTableIfExists(peopleId.fullName).then(() => { + return db.schema.createTable(peopleId.fullName, (table) => { + table.increments('customid') + table.string('name') + table.integer('age') + table.integer('time') + table.boolean('created') + return table + }) + }), + db.schema.dropTableIfExists(users.fullName).then(() => { + return db.schema.createTable(users.fullName, (table) => { + table.increments('id') + table.string('name') + table.integer('age') + table.integer('time') + table.boolean('created') + return table + }) + }) + ]) +} + +type Person = { + id: number + name: string + age: number | null + time: string + create: boolean +} + +type ServiceTypes = { + people: KnexService + 'people-customid': KnexService + users: KnexService +} + +const people = new KnexService({ + Model: db, + name: 'people', + events: ['testing'] +}) + +const peopleId = new KnexService({ + Model: db, + id: 'customid', + name: 'people-customid', + events: ['testing'] +}) + +const users = new KnexService({ + Model: db, + name: 'users', + events: ['testing'] +}) + +describe('Feathers Knex Service', () => { + const app = feathers() + .hooks({ + before: [transaction.start()], + after: [transaction.end()], + error: [transaction.rollback()] + }) + .use('people', people) + .use('people-customid', peopleId) + .use('users', users) + const peopleService = app.service('people') + + before(() => { + if (TYPE === 'sqlite') { + // Attach the public database to mimic a "schema" + db.schema.raw(`attach database '${schemaName}.sqlite' as ${schemaName}`) + } + }) + before(clean) + after(clean) + + describe('$like method', () => { + let charlie: Person + + beforeEach(async () => { + charlie = await peopleService.create({ + name: 'Charlie Brown', + age: 10 + }) + }) + + afterEach(() => peopleService.remove(charlie.id)) + + it('$like in query', async () => { + const data = await peopleService.find({ + paginate: false, + query: { name: { $like: '%lie%' } } + }) + + assert.strictEqual(data[0].name, 'Charlie Brown') + }) + }) + + describe('$notlike method', () => { + let hasMatch: Person + let hasNoMatch: Person + + beforeEach(async () => { + hasMatch = await peopleService.create({ + name: 'XYZabcZYX' + }) + hasNoMatch = await peopleService.create({ + name: 'XYZZYX' + }) + }) + + afterEach(() => { + peopleService.remove(hasMatch.id) + peopleService.remove(hasNoMatch.id) + }) + + it('$notlike in query', async () => { + const data = await peopleService.find({ + paginate: false, + query: { name: { $notlike: '%abc%' } } + }) + + assert.strictEqual(data.length, 1) + assert.strictEqual(data[0].name, 'XYZZYX') + }) + }) + + describe('adapter specifics', () => { + let daves: Person[] + + beforeEach(async () => { + daves = await Promise.all([ + peopleService.create({ + name: 'Ageless', + age: null + }), + peopleService.create({ + name: 'Dave', + age: 32 + }), + peopleService.create({ + name: 'Dada', + age: 1 + }) + ]) + }) + + afterEach(async () => { + try { + await peopleService.remove(daves[0].id) + await peopleService.remove(daves[1].id) + await peopleService.remove(daves[2].id) + } catch (error: unknown) {} + }) + + it('$or works properly (#120)', async () => { + const data = await peopleService.find({ + paginate: false, + query: { + name: 'Dave', + $or: [ + { + age: 1 + }, + { + age: 32 + } + ] + } + }) + + assert.strictEqual(data.length, 1) + assert.strictEqual(data[0].name, 'Dave') + assert.strictEqual(data[0].age, 32) + }) + + it('$and works properly', async () => { + const data = await peopleService.find({ + paginate: false, + query: { + $and: [ + { + $or: [{ name: 'Dave' }, { name: 'Dada' }] + }, + { + age: { $lt: 23 } + } + ] + } + }) + + assert.strictEqual(data.length, 1) + assert.strictEqual(data[0].name, 'Dada') + assert.strictEqual(data[0].age, 1) + }) + + it('where conditions support NULL values properly', async () => { + const data = await peopleService.find({ + paginate: false, + query: { + age: null + } + }) + + assert.strictEqual(data.length, 1) + assert.strictEqual(data[0].name, 'Ageless') + assert.strictEqual(data[0].age, null) + }) + + it('where conditions support NOT NULL case properly', async () => { + const data = await peopleService.find({ + paginate: false, + query: { + age: { $ne: null } + } + }) + + assert.strictEqual(data.length, 2) + assert.notStrictEqual(data[0].name, 'Ageless') + assert.notStrictEqual(data[0].age, null) + assert.notStrictEqual(data[1].name, 'Ageless') + assert.notStrictEqual(data[1].age, null) + }) + + it('where conditions support NULL values within AND conditions', async () => { + const data = await peopleService.find({ + paginate: false, + query: { + age: null, + name: 'Ageless' + } + }) + + assert.strictEqual(data.length, 1) + assert.strictEqual(data[0].name, 'Ageless') + assert.strictEqual(data[0].age, null) + }) + + it('where conditions support NULL values within OR conditions', async () => { + const data = await peopleService.find({ + paginate: false, + query: { + $or: [ + { + age: null + }, + { + name: 'Dada' + } + ] + } + }) + + assert.strictEqual(data.length, 2) + assert.notStrictEqual(data[0].name, 'Dave') + assert.notStrictEqual(data[0].age, 32) + assert.notStrictEqual(data[1].name, 'Dave') + assert.notStrictEqual(data[1].age, 32) + }) + + it('attaches the SQL error', async () => { + await assert.rejects(() => peopleService.create({})) + }) + }) + + describe('hooks', () => { + afterEach(async () => { + await db('people').truncate() + }) + + it('does reject on problem with commit', async () => { + const app = feathers() + + app.hooks({ + before: transaction.start(), + after: [ + (context: HookContext) => { + const client = context.params.transaction.trx.client + const query = client.query + + client.query = (conn: any, sql: any) => { + let result = query.call(client, conn, sql) + + if (sql === 'COMMIT;') { + result = result.then(() => { + throw new TypeError('Deliberate') + }) + } + + return result + } + }, + transaction.end() + ], + error: transaction.rollback() + }) + + app.use('/people', people) + + await assert.rejects(() => app.service('/people').create({ name: 'Foo' }), { + message: 'Deliberate' + }) + }) + + it('does commit, rollback, nesting', async () => { + const app = feathers<{ + people: typeof people + test: Pick & { Model: Knex } + }>() + + app.hooks({ + before: transaction.start(), + after: transaction.end(), + error: transaction.rollback() + }) + + app.use('people', people) + + app.use('test', { + Model: db, + create: async (data: any, params) => { + const created = await app.service('people').create({ name: 'Foo' }, { ...params }) + + if (data.throw) { + throw new TypeError('Deliberate') + } + + return created + } + }) + + await assert.rejects(() => app.service('test').create({ throw: true }), { + message: 'Deliberate' + }) + + assert.strictEqual((await app.service('people').find({ paginate: false })).length, 0) + + await app.service('test').create({}) + + assert.strictEqual((await app.service('people').find({ paginate: false })).length, 1) + }) + + it('does use savepoints for nested calls', async () => { + const app = feathers<{ + people: typeof people + success: Pick & { Model: Knex } + fail: Pick & { Model: Knex } + test: Pick & { Model: Knex } + }>() + + app.hooks({ + before: transaction.start(), + after: transaction.end(), + error: transaction.rollback() + }) + + app.use('people', people) + + app.use('success', { + Model: db, + create: async (_data, params) => { + return app.service('people').create({ name: 'Success' }, { ...params }) + } + }) + + app.use('fail', { + Model: db, + create: async (_data, params) => { + await app.service('people').create({ name: 'Fail' }, { ...params }) + throw new TypeError('Deliberate') + } + }) + + app.use('test', { + Model: db, + create: async (_data, params) => { + await app.service('success').create({}, { ...params }) + await app + .service('fail') + .create({}, { ...params }) + // eslint-disable-next-line @typescript-eslint/no-empty-function + .catch(() => {}) + return [] + } + }) + + await app.service('test').create({}) + + const created = await app.service('people').find({ paginate: false }) + + assert.strictEqual(created.length, 1) + assert.ok(created[0].name) + }) + + it('allows waiting for transaction to complete', async () => { + const app = feathers<{ + people: typeof people + test: Pick & { Model: Knex } + }>() + + let seq: string[] = [] + + app.hooks({ + before: [ + transaction.start(), + (context: HookContext) => { + seq.push(`${context.path}: waiting for trx to be committed`) + context.params.transaction.committed.then((success: any) => { + seq.push(`${context.path}: committed ${success}`) + }) + }, + async (context: HookContext) => { + seq.push(`${context.path}: another hook`) + } + ], + after: [ + transaction.end(), + (context: HookContext) => { + seq.push(`${context.path}: trx ended`) + } + ], + error: [ + transaction.rollback(), + (context: HookContext) => { + seq.push(`${context.path}: trx rolled back`) + } + ] + }) + + app.use('people', people) + + app.use('test', { + Model: db, + create: async (data: any, params) => { + const peeps = await app.service('people').create({ name: 'Foo' }, { ...params }) + + if (data.throw) { + throw new TypeError('Deliberate') + } + return peeps + } + }) + + assert.deepStrictEqual(seq, []) + + await assert.rejects(() => app.service('test').create({ throw: true }), { + message: 'Deliberate' + }) + + assert.deepStrictEqual(seq, [ + 'test: waiting for trx to be committed', + 'test: another hook', + 'people: waiting for trx to be committed', + 'people: another hook', + 'people: trx ended', + 'test: committed false', + 'people: committed false', + 'test: trx rolled back' + ]) + + seq = [] + + assert.strictEqual((await app.service('people').find({ paginate: false })).length, 0) + + assert.deepStrictEqual(seq, [ + 'people: waiting for trx to be committed', + 'people: another hook', + 'people: committed true', + 'people: trx ended' + ]) + + seq = [] + + await app.service('test').create({}) + + assert.deepStrictEqual(seq, [ + 'test: waiting for trx to be committed', + 'test: another hook', + 'people: waiting for trx to be committed', + 'people: another hook', + 'people: trx ended', + 'test: committed true', + 'people: committed true', + 'test: trx ended' + ]) + + seq = [] + + assert.strictEqual((await app.service('people').find({ paginate: false })).length, 1) + + assert.deepStrictEqual(seq, [ + 'people: waiting for trx to be committed', + 'people: another hook', + 'people: committed true', + 'people: trx ended' + ]) + }) + }) + + testSuite(app, errors, 'users') + testSuite(app, errors, 'people') + testSuite(app, errors, 'people-customid', 'customid') +}) diff --git a/packages/knex/test/overrides.test.ts b/packages/knex/test/overrides.test.ts new file mode 100644 index 0000000000..076dc3c6b4 --- /dev/null +++ b/packages/knex/test/overrides.test.ts @@ -0,0 +1,125 @@ +import knex from 'knex' +import assert from 'assert' +import { feathers, Paginated } from '@feathersjs/feathers' +import { KnexAdapterParams, KnexService, transaction } from '../src' +import { PaginationOptions } from '@feathersjs/adapter-commons' + +// const { transaction } = service.hooks + +const db = knex({ + client: 'sqlite3', + connection: { + filename: './db.sqlite' + } +}) + +const schemaName = 'overrides' + +knex({ + client: 'sqlite3', + connection: { + filename: `./${schemaName}.sqlite` + } +}) + +type Animal = { + id: number + ancestor_id: number + ancestor_name: string + name: string +} + +/** + * Override the _find() method to manipulate the knex query, and + * introduce ambiguity by the table to itself. + */ +class AnimalService extends KnexService { + async $find(params?: P & { paginate?: PaginationOptions }): Promise> + async $find(params?: P & { paginate: false }): Promise + async $find(params?: P): Promise | T[]> + async $find(params: P = {} as P): Promise | T[]> { + const knexQuery = this.createQuery(params) + knexQuery + .select('ancestors.name as ancestor_name') + .leftJoin('animals as ancestors', 'ancestors.id', '=', 'animals.ancestor_id') + params.knex = knexQuery + return super.$find(params) + } +} + +const animals = new AnimalService({ + Model: db, + name: 'animals', + events: ['testing'] +}) + +function clean() { + return db.schema.dropTableIfExists(animals.fullName).then(() => { + return db.schema.createTable(animals.fullName, (table) => { + table.increments('id') + table.integer('ancestor_id') + table.string('name').notNullable() + return table + }) + }) +} + +describe('Feathers Knex Overridden Method With Self-Join', () => { + let ancestor: Animal + let animal: Animal + + const app = feathers<{ animals: AnimalService }>() + .hooks({ + before: [transaction.start()], + after: [transaction.end()], + error: [transaction.rollback()] + }) + .use('animals', animals) + const animalService = app.service('animals') + + before(() => { + return db.schema.raw(`attach database '${schemaName}.sqlite' as ${schemaName}`) + }) + before(clean) + after(clean) + + beforeEach(async () => { + ancestor = await animalService.create({ + name: 'Ape' + }) + animal = await animalService.create({ + ancestor_id: ancestor.id, + name: 'Human' + }) + }) + + it('finds properly', async () => { + const foundAnimals = await animalService.find({ + paginate: false, + query: { + $limit: 1, + ancestor_name: 'Ape' + } + }) + assert.strictEqual(foundAnimals[0].id, animal.id) + assert.strictEqual(foundAnimals[0].name, 'Human') + assert.strictEqual(foundAnimals[0].ancestor_name, 'Ape') + }) + + /** + * Previously, any query modified to include joins with ambiguous primary keys + * would yield an ambiguous column errors: + * BadRequest: select `animals`.* + * from `animals` + * left join `animals` as `ancestors` on `ancestors`.`id` = `animals`.`ancestor_id` + * where `id` in (2) - SQLITE_ERROR: ambiguous column name: id + * + * The fix involves explicitly specifying the table to query in the _patch() method + */ + it('patches without ambiguous query', async () => { + const newName = 'Homo Sapiens' + const patchedAnimal = await animalService.patch(animal.id, { name: newName }) + + assert.strictEqual(patchedAnimal.name, newName) + }) +}) diff --git a/_templates/package/new/tsconfig.json.t b/packages/knex/tsconfig.json similarity index 72% rename from _templates/package/new/tsconfig.json.t rename to packages/knex/tsconfig.json index 2bd96b2c60..316fd41336 100644 --- a/_templates/package/new/tsconfig.json.t +++ b/packages/knex/tsconfig.json @@ -1,7 +1,3 @@ ---- -to: packages/<%= name %>/tsconfig.json ---- - { "extends": "../../tsconfig", "include": [ diff --git a/packages/koa/CHANGELOG.md b/packages/koa/CHANGELOG.md index 0ea379af18..af9acf8730 100644 --- a/packages/koa/CHANGELOG.md +++ b/packages/koa/CHANGELOG.md @@ -3,127 +3,157 @@ All notable changes to this project will be documented in this file. See [Conventional Commits](https://conventionalcommits.org) for commit guidelines. -# [5.0.0-pre.16](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.15...v5.0.0-pre.16) (2022-01-12) +# [5.0.0-pre.31](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.30...v5.0.0-pre.31) (2022-10-12) + +### Bug Fixes +- **koa:** Only set error code for Feathers errors ([#2793](https://github.com/feathersjs/feathers/issues/2793)) ([d3ee41e](https://github.com/feathersjs/feathers/commit/d3ee41e27b0ea5d29b344d6584ab03e48d16e2b4)) ### Features -* **express, koa:** make transports similar ([#2486](https://github.com/feathersjs/feathers/issues/2486)) ([26aa937](https://github.com/feathersjs/feathers/commit/26aa937c114fb8596dfefc599b1f53cead69c159)) +- **cli:** Generate full client test suite and improve typed client ([#2788](https://github.com/feathersjs/feathers/issues/2788)) ([57119b6](https://github.com/feathersjs/feathers/commit/57119b6bb2797f7297cf054268a248c093ecd538)) +# [5.0.0-pre.30](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.29...v5.0.0-pre.30) (2022-10-07) +### Bug Fixes +- **core:** Ensure setup and teardown can be overriden and maintain hook functionality ([#2779](https://github.com/feathersjs/feathers/issues/2779)) ([ab580cb](https://github.com/feathersjs/feathers/commit/ab580cbcaa68d19144d86798c13bf564f9d424a6)) +### Features -# [5.0.0-pre.15](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.14...v5.0.0-pre.15) (2021-11-27) +- **core:** Allow to unregister services at runtime ([#2756](https://github.com/feathersjs/feathers/issues/2756)) ([d16601f](https://github.com/feathersjs/feathers/commit/d16601f2277dca5357866ffdefba2a611f6dc7fa)) +# [5.0.0-pre.29](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.28...v5.0.0-pre.29) (2022-09-16) -### Bug Fixes +### Features -* **typescript:** Overall typing improvements ([#2478](https://github.com/feathersjs/feathers/issues/2478)) ([b8eb804](https://github.com/feathersjs/feathers/commit/b8eb804158556d9651a8607e3c3fda15e0bfd110)) +- Add CORS support to oAuth, Express, Koa and generated application ([#2744](https://github.com/feathersjs/feathers/issues/2744)) ([fd218f2](https://github.com/feathersjs/feathers/commit/fd218f289f8ca4c101e9938e8683e2efef6e8131)) +# [5.0.0-pre.28](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.27...v5.0.0-pre.28) (2022-08-03) -### Features +### Bug Fixes -* **core:** add `context.http` and move `statusCode` there ([#2496](https://github.com/feathersjs/feathers/issues/2496)) ([b701bf7](https://github.com/feathersjs/feathers/commit/b701bf77fb83048aa1dffa492b3d77dd53f7b72b)) +- **cli:** Improve generated application and client ([#2701](https://github.com/feathersjs/feathers/issues/2701)) ([bd55ffb](https://github.com/feathersjs/feathers/commit/bd55ffb812e89bf215f4515e7f137656ea888c3f)) +# [5.0.0-pre.27](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.26...v5.0.0-pre.27) (2022-07-13) +**Note:** Version bump only for package @feathersjs/koa +# [5.0.0-pre.26](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.25...v5.0.0-pre.26) (2022-06-22) +**Note:** Version bump only for package @feathersjs/koa -# [5.0.0-pre.14](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.13...v5.0.0-pre.14) (2021-10-13) +# [5.0.0-pre.25](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.24...v5.0.0-pre.25) (2022-06-22) **Note:** Version bump only for package @feathersjs/koa +# [5.0.0-pre.24](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.23...v5.0.0-pre.24) (2022-06-21) +### Features +- **cli:** Add support for JavaScript to the new CLI ([#2668](https://github.com/feathersjs/feathers/issues/2668)) ([ebac587](https://github.com/feathersjs/feathers/commit/ebac587f7d00dc7607c3f546352d79f79b89a5d4)) +- **cli:** Initial Feathers v5 CLI and Pinion generator ([#2578](https://github.com/feathersjs/feathers/issues/2578)) ([7f59ae7](https://github.com/feathersjs/feathers/commit/7f59ae7f1471895ba8a82aa4702f1a23f71b7682)) +# [5.0.0-pre.23](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.22...v5.0.0-pre.23) (2022-06-06) -# [5.0.0-pre.13](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.12...v5.0.0-pre.13) (2021-10-13) +**Note:** Version bump only for package @feathersjs/koa + +# [5.0.0-pre.22](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.21...v5.0.0-pre.22) (2022-05-24) **Note:** Version bump only for package @feathersjs/koa +# [5.0.0-pre.21](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.20...v5.0.0-pre.21) (2022-05-23) +**Note:** Version bump only for package @feathersjs/koa +# [5.0.0-pre.20](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.19...v5.0.0-pre.20) (2022-05-04) +### Bug Fixes -# [5.0.0-pre.12](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.11...v5.0.0-pre.12) (2021-10-12) +- **dependencies:** Lock monorepo package version numbers ([#2623](https://github.com/feathersjs/feathers/issues/2623)) ([5640c10](https://github.com/feathersjs/feathers/commit/5640c1020cc139994e695d658c08bad3494db507)) -**Note:** Version bump only for package @feathersjs/koa +# [5.0.0-pre.19](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.18...v5.0.0-pre.19) (2022-05-01) +**Note:** Version bump only for package @feathersjs/koa +# [5.0.0-pre.18](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.17...v5.0.0-pre.18) (2022-04-11) +### Features +- **core:** Add app.teardown functionality ([#2570](https://github.com/feathersjs/feathers/issues/2570)) ([fcdf524](https://github.com/feathersjs/feathers/commit/fcdf524ae1995bb59265d39f12e98b7794bed023)) +- **core:** Finalize app.teardown() functionality ([#2584](https://github.com/feathersjs/feathers/issues/2584)) ([1a166f3](https://github.com/feathersjs/feathers/commit/1a166f3ded811ecacf0ae8cb67880bc9fa2eeafa)) +- **transport-commons:** add `context.http.response` ([#2524](https://github.com/feathersjs/feathers/issues/2524)) ([5bc9d44](https://github.com/feathersjs/feathers/commit/5bc9d447043c2e2b742c73ed28ecf3b3264dd9e5)) -# [5.0.0-pre.11](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.10...v5.0.0-pre.11) (2021-10-06) +# [5.0.0-pre.17](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.16...v5.0.0-pre.17) (2022-02-15) **Note:** Version bump only for package @feathersjs/koa +# [5.0.0-pre.16](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.15...v5.0.0-pre.16) (2022-01-12) +### Features +- **express, koa:** make transports similar ([#2486](https://github.com/feathersjs/feathers/issues/2486)) ([26aa937](https://github.com/feathersjs/feathers/commit/26aa937c114fb8596dfefc599b1f53cead69c159)) +# [5.0.0-pre.15](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.14...v5.0.0-pre.15) (2021-11-27) -# [5.0.0-pre.10](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.9...v5.0.0-pre.10) (2021-09-19) +### Bug Fixes -**Note:** Version bump only for package @feathersjs/koa +- **typescript:** Overall typing improvements ([#2478](https://github.com/feathersjs/feathers/issues/2478)) ([b8eb804](https://github.com/feathersjs/feathers/commit/b8eb804158556d9651a8607e3c3fda15e0bfd110)) +### Features +- **core:** add `context.http` and move `statusCode` there ([#2496](https://github.com/feathersjs/feathers/issues/2496)) ([b701bf7](https://github.com/feathersjs/feathers/commit/b701bf77fb83048aa1dffa492b3d77dd53f7b72b)) +# [5.0.0-pre.14](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.13...v5.0.0-pre.14) (2021-10-13) +**Note:** Version bump only for package @feathersjs/koa -# [5.0.0-pre.9](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.8...v5.0.0-pre.9) (2021-08-09) +# [5.0.0-pre.13](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.12...v5.0.0-pre.13) (2021-10-13) **Note:** Version bump only for package @feathersjs/koa +# [5.0.0-pre.12](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.11...v5.0.0-pre.12) (2021-10-12) +**Note:** Version bump only for package @feathersjs/koa +# [5.0.0-pre.11](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.10...v5.0.0-pre.11) (2021-10-06) +**Note:** Version bump only for package @feathersjs/koa -# [5.0.0-pre.8](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.7...v5.0.0-pre.8) (2021-08-09) +# [5.0.0-pre.10](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.9...v5.0.0-pre.10) (2021-09-19) **Note:** Version bump only for package @feathersjs/koa +# [5.0.0-pre.9](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.8...v5.0.0-pre.9) (2021-08-09) +**Note:** Version bump only for package @feathersjs/koa +# [5.0.0-pre.8](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.7...v5.0.0-pre.8) (2021-08-09) +**Note:** Version bump only for package @feathersjs/koa # [5.0.0-pre.7](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.6...v5.0.0-pre.7) (2021-08-09) **Note:** Version bump only for package @feathersjs/koa - - - - # [5.0.0-pre.6](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.5...v5.0.0-pre.6) (2021-08-08) - ### Bug Fixes -* **koa:** Throw a NotFound Feathers error on missing paths ([#2415](https://github.com/feathersjs/feathers/issues/2415)) ([e013f98](https://github.com/feathersjs/feathers/commit/e013f98315d550ced6eacffd615c61bb0912b4ba)) - - - - +- **koa:** Throw a NotFound Feathers error on missing paths ([#2415](https://github.com/feathersjs/feathers/issues/2415)) ([e013f98](https://github.com/feathersjs/feathers/commit/e013f98315d550ced6eacffd615c61bb0912b4ba)) # [5.0.0-pre.5](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.4...v5.0.0-pre.5) (2021-06-23) - ### Bug Fixes -* **koa:** Use extended query parser for compatibility ([#2397](https://github.com/feathersjs/feathers/issues/2397)) ([b2944ba](https://github.com/feathersjs/feathers/commit/b2944bac3ec6d5ecc80dc518cd4e58093692db74)) - +- **koa:** Use extended query parser for compatibility ([#2397](https://github.com/feathersjs/feathers/issues/2397)) ([b2944ba](https://github.com/feathersjs/feathers/commit/b2944bac3ec6d5ecc80dc518cd4e58093692db74)) ### Features -* **adapter-commons:** Add support for params.adapter option and move memory adapter to @feathersjs/memory ([#2367](https://github.com/feathersjs/feathers/issues/2367)) ([a43e7da](https://github.com/feathersjs/feathers/commit/a43e7da22b6b981a96d1321736ea9a0cb924fb4f)) - - - - +- **adapter-commons:** Add support for params.adapter option and move memory adapter to @feathersjs/memory ([#2367](https://github.com/feathersjs/feathers/issues/2367)) ([a43e7da](https://github.com/feathersjs/feathers/commit/a43e7da22b6b981a96d1321736ea9a0cb924fb4f)) # [5.0.0-pre.4](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.3...v5.0.0-pre.4) (2021-05-13) - ### Features -* **koa:** KoaJS transport adapter ([#2315](https://github.com/feathersjs/feathers/issues/2315)) ([2554b57](https://github.com/feathersjs/feathers/commit/2554b57cf05731df58feeba9c12faab18e442107)) +- **koa:** KoaJS transport adapter ([#2315](https://github.com/feathersjs/feathers/issues/2315)) ([2554b57](https://github.com/feathersjs/feathers/commit/2554b57cf05731df58feeba9c12faab18e442107)) diff --git a/packages/koa/README.md b/packages/koa/README.md index a1253ff195..475e431487 100644 --- a/packages/koa/README.md +++ b/packages/koa/README.md @@ -1,6 +1,24 @@ # @feathersjs/koa -[![Dependency Status](https://img.shields.io/david/feathersjs/feathers.svg?style=flat-square&path=packages/koa)](https://david-dm.org/feathersjs/feathers?path=packages/koa) +[![CI](https://github.com/feathersjs/feathers/workflows/CI/badge.svg)](https://github.com/feathersjs/feathers/actions?query=workflow%3ACI) [![Download Status](https://img.shields.io/npm/dm/@feathersjs/koa.svg?style=flat-square)](https://www.npmjs.com/package/@feathersjs/koa) +[![Discord](https://badgen.net/badge/icon/discord?icon=discord&label)](https://discord.gg/qa8kez8QBx) > Feathers KoaJS framework bindings and REST provider + +## Installation + +``` +npm install @feathersjs/koa --save +``` + +## Documentation + +Refer to the [Feathers Koa API documentation](https://docs.feathersjs.com/api/koa.html) for more details. + +## License + +Copyright (c) 2022 [Feathers contributors](https://github.com/feathersjs/feathers/graphs/contributors) + +Licensed under the [MIT license](LICENSE). + diff --git a/packages/koa/package.json b/packages/koa/package.json index 29a5bff8ce..8b380d2678 100644 --- a/packages/koa/package.json +++ b/packages/koa/package.json @@ -1,9 +1,10 @@ { "name": "@feathersjs/koa", "description": "Feathers KoaJS framework bindings and REST provider", - "version": "5.0.0-pre.16", + "version": "5.0.0-pre.31", "homepage": "https://feathersjs.com", "main": "lib/", + "types": "lib/", "keywords": [ "feathers", "koajs" @@ -11,7 +12,8 @@ "license": "MIT", "repository": { "type": "git", - "url": "git://github.com/feathersjs/feathers.git" + "url": "git://github.com/feathersjs/feathers.git", + "directory": "packages/koa" }, "author": { "name": "Feathers contributors", @@ -36,9 +38,9 @@ ], "scripts": { "prepublish": "npm run compile", - "compile": "shx rm -rf lib/ && tsc", - "test": "npm run compile && npm run mocha", - "mocha": "mocha --config ../../.mocharc.json --recursive test/**.test.ts test/**/*.test.ts" + "pack": "npm pack --pack-destination ../cli/test/build", + "compile": "shx rm -rf lib/ && tsc && npm run pack", + "test": "mocha --config ../../.mocharc.json --recursive test/**.test.ts test/**/*.test.ts" }, "directories": { "lib": "lib" @@ -47,31 +49,33 @@ "access": "public" }, "dependencies": { - "@feathersjs/authentication": "^5.0.0-pre.16", - "@feathersjs/commons": "^5.0.0-pre.16", - "@feathersjs/errors": "^5.0.0-pre.16", - "@feathersjs/transport-commons": "^5.0.0-pre.16", - "@types/koa": "^2.13.4", - "@types/koa-bodyparser": "^4.3.5", + "@feathersjs/authentication": "^5.0.0-pre.31", + "@feathersjs/commons": "^5.0.0-pre.31", + "@feathersjs/errors": "^5.0.0-pre.31", + "@feathersjs/transport-commons": "^5.0.0-pre.31", + "@koa/cors": "^3.4.2", + "@types/koa": "^2.13.5", + "@types/koa-bodyparser": "^4.3.8", "@types/koa-qs": "^2.0.0", + "@types/koa__cors": "^3.3.0", "koa": "^2.13.4", "koa-bodyparser": "^4.3.0", "koa-compose": "^4.1.0", "koa-qs": "^3.0.0" }, "devDependencies": { - "@feathersjs/authentication-local": "^5.0.0-pre.16", - "@feathersjs/feathers": "^5.0.0-pre.16", - "@feathersjs/memory": "^5.0.0-pre.16", - "@feathersjs/tests": "^5.0.0-pre.16", + "@feathersjs/authentication-local": "^5.0.0-pre.31", + "@feathersjs/feathers": "^5.0.0-pre.31", + "@feathersjs/memory": "^5.0.0-pre.31", + "@feathersjs/tests": "^5.0.0-pre.31", "@types/koa-compose": "^3.2.5", - "@types/mocha": "^9.0.0", - "@types/node": "^17.0.5", - "axios": "^0.24.0", - "mocha": "^9.1.3", - "shx": "^0.3.3", - "ts-node": "^10.4.0", - "typescript": "^4.5.4" + "@types/mocha": "^10.0.0", + "@types/node": "^18.8.2", + "axios": "^0.27.2", + "mocha": "^10.0.0", + "shx": "^0.3.4", + "ts-node": "^10.9.1", + "typescript": "^4.8.4" }, - "gitHead": "f0cd227a82d159b528193bd33747c97684a48773" + "gitHead": "4500dbeb8cea566678cf88b3313a88efd93a2ed9" } diff --git a/packages/koa/src/authentication.ts b/packages/koa/src/authentication.ts index f0730c6374..a84e99cdb2 100644 --- a/packages/koa/src/authentication.ts +++ b/packages/koa/src/authentication.ts @@ -1,56 +1,56 @@ -import { Application, HookContext } from '@feathersjs/feathers'; -import { createDebug } from '@feathersjs/commons'; -import { authenticate as AuthenticateHook } from '@feathersjs/authentication'; +import { Application, HookContext } from '@feathersjs/feathers' +import { createDebug } from '@feathersjs/commons' +import { authenticate as AuthenticateHook } from '@feathersjs/authentication' -import { Middleware } from './declarations'; +import { Middleware } from './declarations' -const debug = createDebug('@feathersjs/koa/authentication'); +const debug = createDebug('@feathersjs/koa/authentication') export type AuthenticationSettings = { - service?: string; - strategies?: string[]; -}; + service?: string + strategies?: string[] +} -export function parseAuthentication (settings: AuthenticationSettings = {}): Middleware { +export function parseAuthentication(settings: AuthenticationSettings = {}): Middleware { return async (ctx, next) => { - const app = ctx.app; - const service = app.defaultAuthentication?.(settings.service); + const app = ctx.app + const service = app.defaultAuthentication?.(settings.service) if (!service) { - return next(); + return next() } - const config = service.configuration; - const authStrategies = settings.strategies || config.parseStrategies || config.authStrategies || []; + const config = service.configuration + const authStrategies = settings.strategies || config.parseStrategies || config.authStrategies || [] if (authStrategies.length === 0) { - debug('No `authStrategies` or `parseStrategies` found in authentication configuration'); - return next(); + debug('No `authStrategies` or `parseStrategies` found in authentication configuration') + return next() } - const authentication = await service.parse(ctx.req, ctx.res, ...authStrategies); + const authentication = await service.parse(ctx.req, ctx.res, ...authStrategies) if (authentication) { - debug('Parsed authentication from HTTP header', authentication); - ctx.feathers = { ...ctx.feathers, authentication }; + debug('Parsed authentication from HTTP header', authentication) + ctx.feathers = { ...ctx.feathers, authentication } } - return next(); - }; + return next() + } } -export function authenticate (settings: string | AuthenticationSettings, ...strategies: string[]): Middleware { - const hook = AuthenticateHook(settings, ...strategies); +export function authenticate(settings: string | AuthenticationSettings, ...strategies: string[]): Middleware { + const hook = AuthenticateHook(settings, ...strategies) return async (ctx, next) => { - const app = ctx.app as Application; - const params = ctx.feathers; - const context = { app, params } as HookContext; + const app = ctx.app as Application + const params = ctx.feathers + const context = { app, params } as HookContext - await hook(context); + await hook(context) - ctx.feathers = context.params; + ctx.feathers = context.params - return next(); - }; + return next() + } } diff --git a/packages/koa/src/declarations.ts b/packages/koa/src/declarations.ts index 506a72d462..7ae1ff50f7 100644 --- a/packages/koa/src/declarations.ts +++ b/packages/koa/src/declarations.ts @@ -1,35 +1,37 @@ -import Koa, { Next } from 'koa'; -import { Server } from 'http'; -import { Application as FeathersApplication, HookContext, Params, RouteLookup } from '@feathersjs/feathers'; -import '@feathersjs/authentication'; +import Koa, { Next } from 'koa' +import { Server } from 'http' +import { Application as FeathersApplication, HookContext, Params, RouteLookup } from '@feathersjs/feathers' +import '@feathersjs/authentication' export type ApplicationAddons = { - listen (port?: number, ...args: any[]): Promise; + server: Server + listen(port?: number, ...args: any[]): Promise } -export type Application = - Omit & FeathersApplication & ApplicationAddons; +export type Application = Omit & + FeathersApplication & + ApplicationAddons export type FeathersKoaContext = Koa.Context & { - app: A; -}; + app: A +} -export type Middleware = (context: FeathersKoaContext, next: Next) => any; +export type Middleware = (context: FeathersKoaContext, next: Next) => any declare module '@feathersjs/feathers/lib/declarations' { interface ServiceOptions { koa?: { - before?: Middleware[]; - after?: Middleware[]; - composed?: Middleware; - }; + before?: Middleware[] + after?: Middleware[] + composed?: Middleware + } } } declare module 'koa' { interface ExtendableContext { - feathers?: Partial; - lookup?: RouteLookup; - hook?: HookContext; + feathers?: Partial + lookup?: RouteLookup + hook?: HookContext } } diff --git a/packages/koa/src/handlers.ts b/packages/koa/src/handlers.ts index 228f529a0e..3c1a1aa216 100644 --- a/packages/koa/src/handlers.ts +++ b/packages/koa/src/handlers.ts @@ -1,18 +1,20 @@ -import { NotFound } from '@feathersjs/errors'; -import { FeathersKoaContext } from './declarations'; +import { FeathersError, NotFound } from '@feathersjs/errors' +import { FeathersKoaContext } from './declarations' export const errorHandler = () => async (ctx: FeathersKoaContext, next: () => Promise) => { try { - await next(); + await next() - if(ctx.body === undefined) { - throw new NotFound('Not Found'); + if (ctx.body === undefined) { + throw new NotFound(`Path ${ctx.path} not found`) } - } catch (error: any) { - ctx.response.status = error.code || 500; - ctx.body = typeof error.toJSON === 'function' ? error.toJSON() : { - message: error.message - }; + ctx.response.status = error instanceof FeathersError ? error.code : 500 + ctx.body = + typeof error.toJSON === 'function' + ? error.toJSON() + : { + message: error.message + } } -}; +} diff --git a/packages/koa/src/index.ts b/packages/koa/src/index.ts index 1e19ca4933..8ee9a0547a 100644 --- a/packages/koa/src/index.ts +++ b/packages/koa/src/index.ts @@ -1,80 +1,96 @@ -import Koa from 'koa'; -import koaQs from 'koa-qs'; -import { Application as FeathersApplication } from '@feathersjs/feathers'; -import { routing } from '@feathersjs/transport-commons'; -import { createDebug } from '@feathersjs/commons'; - -import { Application } from './declarations'; - -export { default as Koa } from 'koa'; -export { default as bodyParser } from 'koa-bodyparser'; - -export * from './authentication'; -export * from './declarations'; -export * from './handlers'; -export * from './rest'; - -const debug = createDebug('@feathersjs/koa'); - -export function koa (feathersApp?: FeathersApplication, koaApp: Koa = new Koa()): Application { +import Koa from 'koa' +import koaQs from 'koa-qs' +import { Application as FeathersApplication } from '@feathersjs/feathers' +import { routing } from '@feathersjs/transport-commons' +import { createDebug } from '@feathersjs/commons' +import bodyParser from 'koa-bodyparser' +import cors from '@koa/cors' + +import { Application } from './declarations' + +export { Koa, bodyParser, cors } +export * from './authentication' +export * from './declarations' +export * from './handlers' +export * from './rest' + +const debug = createDebug('@feathersjs/koa') + +export function koa( + feathersApp?: FeathersApplication, + koaApp: Koa = new Koa() +): Application { if (!feathersApp) { - return koaApp as any; + return koaApp as any } if (typeof feathersApp.setup !== 'function') { - throw new Error('@feathersjs/koa requires a valid Feathers application instance'); + throw new Error('@feathersjs/koa requires a valid Feathers application instance') } - const app = feathersApp as any as Application; - const { listen: koaListen, use: koaUse } = koaApp; - const feathersUse = feathersApp.use as any; + const app = feathersApp as any as Application + const { listen: koaListen, use: koaUse } = koaApp + const { use: feathersUse, teardown: feathersTeardown } = feathersApp Object.assign(app, { - use (location: string|Koa.Middleware, ...args: any[]) { + use(location: string | Koa.Middleware, ...args: any[]) { if (typeof location === 'string') { - return feathersUse.call(this, location, ...args); + return (feathersUse as any).call(this, location, ...args) } - return koaUse.call(this, location); + return koaUse.call(this, location) }, - async listen (port?: number, ...args: any[]) { - const server = koaListen.call(this, port, ...args); + async listen(port?: number, ...args: any[]) { + const server = koaListen.call(this, port, ...args) - await this.setup(server); - debug('Feathers application listening'); + this.server = server + await this.setup(server) + debug('Feathers application listening') - return server; + return server + }, + + async teardown(server?: any) { + return feathersTeardown + .call(this, server) + .then( + () => new Promise((resolve, reject) => this.server.close((e) => (e ? reject(e) : resolve(this)))) + ) } - } as Application); + } as Application) const appDescriptors = { ...Object.getOwnPropertyDescriptors(Object.getPrototypeOf(app)), ...Object.getOwnPropertyDescriptors(app) - }; + } const newDescriptors = { ...Object.getOwnPropertyDescriptors(Object.getPrototypeOf(koaApp)), ...Object.getOwnPropertyDescriptors(koaApp) - }; + } // Copy all non-existing properties (including non-enumerables) // that don't already exist on the Express app - Object.keys(newDescriptors).forEach(prop => { - const appProp = appDescriptors[prop]; - const newProp = newDescriptors[prop]; + Object.keys(newDescriptors).forEach((prop) => { + const appProp = appDescriptors[prop] + const newProp = newDescriptors[prop] if (appProp === undefined && newProp !== undefined) { - Object.defineProperty(app, prop, newProp); + Object.defineProperty(app, prop, newProp) } - }); + }) + + koaQs(app as any) - koaQs(app as any); + // This reinitializes hooks + app.setup = feathersApp.setup as any + app.teardown = feathersApp.teardown as any - app.configure(routing() as any); + app.configure(routing() as any) app.use((ctx, next) => { - ctx.feathers = { ...ctx.feathers, provider: 'rest' }; - return next(); - }); + ctx.feathers = { ...ctx.feathers, provider: 'rest' } + return next() + }) - return app; + return app } diff --git a/packages/koa/src/rest.ts b/packages/koa/src/rest.ts index 5b1182bc53..8bd08dd339 100644 --- a/packages/koa/src/rest.ts +++ b/packages/koa/src/rest.ts @@ -1,93 +1,94 @@ -import compose from 'koa-compose'; -import { http } from '@feathersjs/transport-commons'; -import { createDebug } from '@feathersjs/commons'; -import { getServiceOptions, defaultServiceMethods, createContext } from '@feathersjs/feathers'; -import { MethodNotAllowed } from '@feathersjs/errors'; +import compose from 'koa-compose' +import { http } from '@feathersjs/transport-commons' +import { createDebug } from '@feathersjs/commons' +import { getServiceOptions, defaultServiceMethods, createContext } from '@feathersjs/feathers' +import { MethodNotAllowed } from '@feathersjs/errors' -import { Application, Middleware } from './declarations'; -import { AuthenticationSettings, parseAuthentication } from './authentication'; +import { Application, Middleware } from './declarations' +import { AuthenticationSettings, parseAuthentication } from './authentication' -const debug = createDebug('@feathersjs/koa/rest'); +const debug = createDebug('@feathersjs/koa/rest') const serviceMiddleware = (): Middleware => { return async (ctx, next) => { - const { query, headers, path, body: data, method: httpMethod } = ctx.request; - const methodOverride = ctx.request.headers[http.METHOD_HEADER] as string | undefined; + const { query, headers, path, body: data, method: httpMethod } = ctx.request + const methodOverride = ctx.request.headers[http.METHOD_HEADER] as string | undefined - const { service, params: { __id: id = null, ...route } = {} } = ctx.lookup!; - const method = http.getServiceMethod(httpMethod, id, methodOverride); - const { methods } = getServiceOptions(service); + // eslint-disable-next-line @typescript-eslint/no-non-null-assertion + const { service, params: { __id: id = null, ...route } = {} } = ctx.lookup! + const method = http.getServiceMethod(httpMethod, id, methodOverride) + const { methods } = getServiceOptions(service) - debug(`Found service for path ${path}, attempting to run '${method}' service method`); + debug(`Found service for path ${path}, attempting to run '${method}' service method`) if (!methods.includes(method) || defaultServiceMethods.includes(methodOverride)) { - const error = new MethodNotAllowed(`Method \`${method}\` is not supported by this endpoint.`); - ctx.response.status = error.code; - throw error; + const error = new MethodNotAllowed(`Method \`${method}\` is not supported by this endpoint.`) + ctx.response.status = error.code + throw error } - const createArguments = http.argumentsFor[method as 'get'] || http.argumentsFor.default; - const params = { query, headers, route, ...ctx.feathers }; - const args = createArguments({ id, data, params }); - const contextBase = createContext(service, method, { http: {} }); - ctx.hook = contextBase; + const createArguments = http.argumentsFor[method as 'get'] || http.argumentsFor.default + const params = { query, headers, route, ...ctx.feathers } + const args = createArguments({ id, data, params }) + const contextBase = createContext(service, method, { http: {} }) + ctx.hook = contextBase - const context = await (service as any)[method](...args, contextBase); - ctx.hook = context; + const context = await (service as any)[method](...args, contextBase) + ctx.hook = context - const result = http.getData(context); - const statusCode = http.getStatusCode(context, result); + const response = http.getResponse(context) + ctx.status = response.status + ctx.set(response.headers) + ctx.body = response.body - ctx.body = result; - ctx.status = statusCode; - - return next(); - }; -}; + return next() + } +} const servicesMiddleware = (): Middleware => { return async (ctx, next) => { - const app = ctx.app; - const lookup = app.lookup(ctx.request.path); + const app = ctx.app + const lookup = app.lookup(ctx.request.path) if (!lookup) { - return next(); + return next() } - ctx.lookup = lookup; + ctx.lookup = lookup - const options = getServiceOptions(lookup.service); - const middleware = options.koa!.composed!; + const options = getServiceOptions(lookup.service) + const middleware = options.koa.composed - return middleware(ctx, next); - }; -}; + return middleware(ctx, next) + } +} -export const formatter: Middleware = (_ctx, _next) => {}; +// eslint-disable-next-line @typescript-eslint/no-empty-function +export const formatter: Middleware = (_ctx, _next) => {} export type RestOptions = { - formatter?: Middleware; - authentication?: AuthenticationSettings; -}; + formatter?: Middleware + authentication?: AuthenticationSettings +} export const rest = (options?: RestOptions | Middleware) => { - options = typeof options === 'function' ? { formatter: options } : options || {}; + options = typeof options === 'function' ? { formatter: options } : options || {} - const formatterMiddleware = options.formatter || formatter; - const authenticationOptions = options.authentication; + const formatterMiddleware = options.formatter || formatter + const authenticationOptions = options.authentication return (app: Application) => { - app.use(parseAuthentication(authenticationOptions)); - app.use(servicesMiddleware()); + app.use(parseAuthentication(authenticationOptions)) + app.use(servicesMiddleware()) app.mixins.push((_service, _path, options) => { - const { koa: { before = [], after = [] } = {} } = options; + const { koa: { before = [], after = [] } = {} } = options - const middlewares = [].concat(before, serviceMiddleware(), after, formatterMiddleware); - const middleware = compose(middlewares); + const middlewares = [].concat(before, serviceMiddleware(), after, formatterMiddleware) + const middleware = compose(middlewares) - options.koa ||= {}; - options.koa.composed = middleware; - }); - }; -}; + options.koa ||= {} + options.koa.composed = middleware + }) + } +} diff --git a/packages/koa/test/app.fixture.ts b/packages/koa/test/app.fixture.ts index a0936251ad..c6427fb49c 100644 --- a/packages/koa/test/app.fixture.ts +++ b/packages/koa/test/app.fixture.ts @@ -1,66 +1,70 @@ -import { memory } from '@feathersjs/memory'; -import { feathers, Params, HookContext } from '@feathersjs/feathers'; -import { authenticate, AuthenticationService, JWTStrategy } from '@feathersjs/authentication'; -import { LocalStrategy, hooks } from '@feathersjs/authentication-local'; +import { memory } from '@feathersjs/memory' +import { feathers, Params, HookContext } from '@feathersjs/feathers' +import { authenticate, AuthenticationService, JWTStrategy } from '@feathersjs/authentication' +import { LocalStrategy, hooks } from '@feathersjs/authentication-local' -import { koa, rest, bodyParser, errorHandler } from '../src'; +import { koa, rest, bodyParser, errorHandler, cors } from '../src' -const { protect, hashPassword } = hooks; -const app = koa(feathers()); -const authService = new AuthenticationService(app); +const { protect, hashPassword } = hooks +const app = koa(feathers()) +const authService = new AuthenticationService(app) -app.use(errorHandler()); -app.use(bodyParser()); -app.configure(rest()); +app.use(errorHandler()) +app.use(cors()) +app.use(bodyParser()) +app.configure(rest()) app.set('authentication', { entity: 'user', service: 'users', secret: 'supersecret', - authStrategies: [ 'local', 'jwt' ], - parseStrategies: [ 'jwt' ], + authStrategies: ['local', 'jwt'], + parseStrategies: ['jwt'], local: { usernameField: 'email', passwordField: 'password' } -}); +}) -authService.register('jwt', new JWTStrategy()); -authService.register('local', new LocalStrategy()); +authService.register('jwt', new JWTStrategy()) +authService.register('local', new LocalStrategy()) -app.use('/authentication', authService); -app.use('/users', memory({ - paginate: { - default: 10, - max: 20 - } -})); +app.use('/authentication', authService) +app.use( + '/users', + memory({ + paginate: { + default: 10, + max: 20 + } + }) +) app.service('users').hooks({ before: { - create: [ - hashPassword('password') - ] + create: [hashPassword('password')] }, after: { all: [protect('password')], - get: [(context: HookContext) => { - if (context.params.provider) { - context.result.fromGet = true; - } + get: [ + (context: HookContext) => { + if (context.params.provider) { + context.result.fromGet = true + } - return context; - }] + return context + } + ] } -}); +}) app.use('/dummy', { - async get (id: string, params: Params) { - return { id, params }; + async get(id: string, params: Params) { + return { id, params } } -}); +}) app.service('dummy').hooks({ before: [authenticate('jwt')] -}); +}) -export default app; +export default app diff --git a/packages/koa/test/authentication.test.ts b/packages/koa/test/authentication.test.ts index a0ef78a8d4..ffdf374bf2 100644 --- a/packages/koa/test/authentication.test.ts +++ b/packages/koa/test/authentication.test.ts @@ -1,40 +1,40 @@ -import { strict as assert } from 'assert'; -import _axios from 'axios'; -import { Server } from 'http'; -import { AuthenticationResult } from '@feathersjs/authentication'; +import { strict as assert } from 'assert' +import _axios from 'axios' +import { AuthenticationResult } from '@feathersjs/authentication' -import app from './app.fixture'; +import app from './app.fixture' const axios = _axios.create({ baseURL: 'http://localhost:9776/' -}); +}) describe('@feathersjs/koa/authentication', () => { - const email = 'koatest@authentication.com'; - const password = 'superkoa'; + const email = 'koatest@authentication.com' + const password = 'superkoa' - let server: Server; - let authResult: AuthenticationResult; - let user: any; + let authResult: AuthenticationResult + let user: any before(async () => { - server = await app.listen(9776); - user = await app.service('users').create({ email, password }); - authResult = (await axios.post('/authentication', { - strategy: 'local', - password, - email - })).data; - }); - - after(done => server.close(done)); + await app.listen(9776) + user = await app.service('users').create({ email, password }) + authResult = ( + await axios.post('/authentication', { + strategy: 'local', + password, + email + }) + ).data + }) + + after(() => app.teardown()) describe('service authentication', () => { it('successful local authentication', () => { - assert.ok(authResult.accessToken); - assert.strictEqual(authResult.user.email, email); - assert.strictEqual(authResult.user.password, undefined); - }); + assert.ok(authResult.accessToken) + assert.strictEqual(authResult.user.email, email) + assert.strictEqual(authResult.user.password, undefined) + }) it('local authentication with wrong password fails', async () => { try { @@ -42,82 +42,87 @@ describe('@feathersjs/koa/authentication', () => { strategy: 'local', password: 'wrong', email - }); - assert.fail('Should never get here'); + }) + assert.fail('Should never get here') } catch (error: any) { - const { data } = error.response; - assert.strictEqual(data.name, 'NotAuthenticated'); - assert.strictEqual(data.message, 'Invalid login'); + const { data } = error.response + assert.strictEqual(data.name, 'NotAuthenticated') + assert.strictEqual(data.message, 'Invalid login') } - }); + }) it('authenticating with JWT works but returns same accessToken', async () => { - const { accessToken } = authResult; + const { accessToken } = authResult const { data } = await axios.post('/authentication', { strategy: 'jwt', accessToken - }); + }) - assert.strictEqual(data.accessToken, accessToken); - assert.strictEqual(data.authentication.strategy, 'jwt'); - assert.strictEqual(data.authentication.payload.sub, user.id.toString()); - assert.strictEqual(data.user.email, email); - }); + assert.strictEqual(data.accessToken, accessToken) + assert.strictEqual(data.authentication.strategy, 'jwt') + assert.strictEqual(data.authentication.payload.sub, user.id.toString()) + assert.strictEqual(data.user.email, email) + }) it('can make a protected request with Authorization header', async () => { - const { accessToken } = authResult; + const { accessToken } = authResult const { data } = await axios.get('/dummy/dave?user[name]=thing&user[message]=hi', { headers: { Authorization: accessToken } - }); + }) - assert.strictEqual(data.id, 'dave'); + assert.strictEqual(data.id, 'dave') assert.deepStrictEqual(data.params.query, { user: { name: 'thing', message: 'hi' } - }); - assert.deepStrictEqual(data.params.user, user); - assert.strictEqual(data.params.authentication.accessToken, accessToken); - }); + }) + assert.deepStrictEqual(data.params.user, user) + assert.strictEqual(data.params.authentication.accessToken, accessToken) + }) it('errors when there are no authStrategies and parseStrategies', async () => { - const { accessToken } = authResult; + const { accessToken } = authResult - app.get('authentication').authStrategies = []; - delete app.get('authentication').parseStrategies; + app.get('authentication').authStrategies = [] + delete app.get('authentication').parseStrategies try { await axios.get('/dummy/dave', { headers: { Authorization: accessToken } - }); - assert.fail('Should never get here'); + }) + assert.fail('Should never get here') } catch (error: any) { - assert.strictEqual(error.response.data.name, 'NotAuthenticated'); - app.get('authentication').authStrategies = [ 'jwt', 'local' ]; + assert.strictEqual(error.response.data.name, 'NotAuthenticated') + app.get('authentication').authStrategies = ['jwt', 'local'] } - }); + }) it('can make a protected request with Authorization header and bearer scheme', () => { - const { accessToken } = authResult; + const { accessToken } = authResult - return axios.get('/dummy/dave', { - headers: { - Authorization: ` Bearer: ${accessToken}` - } - }).then(res => { - const { data, data: { params } } = res; - - assert.strictEqual(data.id, 'dave'); - assert.deepStrictEqual(params.user, user); - assert.strictEqual(params.authentication.accessToken, accessToken); - }); - }); - }); -}); + return axios + .get('/dummy/dave', { + headers: { + Authorization: ` Bearer: ${accessToken}` + } + }) + .then((res) => { + const { + data, + data: { params } + } = res + + assert.strictEqual(data.id, 'dave') + assert.deepStrictEqual(params.user, user) + assert.strictEqual(params.authentication.accessToken, accessToken) + }) + }) + }) +}) diff --git a/packages/koa/test/index.test.ts b/packages/koa/test/index.test.ts index 475d748681..e836e1682f 100644 --- a/packages/koa/test/index.test.ts +++ b/packages/koa/test/index.test.ts @@ -1,145 +1,213 @@ -import { strict as assert } from 'assert'; -import Koa from 'koa'; -import axios from 'axios'; -import { Server } from 'http'; -import { feathers, Id } from '@feathersjs/feathers'; -import { Service, restTests } from '@feathersjs/tests'; -import { koa, rest, Application, bodyParser, errorHandler } from '../src'; +import { strict as assert } from 'assert' +import Koa from 'koa' +import axios from 'axios' +import { ApplicationHookMap, feathers, Id } from '@feathersjs/feathers' +import { Service, restTests } from '@feathersjs/tests' +import { koa, rest, Application, bodyParser, errorHandler } from '../src' describe('@feathersjs/koa', () => { - let app: Application; - let server: Server; + let app: Application before(async () => { - app = koa(feathers()); - app.use(errorHandler()); - app.use(bodyParser()); + app = koa(feathers()) + app.use(errorHandler()) + app.use(bodyParser()) app.use(async (ctx, next) => { if (ctx.request.path === '/middleware') { ctx.body = { feathers: ctx.feathers, message: 'Hello from middleware' - }; + } } else { - await next(); + await next() } - }); - app.configure(rest()); - app.use('/', new Service()); + }) + app.configure(rest()) + app.use('/', new Service()) app.use('todo', new Service(), { - methods: [ - 'get', 'find', 'create', 'update', - 'patch', 'remove', 'customMethod' + koa: { + after: [ + async (ctx, next) => { + const body = ctx.body as any + + if (body.id === 'custom-middleware') { + body.description = 'Description from custom middleware' + } + + await next() + } + ] + }, + methods: ['get', 'find', 'create', 'update', 'patch', 'remove', 'customMethod'] + }) + + app.hooks({ + setup: [ + async (context, next) => { + assert.ok(context.app) + await next() + } + ], + teardown: [ + async (context, next) => { + assert.ok(context.app) + await next() + } ] - }); + } as ApplicationHookMap) - server = await app.listen(8465); - }); + await app.listen(8465) + }) - after(() => server.close()); + after(() => app.teardown()) it('throws an error when initialized with invalid application', () => { try { - koa({} as Application); - assert.fail('Should never get here'); + koa({} as Application) + assert.fail('Should never get here') } catch (error: any) { - assert.equal(error.message, '@feathersjs/koa requires a valid Feathers application instance'); + assert.equal(error.message, '@feathersjs/koa requires a valid Feathers application instance') } - }); + }) it('returns Koa instance when no Feathers app is passed', () => { - assert.ok(koa() instanceof Koa); - }); + assert.ok(koa() instanceof Koa) + }) it('Koa wrapped and context.app are the same', async () => { - const app = koa(feathers()); - + const app = koa(feathers()) + app.use('/test', { - async get (id: Id) { - return { id }; + async get(id: Id) { + return { id } } - }); + }) app.service('test').hooks({ before: { - get: [context => { - assert.ok(context.app === app); - }] + get: [ + (context) => { + assert.ok(context.app === app) + } + ] } - }); + }) assert.deepStrictEqual(await app.service('test').get('testing'), { id: 'testing' - }); - }); + }) + }) it('starts as a Koa and Feathers application', async () => { - const { data } = await axios.get('http://localhost:8465/middleware'); + const { data } = await axios.get('http://localhost:8465/middleware') const todo = await app.service('todo').get('dishes', { query: {} - }); + }) assert.deepEqual(data, { message: 'Hello from middleware', feathers: { provider: 'rest' } - }); + }) assert.deepEqual(todo, { id: 'dishes', description: 'You have to do dishes!' - }); - }); + }) + }) + + it('supports custom service middleware', async () => { + const { data } = await axios.get('http://localhost:8465/todo/custom-middleware') + + assert.deepStrictEqual(data, { + id: 'custom-middleware', + description: 'Description from custom middleware' + }) + }) it('works with custom methods that are allowed', async () => { - const { data } = await axios.post('http://localhost:8465/todo', { - message: 'Custom hello' - }, { - headers: { - 'X-Service-Method': 'customMethod' + const { data } = await axios.post( + 'http://localhost:8465/todo', + { + message: 'Custom hello' + }, + { + headers: { + 'X-Service-Method': 'customMethod' + } } - }); - + ) + assert.deepStrictEqual(data, { data: { message: 'Custom hello' }, method: 'customMethod', provider: 'rest' - }); + }) - await assert.rejects(() => axios.post('http://localhost:8465/todo', {}, { - headers: { - 'X-Service-Method': 'internalMethod' + await assert.rejects( + () => + axios.post( + 'http://localhost:8465/todo', + {}, + { + headers: { + 'X-Service-Method': 'internalMethod' + } + } + ), + (error: any) => { + const { data } = error.response + + assert.strictEqual(data.code, 405) + assert.strictEqual(data.message, 'Method `internalMethod` is not supported by this endpoint.') + + return true } - }), (error: any) => { - const { data } = error.response; + ) + }) - assert.strictEqual(data.code, 405); - assert.strictEqual(data.message, 'Method `internalMethod` is not supported by this endpoint.'); + it('throws a 404 NotFound JSON error', async () => { + await assert.rejects( + () => + axios.post( + 'http://localhost:8465/no/where', + {}, + { + headers: { + 'X-Service-Method': 'internalMethod', + Accept: 'application/json' + } + } + ), + (error: any) => { + const { data } = error.response + + assert.deepStrictEqual(data, { + name: 'NotFound', + message: 'Path /no/where not found', + code: 404, + className: 'not-found' + }) + + return true + } + ) + }) - return true; + it('.teardown closes http server', async () => { + const app = koa(feathers()) + let called = false + + const server = await app.listen(8787) + + server.on('close', () => { + called = true }) - }); - it('throws a 404 NotFound JSON error', async () => { - await assert.rejects(() => axios.post('http://localhost:8465/no/where', {}, { - headers: { - 'X-Service-Method': 'internalMethod', - Accept: 'application/json' - } - }), (error: any) => { - const { data } = error.response; - - assert.deepStrictEqual(data, { - name: 'NotFound', - message: 'Not Found', - code: 404, - className: 'not-found' - }); - - return true; - }); - }); - - restTests('Services', 'todo', 8465); - restTests('Root service', '/', 8465); -}); + await app.teardown() + assert.ok(called) + }) + + restTests('Services', 'todo', 8465) + restTests('Root service', '/', 8465) +}) diff --git a/packages/memory/CHANGELOG.md b/packages/memory/CHANGELOG.md index 73105ba8e2..7a6ce726e2 100644 --- a/packages/memory/CHANGELOG.md +++ b/packages/memory/CHANGELOG.md @@ -3,182 +3,187 @@ All notable changes to this project will be documented in this file. See [Conventional Commits](https://conventionalcommits.org) for commit guidelines. -# [5.0.0-pre.16](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.15...v5.0.0-pre.16) (2022-01-12) +# [5.0.0-pre.31](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.30...v5.0.0-pre.31) (2022-10-12) -**Note:** Version bump only for package @feathersjs/memory +### Features +- **cli:** Generate full client test suite and improve typed client ([#2788](https://github.com/feathersjs/feathers/issues/2788)) ([57119b6](https://github.com/feathersjs/feathers/commit/57119b6bb2797f7297cf054268a248c093ecd538)) +# [5.0.0-pre.30](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.29...v5.0.0-pre.30) (2022-10-07) +### Features +- **core:** Allow to unregister services at runtime ([#2756](https://github.com/feathersjs/feathers/issues/2756)) ([d16601f](https://github.com/feathersjs/feathers/commit/d16601f2277dca5357866ffdefba2a611f6dc7fa)) -# [5.0.0-pre.15](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.14...v5.0.0-pre.15) (2021-11-27) +# [5.0.0-pre.29](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.28...v5.0.0-pre.29) (2022-09-16) **Note:** Version bump only for package @feathersjs/memory +# [5.0.0-pre.28](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.27...v5.0.0-pre.28) (2022-08-03) +### Bug Fixes +- **cli:** Improve generated application and client ([#2701](https://github.com/feathersjs/feathers/issues/2701)) ([bd55ffb](https://github.com/feathersjs/feathers/commit/bd55ffb812e89bf215f4515e7f137656ea888c3f)) - -# [5.0.0-pre.14](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.13...v5.0.0-pre.14) (2021-10-13) +# [5.0.0-pre.27](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.26...v5.0.0-pre.27) (2022-07-13) **Note:** Version bump only for package @feathersjs/memory +# [5.0.0-pre.26](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.25...v5.0.0-pre.26) (2022-06-22) +**Note:** Version bump only for package @feathersjs/memory - - -# [5.0.0-pre.13](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.12...v5.0.0-pre.13) (2021-10-13) +# [5.0.0-pre.25](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.24...v5.0.0-pre.25) (2022-06-22) **Note:** Version bump only for package @feathersjs/memory +# [5.0.0-pre.24](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.23...v5.0.0-pre.24) (2022-06-21) +### Features +- **cli:** Initial Feathers v5 CLI and Pinion generator ([#2578](https://github.com/feathersjs/feathers/issues/2578)) ([7f59ae7](https://github.com/feathersjs/feathers/commit/7f59ae7f1471895ba8a82aa4702f1a23f71b7682)) - -# [5.0.0-pre.12](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.11...v5.0.0-pre.12) (2021-10-12) +# [5.0.0-pre.23](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.22...v5.0.0-pre.23) (2022-06-06) **Note:** Version bump only for package @feathersjs/memory +# [5.0.0-pre.22](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.21...v5.0.0-pre.22) (2022-05-24) +**Note:** Version bump only for package @feathersjs/memory - - -# [5.0.0-pre.11](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.10...v5.0.0-pre.11) (2021-10-06) +# [5.0.0-pre.21](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.20...v5.0.0-pre.21) (2022-05-23) **Note:** Version bump only for package @feathersjs/memory +# [5.0.0-pre.20](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.19...v5.0.0-pre.20) (2022-05-04) +### Bug Fixes +- **dependencies:** Lock monorepo package version numbers ([#2623](https://github.com/feathersjs/feathers/issues/2623)) ([5640c10](https://github.com/feathersjs/feathers/commit/5640c1020cc139994e695d658c08bad3494db507)) +# [5.0.0-pre.19](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.18...v5.0.0-pre.19) (2022-05-01) -# [5.0.0-pre.10](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.9...v5.0.0-pre.10) (2021-09-19) +### Bug Fixes +- **adapter-commons:** Clarify adapter query filtering ([#2607](https://github.com/feathersjs/feathers/issues/2607)) ([2dac771](https://github.com/feathersjs/feathers/commit/2dac771b0a3298d6dd25994d05186701b0617718)) ### Features -* **schema:** Initial version of schema definitions and resolvers ([#2441](https://github.com/feathersjs/feathers/issues/2441)) ([c57a5cd](https://github.com/feathersjs/feathers/commit/c57a5cd56699a121647be4506d8f967e6d72ecae)) +- **mongodb:** Add feathers-mongodb adapter as @feathersjs/mongodb ([#2610](https://github.com/feathersjs/feathers/issues/2610)) ([6d43734](https://github.com/feathersjs/feathers/commit/6d43734a53db02c435cafc52a22dca414e5d0940)) +- **typescript:** Improve adapter typings ([#2605](https://github.com/feathersjs/feathers/issues/2605)) ([3b2ca0a](https://github.com/feathersjs/feathers/commit/3b2ca0a6a8e03e8390272c4d7e930b4bffdaacf5)) +- **typescript:** Improve params and query typeability ([#2600](https://github.com/feathersjs/feathers/issues/2600)) ([df28b76](https://github.com/feathersjs/feathers/commit/df28b7619161f1df5e700326f52cca1a92dc5d28)) + +### BREAKING CHANGES +- **adapter-commons:** Changes the common adapter base class to use `sanitizeQuery` and `sanitizeData` +# [5.0.0-pre.18](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.17...v5.0.0-pre.18) (2022-04-11) +### Bug Fixes +- **adapter-tests:** Add tests for pagination in multi updates ([#2472](https://github.com/feathersjs/feathers/issues/2472)) ([98a811a](https://github.com/feathersjs/feathers/commit/98a811ac605575ff812a08d0504729a5efe7a69c)) -# [5.0.0-pre.9](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.8...v5.0.0-pre.9) (2021-08-09) +# [5.0.0-pre.17](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.16...v5.0.0-pre.17) (2022-02-15) **Note:** Version bump only for package @feathersjs/memory +# [5.0.0-pre.16](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.15...v5.0.0-pre.16) (2022-01-12) +**Note:** Version bump only for package @feathersjs/memory +# [5.0.0-pre.15](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.14...v5.0.0-pre.15) (2021-11-27) +**Note:** Version bump only for package @feathersjs/memory -# [5.0.0-pre.8](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.7...v5.0.0-pre.8) (2021-08-09) +# [5.0.0-pre.14](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.13...v5.0.0-pre.14) (2021-10-13) **Note:** Version bump only for package @feathersjs/memory +# [5.0.0-pre.13](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.12...v5.0.0-pre.13) (2021-10-13) +**Note:** Version bump only for package @feathersjs/memory +# [5.0.0-pre.12](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.11...v5.0.0-pre.12) (2021-10-12) +**Note:** Version bump only for package @feathersjs/memory -# [5.0.0-pre.7](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.6...v5.0.0-pre.7) (2021-08-09) +# [5.0.0-pre.11](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.10...v5.0.0-pre.11) (2021-10-06) **Note:** Version bump only for package @feathersjs/memory +# [5.0.0-pre.10](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.9...v5.0.0-pre.10) (2021-09-19) +### Features +- **schema:** Initial version of schema definitions and resolvers ([#2441](https://github.com/feathersjs/feathers/issues/2441)) ([c57a5cd](https://github.com/feathersjs/feathers/commit/c57a5cd56699a121647be4506d8f967e6d72ecae)) +# [5.0.0-pre.9](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.8...v5.0.0-pre.9) (2021-08-09) -# [5.0.0-pre.6](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.5...v5.0.0-pre.6) (2021-08-08) +**Note:** Version bump only for package @feathersjs/memory + +# [5.0.0-pre.8](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.7...v5.0.0-pre.8) (2021-08-09) **Note:** Version bump only for package @feathersjs/memory +# [5.0.0-pre.7](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.6...v5.0.0-pre.7) (2021-08-09) +**Note:** Version bump only for package @feathersjs/memory +# [5.0.0-pre.6](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.5...v5.0.0-pre.6) (2021-08-08) +**Note:** Version bump only for package @feathersjs/memory # [5.0.0-pre.5](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.4...v5.0.0-pre.5) (2021-06-23) - ### Bug Fixes -* Update database adapter common repository urls ([#2380](https://github.com/feathersjs/feathers/issues/2380)) ([3f4db68](https://github.com/feathersjs/feathers/commit/3f4db68d6700c7d9023ecd17d0d39893f75a19fd)) - +- Update database adapter common repository urls ([#2380](https://github.com/feathersjs/feathers/issues/2380)) ([3f4db68](https://github.com/feathersjs/feathers/commit/3f4db68d6700c7d9023ecd17d0d39893f75a19fd)) ### Features -* **adapter-commons:** Add support for params.adapter option and move memory adapter to @feathersjs/memory ([#2367](https://github.com/feathersjs/feathers/issues/2367)) ([a43e7da](https://github.com/feathersjs/feathers/commit/a43e7da22b6b981a96d1321736ea9a0cb924fb4f)) -* **typescript:** Allow to pass generic service options to adapter services ([#2392](https://github.com/feathersjs/feathers/issues/2392)) ([f9431f2](https://github.com/feathersjs/feathers/commit/f9431f242354f804cafb835519f98dd405ac4f0b)) - - - - +- **adapter-commons:** Add support for params.adapter option and move memory adapter to @feathersjs/memory ([#2367](https://github.com/feathersjs/feathers/issues/2367)) ([a43e7da](https://github.com/feathersjs/feathers/commit/a43e7da22b6b981a96d1321736ea9a0cb924fb4f)) +- **typescript:** Allow to pass generic service options to adapter services ([#2392](https://github.com/feathersjs/feathers/issues/2392)) ([f9431f2](https://github.com/feathersjs/feathers/commit/f9431f242354f804cafb835519f98dd405ac4f0b)) # [5.0.0-pre.4](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.3...v5.0.0-pre.4) (2021-05-13) - ### Features -* **koa:** KoaJS transport adapter ([#2315](https://github.com/feathersjs/feathers/issues/2315)) ([2554b57](https://github.com/feathersjs/feathers/commit/2554b57cf05731df58feeba9c12faab18e442107)) - - - - +- **koa:** KoaJS transport adapter ([#2315](https://github.com/feathersjs/feathers/issues/2315)) ([2554b57](https://github.com/feathersjs/feathers/commit/2554b57cf05731df58feeba9c12faab18e442107)) # [5.0.0-pre.3](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.2...v5.0.0-pre.3) (2021-04-21) - ### Bug Fixes -* **typescript:** Improve TypeScript backwards compatibility ([#2310](https://github.com/feathersjs/feathers/issues/2310)) ([f33be73](https://github.com/feathersjs/feathers/commit/f33be73fc46a533efb15df9aab0658e3240d3897)) - - - - +- **typescript:** Improve TypeScript backwards compatibility ([#2310](https://github.com/feathersjs/feathers/issues/2310)) ([f33be73](https://github.com/feathersjs/feathers/commit/f33be73fc46a533efb15df9aab0658e3240d3897)) # [5.0.0-pre.2](https://github.com/feathersjs/feathers/compare/v5.0.0-beta.1...v5.0.0-pre.2) (2021-04-06) **Note:** Version bump only for package @feathersjs/memory - - - - # [5.0.0-beta.1](https://github.com/feathersjs/feathers/compare/v5.0.0-beta.0...v5.0.0-beta.1) (2021-04-03) **Note:** Version bump only for package @feathersjs/memory - - - - # [5.0.0-beta.0](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.1...v5.0.0-beta.0) (2021-03-28) - ### Bug Fixes -* Update Grant usage and other dependencies ([#2264](https://github.com/feathersjs/feathers/issues/2264)) ([7b0f8fa](https://github.com/feathersjs/feathers/commit/7b0f8fad252419ed0ad0bf259cdf3104d322ab60)) - +- Update Grant usage and other dependencies ([#2264](https://github.com/feathersjs/feathers/issues/2264)) ([7b0f8fa](https://github.com/feathersjs/feathers/commit/7b0f8fad252419ed0ad0bf259cdf3104d322ab60)) ### Features -* Feathers v5 core refactoring and features ([#2255](https://github.com/feathersjs/feathers/issues/2255)) ([2dafb7c](https://github.com/feathersjs/feathers/commit/2dafb7ce14ba57406aeec13d10ca45b1e709bee9)) - - - - +- Feathers v5 core refactoring and features ([#2255](https://github.com/feathersjs/feathers/issues/2255)) ([2dafb7c](https://github.com/feathersjs/feathers/commit/2dafb7ce14ba57406aeec13d10ca45b1e709bee9)) # [5.0.0-pre.1](https://github.com/feathersjs/feathers/compare/v4.5.11...v5.0.0-pre.1) (2020-12-17) - ### Features -* **memory:** Move feathers-memory into @feathersjs/memory ([#2153](https://github.com/feathersjs/feathers/issues/2153)) ([dd61fe3](https://github.com/feathersjs/feathers/commit/dd61fe371fb0502f78b8ccbe1f45a030e31ecff6)) - - - - +- **memory:** Move feathers-memory into @feathersjs/memory ([#2153](https://github.com/feathersjs/feathers/issues/2153)) ([dd61fe3](https://github.com/feathersjs/feathers/commit/dd61fe371fb0502f78b8ccbe1f45a030e31ecff6)) # Change Log ## [v4.1.0](https://github.com/feathersjs-ecosystem/feathers-memory/tree/v4.1.0) (2019-10-07) + [Full Changelog](https://github.com/feathersjs-ecosystem/feathers-memory/compare/v4.0.1...v4.1.0) **Merged pull requests:** @@ -186,6 +191,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Update all dependencies [\#104](https://github.com/feathersjs-ecosystem/feathers-memory/pull/104) ([daffl](https://github.com/daffl)) ## [v4.0.1](https://github.com/feathersjs-ecosystem/feathers-memory/tree/v4.0.1) (2019-09-29) + [Full Changelog](https://github.com/feathersjs-ecosystem/feathers-memory/compare/v4.0.0...v4.0.1) **Closed issues:** @@ -201,6 +207,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Greenkeeper/webpack 4.36.1 [\#99](https://github.com/feathersjs-ecosystem/feathers-memory/pull/99) ([daffl](https://github.com/daffl)) ## [v4.0.0](https://github.com/feathersjs-ecosystem/feathers-memory/tree/v4.0.0) (2019-07-05) + [Full Changelog](https://github.com/feathersjs-ecosystem/feathers-memory/compare/v3.0.2...v4.0.0) **Merged pull requests:** @@ -209,6 +216,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Update mocha to the latest version 🚀 [\#94](https://github.com/feathersjs-ecosystem/feathers-memory/pull/94) ([greenkeeper[bot]](https://github.com/apps/greenkeeper)) ## [v3.0.2](https://github.com/feathersjs-ecosystem/feathers-memory/tree/v3.0.2) (2019-01-24) + [Full Changelog](https://github.com/feathersjs-ecosystem/feathers-memory/compare/v3.0.1...v3.0.2) **Closed issues:** @@ -222,6 +230,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Update @feathersjs/adapter-commons to the latest version 🚀 [\#90](https://github.com/feathersjs-ecosystem/feathers-memory/pull/90) ([greenkeeper[bot]](https://github.com/apps/greenkeeper)) ## [v3.0.1](https://github.com/feathersjs-ecosystem/feathers-memory/tree/v3.0.1) (2018-12-29) + [Full Changelog](https://github.com/feathersjs-ecosystem/feathers-memory/compare/v3.0.0...v3.0.1) **Merged pull requests:** @@ -229,6 +238,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Add default params to hook-less methods [\#89](https://github.com/feathersjs-ecosystem/feathers-memory/pull/89) ([daffl](https://github.com/daffl)) ## [v3.0.0](https://github.com/feathersjs-ecosystem/feathers-memory/tree/v3.0.0) (2018-12-17) + [Full Changelog](https://github.com/feathersjs-ecosystem/feathers-memory/compare/v2.2.0...v3.0.0) **Closed issues:** @@ -244,6 +254,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Update babel-loader to the latest version 🚀 [\#81](https://github.com/feathersjs-ecosystem/feathers-memory/pull/81) ([greenkeeper[bot]](https://github.com/apps/greenkeeper)) ## [v2.2.0](https://github.com/feathersjs-ecosystem/feathers-memory/tree/v2.2.0) (2018-08-26) + [Full Changelog](https://github.com/feathersjs-ecosystem/feathers-memory/compare/v2.1.3...v2.2.0) **Closed issues:** @@ -257,6 +268,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Update sift to the latest version 🚀 [\#76](https://github.com/feathersjs-ecosystem/feathers-memory/pull/76) ([greenkeeper[bot]](https://github.com/apps/greenkeeper)) ## [v2.1.3](https://github.com/feathersjs-ecosystem/feathers-memory/tree/v2.1.3) (2018-06-11) + [Full Changelog](https://github.com/feathersjs-ecosystem/feathers-memory/compare/v2.1.2...v2.1.3) **Closed issues:** @@ -269,6 +281,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Update shx to the latest version 🚀 [\#73](https://github.com/feathersjs-ecosystem/feathers-memory/pull/73) ([greenkeeper[bot]](https://github.com/apps/greenkeeper)) ## [v2.1.2](https://github.com/feathersjs-ecosystem/feathers-memory/tree/v2.1.2) (2018-06-03) + [Full Changelog](https://github.com/feathersjs-ecosystem/feathers-memory/compare/v2.1.1...v2.1.2) **Merged pull requests:** @@ -277,6 +290,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Update clone-deep to the latest version 🚀 [\#70](https://github.com/feathersjs-ecosystem/feathers-memory/pull/70) ([greenkeeper[bot]](https://github.com/apps/greenkeeper)) ## [v2.1.1](https://github.com/feathersjs-ecosystem/feathers-memory/tree/v2.1.1) (2018-03-07) + [Full Changelog](https://github.com/feathersjs-ecosystem/feathers-memory/compare/v2.1.0...v2.1.1) **Closed issues:** @@ -291,6 +305,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Update semistandard to the latest version 🚀 [\#65](https://github.com/feathersjs-ecosystem/feathers-memory/pull/65) ([greenkeeper[bot]](https://github.com/apps/greenkeeper)) ## [v2.1.0](https://github.com/feathersjs-ecosystem/feathers-memory/tree/v2.1.0) (2017-12-03) + [Full Changelog](https://github.com/feathersjs-ecosystem/feathers-memory/compare/v2.0.0...v2.1.0) **Merged pull requests:** @@ -298,6 +313,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Use namespaced module name for exporting [\#64](https://github.com/feathersjs-ecosystem/feathers-memory/pull/64) ([daffl](https://github.com/daffl)) ## [v2.0.0](https://github.com/feathersjs-ecosystem/feathers-memory/tree/v2.0.0) (2017-12-03) + [Full Changelog](https://github.com/feathersjs-ecosystem/feathers-memory/compare/v1.3.1...v2.0.0) **Merged pull requests:** @@ -308,6 +324,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Update clone-deep to the latest version 🚀 [\#60](https://github.com/feathersjs-ecosystem/feathers-memory/pull/60) ([greenkeeper[bot]](https://github.com/apps/greenkeeper)) ## [v1.3.1](https://github.com/feathersjs-ecosystem/feathers-memory/tree/v1.3.1) (2017-10-20) + [Full Changelog](https://github.com/feathersjs-ecosystem/feathers-memory/compare/v1.3.0...v1.3.1) **Closed issues:** @@ -320,6 +337,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Do not select the id by default [\#59](https://github.com/feathersjs-ecosystem/feathers-memory/pull/59) ([daffl](https://github.com/daffl)) ## [v1.3.0](https://github.com/feathersjs-ecosystem/feathers-memory/tree/v1.3.0) (2017-10-19) + [Full Changelog](https://github.com/feathersjs-ecosystem/feathers-memory/compare/v1.2.1...v1.3.0) **Merged pull requests:** @@ -328,9 +346,11 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Update mocha to the latest version 🚀 [\#56](https://github.com/feathersjs-ecosystem/feathers-memory/pull/56) ([greenkeeper[bot]](https://github.com/apps/greenkeeper)) ## [v1.2.1](https://github.com/feathersjs-ecosystem/feathers-memory/tree/v1.2.1) (2017-09-13) + [Full Changelog](https://github.com/feathersjs-ecosystem/feathers-memory/compare/v1.2.0...v1.2.1) ## [v1.2.0](https://github.com/feathersjs-ecosystem/feathers-memory/tree/v1.2.0) (2017-09-13) + [Full Changelog](https://github.com/feathersjs-ecosystem/feathers-memory/compare/v1.1.0...v1.2.0) **Closed issues:** @@ -346,6 +366,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Update dependencies to enable Greenkeeper 🌴 [\#48](https://github.com/feathersjs-ecosystem/feathers-memory/pull/48) ([greenkeeper[bot]](https://github.com/apps/greenkeeper)) ## [v1.1.0](https://github.com/feathersjs-ecosystem/feathers-memory/tree/v1.1.0) (2017-01-31) + [Full Changelog](https://github.com/feathersjs-ecosystem/feathers-memory/compare/v1.0.1...v1.1.0) **Merged pull requests:** @@ -354,6 +375,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Change `var` to `const`, fix a mistake with `feathers-memory` requiring [\#46](https://github.com/feathersjs-ecosystem/feathers-memory/pull/46) ([osenvosem](https://github.com/osenvosem)) ## [v1.0.1](https://github.com/feathersjs-ecosystem/feathers-memory/tree/v1.0.1) (2016-11-15) + [Full Changelog](https://github.com/feathersjs-ecosystem/feathers-memory/compare/v1.0.0...v1.0.1) **Merged pull requests:** @@ -361,6 +383,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - feathers-service-tests@0.9.1 breaks build 🚨 [\#45](https://github.com/feathersjs-ecosystem/feathers-memory/pull/45) ([greenkeeperio-bot](https://github.com/greenkeeperio-bot)) ## [v1.0.0](https://github.com/feathersjs-ecosystem/feathers-memory/tree/v1.0.0) (2016-11-11) + [Full Changelog](https://github.com/feathersjs-ecosystem/feathers-memory/compare/v0.8.1...v1.0.0) **Closed issues:** @@ -373,6 +396,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Update feathers-commons to version 0.8.0 🚀 [\#43](https://github.com/feathersjs-ecosystem/feathers-memory/pull/43) ([greenkeeperio-bot](https://github.com/greenkeeperio-bot)) ## [v0.8.1](https://github.com/feathersjs-ecosystem/feathers-memory/tree/v0.8.1) (2016-11-02) + [Full Changelog](https://github.com/feathersjs-ecosystem/feathers-memory/compare/v0.8.0...v0.8.1) **Merged pull requests:** @@ -385,6 +409,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Update feathers-service-tests to version 0.8.0 🚀 [\#32](https://github.com/feathersjs-ecosystem/feathers-memory/pull/32) ([greenkeeperio-bot](https://github.com/greenkeeperio-bot)) ## [v0.8.0](https://github.com/feathersjs-ecosystem/feathers-memory/tree/v0.8.0) (2016-09-08) + [Full Changelog](https://github.com/feathersjs-ecosystem/feathers-memory/compare/v0.7.5...v0.8.0) **Closed issues:** @@ -397,9 +422,11 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Update mocha to version 3.0.0 🚀 [\#29](https://github.com/feathersjs-ecosystem/feathers-memory/pull/29) ([greenkeeperio-bot](https://github.com/greenkeeperio-bot)) ## [v0.7.5](https://github.com/feathersjs-ecosystem/feathers-memory/tree/v0.7.5) (2016-07-25) + [Full Changelog](https://github.com/feathersjs-ecosystem/feathers-memory/compare/v0.7.4...v0.7.5) ## [v0.7.4](https://github.com/feathersjs-ecosystem/feathers-memory/tree/v0.7.4) (2016-07-21) + [Full Changelog](https://github.com/feathersjs-ecosystem/feathers-memory/compare/v0.7.3...v0.7.4) **Merged pull requests:** @@ -407,6 +434,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Update feathers-query-filters to version 2.0.0 🚀 [\#28](https://github.com/feathersjs-ecosystem/feathers-memory/pull/28) ([greenkeeperio-bot](https://github.com/greenkeeperio-bot)) ## [v0.7.3](https://github.com/feathersjs-ecosystem/feathers-memory/tree/v0.7.3) (2016-06-16) + [Full Changelog](https://github.com/feathersjs-ecosystem/feathers-memory/compare/v0.7.2...v0.7.3) **Merged pull requests:** @@ -414,6 +442,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Update feathers-service-tests to version 0.6.0 🚀 [\#27](https://github.com/feathersjs-ecosystem/feathers-memory/pull/27) ([greenkeeperio-bot](https://github.com/greenkeeperio-bot)) ## [v0.7.2](https://github.com/feathersjs-ecosystem/feathers-memory/tree/v0.7.2) (2016-06-14) + [Full Changelog](https://github.com/feathersjs-ecosystem/feathers-memory/compare/v0.7.1...v0.7.2) **Closed issues:** @@ -427,9 +456,11 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Update babel-plugin-add-module-exports to version 0.2.0 🚀 [\#24](https://github.com/feathersjs-ecosystem/feathers-memory/pull/24) ([greenkeeperio-bot](https://github.com/greenkeeperio-bot)) ## [v0.7.1](https://github.com/feathersjs-ecosystem/feathers-memory/tree/v0.7.1) (2016-04-05) + [Full Changelog](https://github.com/feathersjs-ecosystem/feathers-memory/compare/v0.7.0...v0.7.1) ## [v0.7.0](https://github.com/feathersjs-ecosystem/feathers-memory/tree/v0.7.0) (2016-04-04) + [Full Changelog](https://github.com/feathersjs-ecosystem/feathers-memory/compare/v0.6.3...v0.7.0) **Merged pull requests:** @@ -437,6 +468,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Move to feathers-commons utilities [\#20](https://github.com/feathersjs-ecosystem/feathers-memory/pull/20) ([daffl](https://github.com/daffl)) ## [v0.6.3](https://github.com/feathersjs-ecosystem/feathers-memory/tree/v0.6.3) (2016-02-25) + [Full Changelog](https://github.com/feathersjs-ecosystem/feathers-memory/compare/v0.6.2...v0.6.3) **Closed issues:** @@ -448,6 +480,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Use individual Lodash methods [\#19](https://github.com/feathersjs-ecosystem/feathers-memory/pull/19) ([daffl](https://github.com/daffl)) ## [v0.6.2](https://github.com/feathersjs-ecosystem/feathers-memory/tree/v0.6.2) (2016-02-24) + [Full Changelog](https://github.com/feathersjs-ecosystem/feathers-memory/compare/v0.6.1...v0.6.2) **Merged pull requests:** @@ -455,6 +488,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - bumping feathers-errors version [\#16](https://github.com/feathersjs-ecosystem/feathers-memory/pull/16) ([ekryski](https://github.com/ekryski)) ## [v0.6.1](https://github.com/feathersjs-ecosystem/feathers-memory/tree/v0.6.1) (2016-02-22) + [Full Changelog](https://github.com/feathersjs-ecosystem/feathers-memory/compare/v0.6.0...v0.6.1) **Merged pull requests:** @@ -462,6 +496,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Exmaple update [\#15](https://github.com/feathersjs-ecosystem/feathers-memory/pull/15) ([ekryski](https://github.com/ekryski)) ## [v0.6.0](https://github.com/feathersjs-ecosystem/feathers-memory/tree/v0.6.0) (2016-01-30) + [Full Changelog](https://github.com/feathersjs-ecosystem/feathers-memory/compare/v0.5.3...v0.6.0) **Merged pull requests:** @@ -469,9 +504,11 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Use internal methods instead of service methods directly [\#13](https://github.com/feathersjs-ecosystem/feathers-memory/pull/13) ([daffl](https://github.com/daffl)) ## [v0.5.3](https://github.com/feathersjs-ecosystem/feathers-memory/tree/v0.5.3) (2016-01-23) + [Full Changelog](https://github.com/feathersjs-ecosystem/feathers-memory/compare/v0.5.2...v0.5.3) ## [v0.5.2](https://github.com/feathersjs-ecosystem/feathers-memory/tree/v0.5.2) (2016-01-23) + [Full Changelog](https://github.com/feathersjs-ecosystem/feathers-memory/compare/v0.5.1...v0.5.2) **Merged pull requests:** @@ -479,12 +516,15 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Adding nsp check [\#12](https://github.com/feathersjs-ecosystem/feathers-memory/pull/12) ([marshallswain](https://github.com/marshallswain)) ## [v0.5.1](https://github.com/feathersjs-ecosystem/feathers-memory/tree/v0.5.1) (2015-12-19) + [Full Changelog](https://github.com/feathersjs-ecosystem/feathers-memory/compare/v0.5.0...v0.5.1) ## [v0.5.0](https://github.com/feathersjs-ecosystem/feathers-memory/tree/v0.5.0) (2015-12-03) + [Full Changelog](https://github.com/feathersjs-ecosystem/feathers-memory/compare/v0.4.1...v0.5.0) ## [v0.4.1](https://github.com/feathersjs-ecosystem/feathers-memory/tree/v0.4.1) (2015-12-03) + [Full Changelog](https://github.com/feathersjs-ecosystem/feathers-memory/compare/v0.4.0...v0.4.1) **Merged pull requests:** @@ -492,6 +532,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Use ES6 classes, Promises and support pagination [\#11](https://github.com/feathersjs-ecosystem/feathers-memory/pull/11) ([daffl](https://github.com/daffl)) ## [v0.4.0](https://github.com/feathersjs-ecosystem/feathers-memory/tree/v0.4.0) (2015-11-07) + [Full Changelog](https://github.com/feathersjs-ecosystem/feathers-memory/compare/0.3.4...v0.4.0) **Closed issues:** @@ -507,6 +548,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Added support for simple query in find [\#6](https://github.com/feathersjs-ecosystem/feathers-memory/pull/6) ([ruimgoncalves](https://github.com/ruimgoncalves)) ## [0.3.4](https://github.com/feathersjs-ecosystem/feathers-memory/tree/0.3.4) (2014-09-25) + [Full Changelog](https://github.com/feathersjs-ecosystem/feathers-memory/compare/0.3.3...0.3.4) **Closed issues:** @@ -514,12 +556,15 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Query and persisting Data [\#5](https://github.com/feathersjs-ecosystem/feathers-memory/issues/5) ## [0.3.3](https://github.com/feathersjs-ecosystem/feathers-memory/tree/0.3.3) (2014-06-13) + [Full Changelog](https://github.com/feathersjs-ecosystem/feathers-memory/compare/0.3.2...0.3.3) ## [0.3.2](https://github.com/feathersjs-ecosystem/feathers-memory/tree/0.3.2) (2014-06-13) + [Full Changelog](https://github.com/feathersjs-ecosystem/feathers-memory/compare/0.3.1...0.3.2) ## [0.3.1](https://github.com/feathersjs-ecosystem/feathers-memory/tree/0.3.1) (2014-06-13) + [Full Changelog](https://github.com/feathersjs-ecosystem/feathers-memory/compare/0.3.0...0.3.1) **Closed issues:** @@ -529,18 +574,21 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Need to return proper errors [\#1](https://github.com/feathersjs-ecosystem/feathers-memory/issues/1) ## [0.3.0](https://github.com/feathersjs-ecosystem/feathers-memory/tree/0.3.0) (2014-06-05) + [Full Changelog](https://github.com/feathersjs-ecosystem/feathers-memory/compare/0.2.1...0.3.0) ## [0.2.1](https://github.com/feathersjs-ecosystem/feathers-memory/tree/0.2.1) (2014-06-04) + [Full Changelog](https://github.com/feathersjs-ecosystem/feathers-memory/compare/0.2.0...0.2.1) ## [0.2.0](https://github.com/feathersjs-ecosystem/feathers-memory/tree/0.2.0) (2014-04-22) + [Full Changelog](https://github.com/feathersjs-ecosystem/feathers-memory/compare/0.1.2...0.2.0) ## [0.1.2](https://github.com/feathersjs-ecosystem/feathers-memory/tree/0.1.2) (2014-04-11) + [Full Changelog](https://github.com/feathersjs-ecosystem/feathers-memory/compare/0.1.1...0.1.2) ## [0.1.1](https://github.com/feathersjs-ecosystem/feathers-memory/tree/0.1.1) (2014-04-11) - -\* *This Change Log was automatically generated by [github_changelog_generator](https://github.com/skywinder/Github-Changelog-Generator)* +\* _This Change Log was automatically generated by [github_changelog_generator](https://github.com/skywinder/Github-Changelog-Generator)_ diff --git a/packages/memory/LICENSE b/packages/memory/LICENSE index 3f395cc665..59604f46f3 100644 --- a/packages/memory/LICENSE +++ b/packages/memory/LICENSE @@ -1,6 +1,6 @@ The MIT License (MIT) -Copyright (c) 2021 Feathers +Copyright (c) 2022 Feathers Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated documentation files (the "Software"), to deal diff --git a/packages/memory/README.md b/packages/memory/README.md index 6bc0191b01..065921d51b 100644 --- a/packages/memory/README.md +++ b/packages/memory/README.md @@ -1,8 +1,8 @@ # @feathersjs/memory [![CI](https://github.com/feathersjs/feathers/workflows/CI/badge.svg)](https://github.com/feathersjs/feathers/actions?query=workflow%3ACI) -[![Dependency Status](https://img.shields.io/david/feathersjs/feathers.svg?style=flat-square&path=packages/memory)](https://david-dm.org/feathersjs/feathers?path=packages/memory) [![Download Status](https://img.shields.io/npm/dm/@feathersjs/memory.svg?style=flat-square)](https://www.npmjs.com/package/@feathersjs/memory) +[![Discord](https://badgen.net/badge/icon/discord?icon=discord&label)](https://discord.gg/qa8kez8QBx) A [Feathers](https://feathersjs.com) service adapter for in-memory data storage that works on all platforms. @@ -92,6 +92,6 @@ Run the example with `node app` and go to [localhost:3030/messages](http://local ## License -Copyright (c) 2021 [Feathers contributors](https://github.com/feathersjs/feathers/graphs/contributors) +Copyright (c) 2022 [Feathers contributors](https://github.com/feathersjs/feathers/graphs/contributors) Licensed under the [MIT license](LICENSE). diff --git a/packages/memory/package.json b/packages/memory/package.json index cc780ca084..35a4be5448 100644 --- a/packages/memory/package.json +++ b/packages/memory/package.json @@ -1,9 +1,10 @@ { "name": "@feathersjs/memory", "description": "An in memory service store", - "version": "5.0.0-pre.16", + "version": "5.0.0-pre.31", "homepage": "https://github.com/feathersjs/feathers", "main": "lib/", + "types": "lib/", "keywords": [ "feathers", "feathers-plugin" @@ -11,7 +12,8 @@ "license": "MIT", "repository": { "type": "git", - "url": "git://github.com/feathersjs/feathers.git" + "url": "git://github.com/feathersjs/feathers.git", + "directory": "packages/memory" }, "author": { "name": "Feathers contributors", @@ -29,15 +31,16 @@ "CHANGELOG.md", "LICENSE", "README.md", + "_templates/**", "src/**", "lib/**", "*.js" ], "scripts": { "prepublish": "npm run compile", - "compile": "shx rm -rf lib/ && tsc", - "test": "npm run compile && npm run mocha", - "mocha": "mocha --config ../../.mocharc.json --recursive test/**.test.ts test/**/*.test.ts" + "pack": "npm pack --pack-destination ../cli/test/build", + "compile": "shx rm -rf lib/ && tsc && npm run pack", + "test": "mocha --config ../../.mocharc.json --recursive test/**/*.test.ts" }, "publishConfig": { "access": "public" @@ -46,20 +49,20 @@ "lib": "lib" }, "dependencies": { - "@feathersjs/adapter-commons": "^5.0.0-pre.16", - "@feathersjs/commons": "^5.0.0-pre.16", - "@feathersjs/errors": "^5.0.0-pre.16", - "sift": "^15.1.3" + "@feathersjs/adapter-commons": "^5.0.0-pre.31", + "@feathersjs/commons": "^5.0.0-pre.31", + "@feathersjs/errors": "^5.0.0-pre.31", + "sift": "^16.0.0" }, "devDependencies": { - "@feathersjs/adapter-tests": "^5.0.0-pre.16", - "@feathersjs/feathers": "^5.0.0-pre.16", - "@types/mocha": "^9.0.0", - "@types/node": "^17.0.5", - "mocha": "^9.1.3", - "shx": "^0.3.3", - "ts-node": "^10.4.0", - "typescript": "^4.5.4" + "@feathersjs/adapter-tests": "^5.0.0-pre.31", + "@feathersjs/feathers": "^5.0.0-pre.31", + "@types/mocha": "^10.0.0", + "@types/node": "^18.8.2", + "mocha": "^10.0.0", + "shx": "^0.3.4", + "ts-node": "^10.9.1", + "typescript": "^4.8.4" }, - "gitHead": "f0cd227a82d159b528193bd33747c97684a48773" + "gitHead": "4500dbeb8cea566678cf88b3313a88efd93a2ed9" } diff --git a/packages/memory/src/index.ts b/packages/memory/src/index.ts index 061c00b6c3..a4a3b10d1a 100644 --- a/packages/memory/src/index.ts +++ b/packages/memory/src/index.ts @@ -1,156 +1,239 @@ -import { NotFound } from '@feathersjs/errors'; -import { _ } from '@feathersjs/commons'; -import { sorter, select, AdapterService, ServiceOptions, InternalServiceMethods, AdapterParams } from '@feathersjs/adapter-commons'; -import sift from 'sift'; -import { NullableId, Id } from '@feathersjs/feathers'; +import { NotFound } from '@feathersjs/errors' +import { _ } from '@feathersjs/commons' +import { + sorter, + select, + AdapterBase, + AdapterServiceOptions, + PaginationOptions, + AdapterParams +} from '@feathersjs/adapter-commons' +import sift from 'sift' +import { NullableId, Id, Params, ServiceMethods, Paginated } from '@feathersjs/feathers' export interface MemoryServiceStore { - [key: string]: T; + [key: string]: T } -export interface MemoryServiceOptions extends ServiceOptions { - store: MemoryServiceStore; - startId: number; - matcher?: (query: any) => any; - sorter?: (sort: any) => any; +export interface MemoryServiceOptions extends AdapterServiceOptions { + store?: MemoryServiceStore + startId?: number + matcher?: (query: any) => any + sorter?: (sort: any) => any } const _select = (data: any, params: any, ...args: any[]) => { - const base = select(params, ...args); + const base = select(params, ...args) - return base(JSON.parse(JSON.stringify(data))); -}; - -export class Service> extends AdapterService implements InternalServiceMethods { - options: MemoryServiceOptions; - store: MemoryServiceStore; - _uId: number; + return base(JSON.parse(JSON.stringify(data))) +} - constructor (options: Partial> = {}) { - super(_.extend({ +export class MemoryAdapter, P extends Params = Params> extends AdapterBase< + T, + D, + P, + MemoryServiceOptions +> { + store: MemoryServiceStore + _uId: number + + constructor(options: MemoryServiceOptions = {}) { + super({ id: 'id', matcher: sift, - sorter - }, options)); - this._uId = options.startId || 0; - this.store = options.store || {}; + sorter, + store: {}, + startId: 0, + ...options + }) + this._uId = this.options.startId + this.store = { ...this.options.store } + } + + async getEntries(_params?: P) { + const params = _params || ({} as P) + + return this.$find({ + ...params, + paginate: false + }) } - async getEntries (params = {}) { - const { query } = this.filterQuery(params); + getQuery(params: P) { + const { $skip, $sort, $limit, $select, ...query } = params.query || {} - return this._find(Object.assign({}, params, { - paginate: false, - query - }) as any) as Promise; + return { + query, + filters: { $skip, $sort, $limit, $select } + } } - async _find (params: AdapterParams = {}) { - const { query, filters, paginate } = this.filterQuery(params); - let values = _.values(this.store).filter(this.options.matcher(query)); - const total = values.length; + async $find(_params?: P & { paginate?: PaginationOptions }): Promise> + async $find(_params?: P & { paginate: false }): Promise + async $find(_params?: P): Promise | T[]> + async $find(params: P = {} as P): Promise | T[]> { + const { paginate } = this.getOptions(params) + const { query, filters } = this.getQuery(params) + + let values = _.values(this.store).filter(this.options.matcher(query)) + const total = values.length if (filters.$sort !== undefined) { - values.sort(this.options.sorter(filters.$sort)); + values.sort(this.options.sorter(filters.$sort)) } if (filters.$skip !== undefined) { - values = values.slice(filters.$skip); + values = values.slice(filters.$skip) } if (filters.$limit !== undefined) { - values = values.slice(0, filters.$limit); + values = values.slice(0, filters.$limit) } - const result = { + const result: Paginated = { total, limit: filters.$limit, skip: filters.$skip || 0, - data: values.map(value => _select(value, params)) - }; + data: values.map((value) => _select(value, params)) + } - if (!(paginate && (paginate ).default)) { - return result.data; + if (!paginate) { + return result.data } - return result; + return result } - async _get (id: Id, params: AdapterParams = {}) { + async $get(id: Id, params: P = {} as P): Promise { + const { query } = this.getQuery(params) + if (id in this.store) { - const { query } = this.filterQuery(params); - const value = this.store[id]; + const value = this.store[id] if (this.options.matcher(query)(value)) { - return _select(value, params, this.id); + return _select(value, params, this.id) } } - throw new NotFound(`No record found for id '${id}'`); + throw new NotFound(`No record found for id '${id}'`) } - // Create without hooks and mixins that can be used internally - async _create (data: Partial | Partial[], params: AdapterParams = {}): Promise { + async $create(data: Partial, params?: P): Promise + async $create(data: Partial[], params?: P): Promise + async $create(data: Partial | Partial[], _params?: P): Promise + async $create(data: Partial | Partial[], params: P = {} as P): Promise { if (Array.isArray(data)) { - return Promise.all(data.map(current => this._create(current, params) as Promise)); + return Promise.all(data.map((current) => this.$create(current, params))) } - const id = (data as any)[this.id] || this._uId++; - const current = _.extend({}, data, { [this.id]: id }); - const result = (this.store[id] = current); + const id = (data as any)[this.id] || this._uId++ + const current = _.extend({}, data, { [this.id]: id }) + const result = (this.store[id] = current) - return _select(result, params, this.id); + return _select(result, params, this.id) as T } - async _update (id: NullableId, data: T, params: AdapterParams = {}) { - const oldEntry = await this._get(id); + async $update(id: Id, data: D, params: P = {} as P): Promise { + const oldEntry = await this.$get(id) // We don't want our id to change type if it can be coerced - const oldId = oldEntry[this.id]; + const oldId = (oldEntry as any)[this.id] // eslint-disable-next-line eqeqeq - id = oldId == id ? oldId : id; + id = oldId == id ? oldId : id - this.store[id] = _.extend({}, data, { [this.id]: id }); + this.store[id] = _.extend({}, data, { [this.id]: id }) - return this._get(id, params); + return this.$get(id, params) } - async _patch (id: NullableId, data: Partial, params: AdapterParams = {}) { + async $patch(id: null, data: Partial, params?: P): Promise + async $patch(id: Id, data: Partial, params?: P): Promise + async $patch(id: NullableId, data: Partial, _params?: P): Promise + async $patch(id: NullableId, data: Partial, params: P = {} as P): Promise { + const { query } = this.getQuery(params) const patchEntry = (entry: T) => { - const currentId = (entry as any)[this.id]; + const currentId = (entry as any)[this.id] - this.store[currentId] = _.extend(this.store[currentId], _.omit(data, this.id)); + this.store[currentId] = _.extend(this.store[currentId], _.omit(data, this.id)) - return _select(this.store[currentId], params, this.id); - }; + return _select(this.store[currentId], params, this.id) + } if (id === null) { - const entries = await this.getEntries(params); + const entries = await this.getEntries({ + ...params, + query + }) - return entries.map(patchEntry); + return entries.map(patchEntry) } - return patchEntry(await this._get(id, params)); // Will throw an error if not found + return patchEntry(await this.$get(id, params)) // Will throw an error if not found } - // Remove without hooks and mixins that can be used internally - async _remove (id: NullableId, params: AdapterParams = {}): Promise { + async $remove(id: null, params?: P): Promise + async $remove(id: Id, params?: P): Promise + async $remove(id: NullableId, _params?: P): Promise + async $remove(id: NullableId, params: P = {} as P): Promise { + const { query } = this.getQuery(params) + if (id === null) { - const entries = await this.getEntries(params); + const entries = await this.getEntries({ + ...params, + query + }) - return Promise.all(entries.map(current => - this._remove((current as any)[this.id], params) as Promise - )); + return Promise.all(entries.map((current: any) => this.$remove(current[this.id] as Id, params))) } - const entry = await this._get(id, params); + const entry = await this.$get(id, params) + + delete this.store[id] - delete this.store[id]; + return entry + } +} + +export class MemoryService, P extends AdapterParams = AdapterParams> + extends MemoryAdapter + implements ServiceMethods, D, P> +{ + async find(params?: P & { paginate?: PaginationOptions }): Promise> + async find(params?: P & { paginate: false }): Promise + async find(params?: P): Promise | T[]> + async find(params?: P): Promise | T[]> { + return this._find(params) as any + } + + async get(id: Id, params?: P): Promise { + return this._get(id, params) + } + + async create(data: D, params?: P): Promise + async create(data: D[], params?: P): Promise + async create(data: D | D[], params?: P): Promise { + return this._create(data, params) + } + + async update(id: Id, data: D, params?: P): Promise { + return this._update(id, data, params) + } + + async patch(id: Id, data: Partial, params?: P): Promise + async patch(id: null, data: Partial, params?: P): Promise + async patch(id: NullableId, data: Partial, params?: P): Promise { + return this._patch(id, data, params) + } - return entry; + async remove(id: Id, params?: P): Promise + async remove(id: null, params?: P): Promise + async remove(id: NullableId, params?: P): Promise { + return this._remove(id, params) } } -export function memory (options: Partial = {}) { - return new Service(options); +export function memory, P extends Params = Params>( + options: Partial> = {} +) { + return new MemoryService(options) } diff --git a/packages/memory/test/index.test.ts b/packages/memory/test/index.test.ts index 5f95ee5403..0084f141b2 100644 --- a/packages/memory/test/index.test.ts +++ b/packages/memory/test/index.test.ts @@ -1,9 +1,9 @@ -import assert from 'assert'; -import adapterTests from '@feathersjs/adapter-tests'; -import errors from '@feathersjs/errors'; -import { feathers } from '@feathersjs/feathers'; +import assert from 'assert' +import adapterTests from '@feathersjs/adapter-tests' +import errors from '@feathersjs/errors' +import { feathers } from '@feathersjs/feathers' -import { memory } from '../src'; +import { MemoryService } from '../src' const testSuite = adapterTests([ '.options', @@ -14,6 +14,12 @@ const testSuite = adapterTests([ '._update', '._patch', '._remove', + '.$get', + '.$find', + '.$create', + '.$update', + '.$patch', + '.$remove', '.get', '.get + $select', '.get + id + query', @@ -25,6 +31,7 @@ const testSuite = adapterTests([ '.remove + $select', '.remove + id + query', '.remove + multi', + '.remove + multi no pagination', '.remove + id + query id', '.update', '.update + $select', @@ -36,6 +43,7 @@ const testSuite = adapterTests([ '.patch + $select', '.patch + id + query', '.patch multiple', + '.patch multiple no pagination', '.patch multi query same', '.patch multi query changed', '.patch + query + NotFound', @@ -74,121 +82,147 @@ const testSuite = adapterTests([ '.find + paginate + params', 'params.adapter + paginate', 'params.adapter + multi' -]); +]) describe('Feathers Memory Service', () => { - const events = [ 'testing' ]; - const app = feathers() - .use('/people', memory({ events })) - .use('/people-customid', memory({ - id: 'customid', events - })); + type Person = { + id: number + name: string + age: number + } + + type Animal = { + type: string + age: number + } + + const events = ['testing'] + const app = feathers<{ + people: MemoryService + 'people-customid': MemoryService + animals: MemoryService + matcher: MemoryService + }>() + + app.use('people', new MemoryService({ events })) + app.use( + 'people-customid', + new MemoryService({ + id: 'customid', + events + }) + ) it('update with string id works', async () => { - const people = app.service('people'); + const people = app.service('people') const person = await people.create({ name: 'Tester', age: 33 - }); + }) - const updatedPerson: any = await people.update(person.id.toString(), person); + const updatedPerson: any = await people.update(person.id.toString(), person) - assert.strictEqual(typeof updatedPerson.id, 'number'); + assert.strictEqual(typeof updatedPerson.id, 'number') - await people.remove(person.id.toString()); - }); + await people.remove(person.id.toString()) + }) it('patch record with prop also in query', async () => { - app.use('/animals', memory({ multi: true })); - const animals = app.service('animals'); - await animals.create([{ - type: 'cat', - age: 30 - }, { - type: 'dog', - age: 10 - }]); + app.use('animals', new MemoryService({ multi: true })) + const animals = app.service('animals') + await animals.create([ + { + type: 'cat', + age: 30 + }, + { + type: 'dog', + age: 10 + } + ]) - const [updated] = await animals.patch(null, { age: 40 }, { query: { age: 30 } }); + const [updated] = await animals.patch(null, { age: 40 }, { query: { age: 30 } }) - assert.strictEqual(updated.age, 40); + assert.strictEqual(updated.age, 40) - await animals.remove(null, {}); - }); + await animals.remove(null, {}) + }) it('allows to pass custom find and sort matcher', async () => { - let sorterCalled = false; - let matcherCalled = false; - - app.use('/matcher', memory({ - matcher () { - matcherCalled = true; - return function () { - return true; - }; - }, - - sorter () { - sorterCalled = true; - return function () { - return 0; - }; - } - })); + let sorterCalled = false + let matcherCalled = false + + app.use( + 'matcher', + new MemoryService({ + matcher() { + matcherCalled = true + return function () { + return true + } + }, + + sorter() { + sorterCalled = true + return function () { + return 0 + } + } + }) + ) await app.service('matcher').find({ query: { $sort: { something: 1 } } - }); + }) - assert.ok(sorterCalled, 'sorter called'); - assert.ok(matcherCalled, 'matcher called'); - }); + assert.ok(sorterCalled, 'sorter called') + assert.ok(matcherCalled, 'matcher called') + }) it('does not modify the original data', async () => { - const people = app.service('people'); + const people = app.service('people') const person = await people.create({ name: 'Delete tester', age: 33 - }); + }) - delete person.age; + delete person.age - const otherPerson = await people.get(person.id); + const otherPerson = await people.get(person.id) - assert.strictEqual(otherPerson.age, 33); + assert.strictEqual(otherPerson.age, 33) - await people.remove(person.id); - }); + await people.remove(person.id) + }) it('does not $select the id', async () => { - const people = app.service('people'); + const people = app.service('people') const person = await people.create({ name: 'Tester' - }); + }) const results = await people.find({ + paginate: false, query: { name: 'Tester', $select: ['name'] } - }); + }) - assert.deepStrictEqual(results[0], { name: 'Tester' }, - 'deepEquals the same' - ); + assert.deepStrictEqual(results[0], { name: 'Tester' }, 'deepEquals the same') - await people.remove(person.id); - }); + await people.remove(person.id) + }) it('update with null throws error', async () => { try { - await app.service('people').update(null, {}); - throw new Error('Should never get here'); + await app.service('people').update(null, {}) + throw new Error('Should never get here') } catch (error: any) { - assert.strictEqual(error.message, 'You can not replace multiple instances. Did you mean \'patch\'?'); + assert.strictEqual(error.message, "You can not replace multiple instances. Did you mean 'patch'?") } - }); + }) - testSuite(app, errors, 'people'); - testSuite(app, errors, 'people-customid', 'customid'); -}); + testSuite(app, errors, 'people') + testSuite(app, errors, 'people-customid', 'customid') +}) diff --git a/packages/mongodb/CHANGELOG.md b/packages/mongodb/CHANGELOG.md new file mode 100644 index 0000000000..da6dce6892 --- /dev/null +++ b/packages/mongodb/CHANGELOG.md @@ -0,0 +1,73 @@ +# Change Log + +All notable changes to this project will be documented in this file. +See [Conventional Commits](https://conventionalcommits.org) for commit guidelines. + +# [5.0.0-pre.31](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.30...v5.0.0-pre.31) (2022-10-12) + +### Features + +- **cli:** Generate full client test suite and improve typed client ([#2788](https://github.com/feathersjs/feathers/issues/2788)) ([57119b6](https://github.com/feathersjs/feathers/commit/57119b6bb2797f7297cf054268a248c093ecd538)) +- **cli:** Improve generated schema definitions ([#2783](https://github.com/feathersjs/feathers/issues/2783)) ([474a9fd](https://github.com/feathersjs/feathers/commit/474a9fda2107e9bcf357746320a8e00cda8182b6)) + +# [5.0.0-pre.30](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.29...v5.0.0-pre.30) (2022-10-07) + +### Features + +- **core:** Allow to unregister services at runtime ([#2756](https://github.com/feathersjs/feathers/issues/2756)) ([d16601f](https://github.com/feathersjs/feathers/commit/d16601f2277dca5357866ffdefba2a611f6dc7fa)) + +# [5.0.0-pre.29](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.28...v5.0.0-pre.29) (2022-09-16) + +**Note:** Version bump only for package @feathersjs/mongodb + +# [5.0.0-pre.28](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.27...v5.0.0-pre.28) (2022-08-03) + +### Bug Fixes + +- **cli:** Improve generated application and client ([#2701](https://github.com/feathersjs/feathers/issues/2701)) ([bd55ffb](https://github.com/feathersjs/feathers/commit/bd55ffb812e89bf215f4515e7f137656ea888c3f)) +- **mongodb:** Ensure transactions are used properly in create ([#2699](https://github.com/feathersjs/feathers/issues/2699)) ([fe22615](https://github.com/feathersjs/feathers/commit/fe22615b7fa17d3c20ac26d6f82097917c9b63f6)) + +# [5.0.0-pre.27](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.26...v5.0.0-pre.27) (2022-07-13) + +**Note:** Version bump only for package @feathersjs/mongodb + +# [5.0.0-pre.26](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.25...v5.0.0-pre.26) (2022-06-22) + +**Note:** Version bump only for package @feathersjs/mongodb + +# [5.0.0-pre.25](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.24...v5.0.0-pre.25) (2022-06-22) + +**Note:** Version bump only for package @feathersjs/mongodb + +# [5.0.0-pre.24](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.23...v5.0.0-pre.24) (2022-06-21) + +### Features + +- **authentication-local:** Add passwordHash property resolver ([#2660](https://github.com/feathersjs/feathers/issues/2660)) ([b41279b](https://github.com/feathersjs/feathers/commit/b41279b55eea3771a6fa4983a37be2413287bbc6)) +- **knex:** Add KnexJS SQL database adapter to core ([#2671](https://github.com/feathersjs/feathers/issues/2671)) ([9380fff](https://github.com/feathersjs/feathers/commit/9380fff58596e8bb90b8bb098d2795b7eadfec20)) + +# [5.0.0-pre.23](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.22...v5.0.0-pre.23) (2022-06-06) + +**Note:** Version bump only for package @feathersjs/mongodb + +# [5.0.0-pre.22](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.21...v5.0.0-pre.22) (2022-05-24) + +**Note:** Version bump only for package @feathersjs/mongodb + +# [5.0.0-pre.21](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.20...v5.0.0-pre.21) (2022-05-23) + +### Bug Fixes + +- **typescript:** Make additional types generic to work with extended types ([#2625](https://github.com/feathersjs/feathers/issues/2625)) ([269fdec](https://github.com/feathersjs/feathers/commit/269fdecc5961092dc8608b3cbe16f433c80bfa96)) + +# [5.0.0-pre.20](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.19...v5.0.0-pre.20) (2022-05-04) + +### Bug Fixes + +- **dependencies:** Lock monorepo package version numbers ([#2623](https://github.com/feathersjs/feathers/issues/2623)) ([5640c10](https://github.com/feathersjs/feathers/commit/5640c1020cc139994e695d658c08bad3494db507)) + +# [5.0.0-pre.19](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.18...v5.0.0-pre.19) (2022-05-01) + +### Features + +- **mongodb:** Add feathers-mongodb adapter as @feathersjs/mongodb ([#2610](https://github.com/feathersjs/feathers/issues/2610)) ([6d43734](https://github.com/feathersjs/feathers/commit/6d43734a53db02c435cafc52a22dca414e5d0940)) diff --git a/packages/mongodb/LICENSE b/packages/mongodb/LICENSE new file mode 100644 index 0000000000..59604f46f3 --- /dev/null +++ b/packages/mongodb/LICENSE @@ -0,0 +1,22 @@ +The MIT License (MIT) + +Copyright (c) 2022 Feathers + +Permission is hereby granted, free of charge, to any person obtaining a copy +of this software and associated documentation files (the "Software"), to deal +in the Software without restriction, including without limitation the rights +to use, copy, modify, merge, publish, distribute, sublicense, and/or sell +copies of the Software, and to permit persons to whom the Software is +furnished to do so, subject to the following conditions: + +The above copyright notice and this permission notice shall be included in all +copies or substantial portions of the Software. + +THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE +AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, +OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE +SOFTWARE. + diff --git a/packages/mongodb/README.md b/packages/mongodb/README.md new file mode 100644 index 0000000000..df26a2d75c --- /dev/null +++ b/packages/mongodb/README.md @@ -0,0 +1,22 @@ +# @feathersjs/mongodb + +[![CI](https://github.com/feathersjs/feathers/workflows/CI/badge.svg)](https://github.com/feathersjs/feathers/actions?query=workflow%3ACI) +[![Download Status](https://img.shields.io/npm/dm/@feathersjs/mongodb.svg?style=flat-square)](https://www.npmjs.com/package/@feathersjs/mongodb) + +> Feathers MongoDB service adapter + +## Installation + +``` +npm install @feathersjs/mongodb --save +``` + +## Documentation + +Refer to the [Feathers documentation](https://docs.feathersjs.com) for more details. + +## License + +Copyright (c) 2022 [Feathers contributors](https://github.com/feathersjs/feathers/graphs/contributors) + +Licensed under the [MIT license](LICENSE). diff --git a/packages/mongodb/package.json b/packages/mongodb/package.json new file mode 100644 index 0000000000..260b979a63 --- /dev/null +++ b/packages/mongodb/package.json @@ -0,0 +1,72 @@ +{ + "name": "@feathersjs/mongodb", + "description": "Feathers MongoDB service adapter", + "version": "5.0.0-pre.31", + "homepage": "https://feathersjs.com", + "main": "lib/", + "keywords": [ + "feathers", + "feathers-plugin" + ], + "license": "MIT", + "funding": { + "type": "github", + "url": "https://github.com/sponsors/daffl" + }, + "repository": { + "type": "git", + "url": "git://github.com/feathersjs/feathers.git" + }, + "author": { + "name": "Feathers contributors", + "email": "hello@feathersjs.com", + "url": "https://feathersjs.com" + }, + "contributors": [], + "bugs": { + "url": "https://github.com/feathersjs/feathers/issues" + }, + "engines": { + "node": ">= 14" + }, + "files": [ + "CHANGELOG.md", + "LICENSE", + "README.md", + "src/**", + "lib/**", + "*.d.ts", + "*.js" + ], + "scripts": { + "prepublish": "npm run compile", + "pack": "npm pack --pack-destination ../cli/test/build", + "compile": "shx rm -rf lib/ && tsc && npm run pack", + "test": "mocha --config ../../.mocharc.json --recursive test/**.test.ts test/**/*.test.ts" + }, + "directories": { + "lib": "lib" + }, + "publishConfig": { + "access": "public" + }, + "dependencies": { + "@feathersjs/adapter-commons": "^5.0.0-pre.31", + "@feathersjs/commons": "^5.0.0-pre.31", + "@feathersjs/errors": "^5.0.0-pre.31", + "@feathersjs/feathers": "^5.0.0-pre.31" + }, + "peerDependencies": { + "mongodb": "^4.5.0" + }, + "devDependencies": { + "@feathersjs/adapter-tests": "^5.0.0-pre.31", + "@types/mocha": "^10.0.0", + "@types/node": "^18.8.2", + "mocha": "^10.0.0", + "mongodb-memory-server": "^8.9.3", + "shx": "^0.3.4", + "typescript": "^4.8.4" + }, + "gitHead": "4500dbeb8cea566678cf88b3313a88efd93a2ed9" +} diff --git a/packages/mongodb/src/adapter.ts b/packages/mongodb/src/adapter.ts new file mode 100644 index 0000000000..2a84d9a2a3 --- /dev/null +++ b/packages/mongodb/src/adapter.ts @@ -0,0 +1,322 @@ +import { + ObjectId, + Collection, + FindOptions, + BulkWriteOptions, + InsertOneOptions, + DeleteOptions, + CountDocumentsOptions, + ReplaceOptions +} from 'mongodb' +import { NotFound } from '@feathersjs/errors' +import { _ } from '@feathersjs/commons' +import { + AdapterBase, + select, + AdapterParams, + AdapterServiceOptions, + PaginationOptions, + AdapterQuery +} from '@feathersjs/adapter-commons' +import { NullableId, Id, Paginated } from '@feathersjs/feathers' +import { errorHandler } from './error-handler' + +export interface MongoDBAdapterOptions extends AdapterServiceOptions { + Model: Collection | Promise + disableObjectify?: boolean + useEstimatedDocumentCount?: boolean +} + +export interface MongoDBAdapterParams + extends AdapterParams> { + mongodb?: + | BulkWriteOptions + | FindOptions + | InsertOneOptions + | DeleteOptions + | CountDocumentsOptions + | ReplaceOptions +} + +// Create the service. +export class MongoDbAdapter< + T, + D = Partial, + P extends MongoDBAdapterParams = MongoDBAdapterParams +> extends AdapterBase { + constructor(options: MongoDBAdapterOptions) { + if (!options) { + throw new Error('MongoDB options have to be provided') + } + + super({ + id: '_id', + ...options + }) + } + + getObjectId(id: Id | ObjectId) { + if (this.options.disableObjectify) { + return id + } + + if (this.id === '_id' && ObjectId.isValid(id)) { + id = new ObjectId(id.toString()) + } + + return id + } + + filterQuery(id: NullableId, params: P) { + const { $select, $sort, $limit, $skip, ...query } = (params.query || {}) as AdapterQuery + + if (id !== null) { + query.$and = (query.$and || []).concat({ + [this.id]: this.getObjectId(id) + }) + } + + if (query[this.id]) { + query[this.id] = this.getObjectId(query[this.id]) + } + + return { + filters: { $select, $sort, $limit, $skip }, + query + } + } + + getSelect(select: string[] | { [key: string]: number }) { + if (Array.isArray(select)) { + return select.reduce<{ [key: string]: number }>( + (value, name) => ({ + ...value, + [name]: 1 + }), + {} + ) + } + + return select + } + + async $findOrGet(id: NullableId, params: P) { + return id === null ? await this.$find(params) : await this.$get(id, params) + } + + normalizeId(id: NullableId, data: Partial): Partial { + if (this.id === '_id') { + // Default Mongo IDs cannot be updated. The Mongo library handles + // this automatically. + return _.omit(data, this.id) + } else if (id !== null) { + // If not using the default Mongo _id field set the ID to its + // previous value. This prevents orphaned documents. + return { + ...data, + [this.id]: id + } + } + return data + } + + async $get(id: Id, params: P = {} as P): Promise { + const { Model } = this.getOptions(params) + const { + query, + filters: { $select } + } = this.filterQuery(id, params) + const projection = $select + ? { + projection: { + ...this.getSelect($select), + [this.id]: 1 + } + } + : {} + const findOptions: FindOptions = { + ...params.mongodb, + ...projection + } + + return Promise.resolve(Model) + .then((model) => model.findOne(query, findOptions)) + .then((data) => { + if (data == null) { + throw new NotFound(`No record found for id '${id}'`) + } + + return data + }) + .catch(errorHandler) + } + + async $find(params?: P & { paginate?: PaginationOptions }): Promise> + async $find(params?: P & { paginate: false }): Promise + async $find(params?: P): Promise | T[]> + async $find(params: P = {} as P): Promise | T[]> { + const { filters, query } = this.filterQuery(null, params) + const { paginate, Model, useEstimatedDocumentCount } = this.getOptions(params) + const findOptions = { ...params.mongodb } + const model = await Promise.resolve(Model) + const q = model.find(query, findOptions) + + if (filters.$select !== undefined) { + q.project(this.getSelect(filters.$select)) + } + + if (filters.$sort !== undefined) { + q.sort(filters.$sort) + } + + if (filters.$limit !== undefined) { + q.limit(filters.$limit) + } + + if (filters.$skip !== undefined) { + q.skip(filters.$skip) + } + + const runQuery = async (total: number) => ({ + total, + limit: filters.$limit, + skip: filters.$skip || 0, + data: filters.$limit === 0 ? [] : ((await q.toArray()) as any as T[]) + }) + + if (paginate && paginate.default) { + if (useEstimatedDocumentCount && typeof model.estimatedDocumentCount === 'function') { + return model.estimatedDocumentCount().then(runQuery) + } + + return model.countDocuments(query, findOptions).then(runQuery) + } + + return runQuery(0).then((page) => page.data) + } + + async $create(data: D, params?: P): Promise + async $create(data: D[], params?: P): Promise + async $create(data: D | D[], _params?: P): Promise + async $create(data: D | D[], params: P = {} as P): Promise { + const writeOptions = params.mongodb + const { Model } = this.getOptions(params) + const model = await Promise.resolve(Model) + const setId = (item: any) => { + const entry = Object.assign({}, item) + + // Generate a MongoId if we use a custom id + if (this.id !== '_id' && typeof entry[this.id] === 'undefined') { + return { + [this.id]: new ObjectId().toHexString(), + ...entry + } + } + + return entry + } + + const promise = Array.isArray(data) + ? model + .insertMany(data.map(setId), writeOptions) + .then(async (result) => + Promise.all( + Object.values(result.insertedIds).map(async (_id) => model.findOne({ _id }, params.mongodb)) + ) + ) + : model + .insertOne(setId(data), writeOptions) + .then(async (result) => model.findOne({ _id: result.insertedId }, params.mongodb)) + + return promise.then(select(params, this.id)).catch(errorHandler) + } + + async $patch(id: null, data: Partial, params?: P): Promise + async $patch(id: Id, data: Partial, params?: P): Promise + async $patch(id: NullableId, data: Partial, _params?: P): Promise + async $patch(id: NullableId, _data: Partial, params: P = {} as P): Promise { + const data = this.normalizeId(id, _data) + const { Model } = this.getOptions(params) + const model = await Promise.resolve(Model) + const { + query, + filters: { $select } + } = this.filterQuery(id, params) + const updateOptions = { ...params.mongodb } + const modifier = Object.keys(data).reduce((current, key) => { + const value = (data as any)[key] + + if (key.charAt(0) !== '$') { + current.$set = { + ...current.$set, + [key]: value + } + } else { + current[key] = value + } + + return current + }, {} as any) + const originalIds = await this.$findOrGet(id, { + ...params, + query: { + ...query, + $select: [this.id] + }, + paginate: false + }) + const items = Array.isArray(originalIds) ? originalIds : [originalIds] + const idList = items.map((item: any) => item[this.id]) + const findParams = { + ...params, + paginate: false, + query: { + [this.id]: { $in: idList }, + $select + } + } + + await model.updateMany(query, modifier, updateOptions) + + return this.$findOrGet(id, findParams).catch(errorHandler) + } + + async $update(id: Id, data: D, params: P = {} as P): Promise { + const { Model } = this.getOptions(params) + const model = await Promise.resolve(Model) + const { query } = this.filterQuery(id, params) + const replaceOptions = { ...params.mongodb } + + await model.replaceOne(query, this.normalizeId(id, data), replaceOptions) + + return this.$findOrGet(id, params).catch(errorHandler) + } + + async $remove(id: null, params?: P): Promise + async $remove(id: Id, params?: P): Promise + async $remove(id: NullableId, _params?: P): Promise + async $remove(id: NullableId, params: P = {} as P): Promise { + const { Model } = this.getOptions(params) + const model = await Promise.resolve(Model) + const { + query, + filters: { $select } + } = this.filterQuery(id, params) + const deleteOptions = { ...params.mongodb } + const findParams = { + ...params, + paginate: false, + query: { + ...query, + $select + } + } + + return this.$findOrGet(id, findParams) + .then(async (items) => { + await model.deleteMany(query, deleteOptions) + return items + }) + .catch(errorHandler) + } +} diff --git a/packages/mongodb/src/error-handler.ts b/packages/mongodb/src/error-handler.ts new file mode 100644 index 0000000000..e485b00f75 --- /dev/null +++ b/packages/mongodb/src/error-handler.ts @@ -0,0 +1,14 @@ +import { GeneralError } from '@feathersjs/errors' +import { MongoError } from 'mongodb' + +export function errorHandler(error: MongoError): any { + // See https://github.com/mongodb/mongo/blob/master/docs/errors.md + if (error && error.name && error.name.startsWith('Mongo')) { + throw new GeneralError(error, { + name: error.name, + code: error.code + }) + } + + throw error +} diff --git a/packages/mongodb/src/index.ts b/packages/mongodb/src/index.ts new file mode 100644 index 0000000000..b039d8992f --- /dev/null +++ b/packages/mongodb/src/index.ts @@ -0,0 +1,44 @@ +import { PaginationOptions } from '@feathersjs/adapter-commons' +import { Paginated, ServiceMethods, Id, NullableId, Params } from '@feathersjs/feathers' +import { MongoDbAdapter, MongoDBAdapterParams } from './adapter' + +export * from './adapter' +export * from './error-handler' + +export class MongoDBService, P extends Params = MongoDBAdapterParams> + extends MongoDbAdapter + implements ServiceMethods, D, P> +{ + async find(params?: P & { paginate?: PaginationOptions }): Promise> + async find(params?: P & { paginate: false }): Promise + async find(params?: P): Promise | T[]> + async find(params?: P): Promise | T[]> { + return this._find(params) as any + } + + async get(id: Id, params?: P): Promise { + return this._get(id, params) + } + + async create(data: D, params?: P): Promise + async create(data: D[], params?: P): Promise + async create(data: D | D[], params?: P): Promise { + return this._create(data, params) + } + + async update(id: Id, data: D, params?: P): Promise { + return this._update(id, data, params) + } + + async patch(id: Id, data: Partial, params?: P): Promise + async patch(id: null, data: Partial, params?: P): Promise + async patch(id: NullableId, data: Partial, params?: P): Promise { + return this._patch(id, data, params) + } + + async remove(id: Id, params?: P): Promise + async remove(id: null, params?: P): Promise + async remove(id: NullableId, params?: P): Promise { + return this._remove(id, params) + } +} diff --git a/packages/mongodb/test/index.test.ts b/packages/mongodb/test/index.test.ts new file mode 100644 index 0000000000..4d4cc6edc0 --- /dev/null +++ b/packages/mongodb/test/index.test.ts @@ -0,0 +1,356 @@ +import { Db, MongoClient, ObjectId } from 'mongodb' +import adapterTests from '@feathersjs/adapter-tests' +import assert from 'assert' +import { MongoMemoryServer } from 'mongodb-memory-server' + +import { feathers } from '@feathersjs/feathers' +import errors from '@feathersjs/errors' +import { MongoDBService } from '../src' + +const testSuite = adapterTests([ + '.options', + '.events', + '._get', + '._find', + '._create', + '._update', + '._patch', + '._remove', + '.$get', + '.$find', + '.$create', + '.$update', + '.$patch', + '.$remove', + '.get', + '.get + $select', + '.get + id + query', + '.get + NotFound', + '.get + id + query id', + '.find', + '.find + paginate + query', + '.remove', + '.remove + $select', + '.remove + id + query', + '.remove + multi', + '.remove + multi no pagination', + '.remove + id + query id', + '.update', + '.update + $select', + '.update + id + query', + '.update + NotFound', + '.update + id + query id', + '.update + query + NotFound', + '.patch', + '.patch + $select', + '.patch + id + query', + '.patch multiple', + '.patch multiple no pagination', + '.patch multi query same', + '.patch multi query changed', + '.patch + query + NotFound', + '.patch + NotFound', + '.patch + id + query id', + '.create', + '.create + $select', + '.create multi', + 'internal .find', + 'internal .get', + 'internal .create', + 'internal .update', + 'internal .patch', + 'internal .remove', + '.find + equal', + '.find + equal multiple', + '.find + $sort', + '.find + $sort + string', + '.find + $limit', + '.find + $limit 0', + '.find + $skip', + '.find + $select', + '.find + $or', + '.find + $in', + '.find + $nin', + '.find + $lt', + '.find + $lte', + '.find + $gt', + '.find + $gte', + '.find + $ne', + '.find + $gt + $lt + $sort', + '.find + $or nested + $sort', + '.find + paginate', + '.find + paginate + $limit + $skip', + '.find + paginate + $limit 0', + '.find + paginate + params', + 'params.adapter + paginate', + 'params.adapter + multi' +]) + +describe('Feathers MongoDB Service', () => { + type Person = { + _id: string + name: string + age: number + friends?: string[] + team: string + $push: { + friends: string + } + } + + type ServiceTypes = { + people: MongoDBService + 'people-customid': MongoDBService + } + + const app = feathers() + + let db: Db + let mongoClient: MongoClient + let mongod: MongoMemoryServer + + before(async () => { + mongod = await MongoMemoryServer.create() + + const client = await MongoClient.connect(mongod.getUri()) + + mongoClient = client + db = client.db('feathers-test') + + app.use( + 'people', + new MongoDBService({ + Model: db.collection('people'), + events: ['testing'] + }) + ) + app.use( + 'people-customid', + new MongoDBService({ + Model: db.collection('people-customid'), + id: 'customid', + events: ['testing'] + }) + ) + + db.collection('people-customid').deleteMany({}) + db.collection('people').deleteMany({}) + db.collection('todos').deleteMany({}) + + db.collection('people').createIndex({ name: 1 }, { partialFilterExpression: { team: 'blue' } }) + }) + + after(async () => { + await db.dropDatabase() + await mongoClient.close() + await mongod.stop() + }) + + describe('Service utility functions', () => { + describe('getObjectId', () => { + it('returns an ObjectID instance for a valid ID', () => { + const id = new ObjectId() + const objectify = app.service('people').getObjectId(id.toString()) + + assert.ok(objectify instanceof ObjectId) + assert.strictEqual(objectify.toString(), id.toString()) + }) + + it('returns an ObjectID instance for a valid ID', () => { + const id = 'non-valid object id' + const objectify = app.service('people').getObjectId(id.toString()) + + assert.ok(!(objectify instanceof ObjectId)) + assert.strictEqual(objectify, id) + }) + }) + }) + + describe('Special collation param', () => { + let peopleService: MongoDBService + let people: Person[] + + function indexOfName(results: Person[], name: string) { + let index = 0 + + for (const person of results) { + if (person.name === name) { + return index + } + index++ + } + + return -1 + } + + beforeEach(async () => { + peopleService = app.service('people') + peopleService.options.multi = true + peopleService.options.disableObjectify = true + people = await peopleService.create([{ name: 'AAA' }, { name: 'aaa' }, { name: 'ccc' }]) + }) + + afterEach(async () => { + peopleService.options.multi = false + + try { + await Promise.all([ + peopleService.remove(people[0]._id), + peopleService.remove(people[1]._id), + peopleService.remove(people[2]._id) + ]) + } catch (error: unknown) {} + }) + + it('queries for ObjectId in find', async () => { + const person = await peopleService.create({ name: 'Coerce' }) + const results = await peopleService.find({ + paginate: false, + query: { + _id: new ObjectId(person._id) + } + }) + + assert.strictEqual(results.length, 1) + + await peopleService.remove(person._id) + }) + + it('works with normal string _id', async () => { + const person = await peopleService.create({ + _id: 'lessonKTDA08', + name: 'Coerce' + }) + const result = await peopleService.get(person._id) + + assert.strictEqual(result.name, 'Coerce') + + await peopleService.remove(person._id) + }) + + it('sorts with default behavior without collation param', async () => { + const results = await peopleService.find({ + paginate: false, + query: { $sort: { name: -1 } } + }) + + assert.ok(indexOfName(results, 'aaa') < indexOfName(results, 'AAA')) + }) + + it('sorts using collation param if present', async () => { + const results = await peopleService.find({ + paginate: false, + query: { $sort: { name: -1 } }, + mongodb: { collation: { locale: 'en', strength: 1 } } + }) + + assert.ok(indexOfName(results, 'aaa') > indexOfName(results, 'AAA')) + }) + + it('removes with default behavior without collation param', async () => { + await peopleService.remove(null, { query: { name: { $gt: 'AAA' } } }) + + const results = await peopleService.find({ paginate: false }) + + assert.strictEqual(results.length, 1) + assert.strictEqual(results[0].name, 'AAA') + }) + + it('removes using collation param if present', async () => { + const removed = await peopleService.remove(null, { + query: { name: 'AAA' }, + mongodb: { collation: { locale: 'en', strength: 1 } } + }) + const results = await peopleService.find({ paginate: false }) + + assert.strictEqual(removed.length, 2) + assert.strictEqual(results[0].name, 'ccc') + assert.strictEqual(results.length, 1) + }) + + it('handles errors', async () => { + await assert.rejects( + () => + peopleService.create( + { + name: 'Dave' + }, + { + mongodb: { collation: { locale: 'fdsfdsfds', strength: 1 } } + } + ), + { + name: 'GeneralError' + } + ) + }) + + it('updates with default behavior without collation param', async () => { + const query = { name: { $gt: 'AAA' } } + + const result = await peopleService.patch(null, { age: 99 }, { query }) + + assert.strictEqual(result.length, 2) + result.forEach((person) => { + assert.strictEqual(person.age, 99) + }) + }) + + it('updates using collation param if present', async () => { + const result = await peopleService.patch( + null, + { age: 110 }, + { + query: { name: { $gt: 'AAA' } }, + mongodb: { collation: { locale: 'en', strength: 1 } } + } + ) + + assert.strictEqual(result.length, 1) + assert.strictEqual(result[0].name, 'ccc') + }) + + it('pushes to an array using patch', async () => { + const result = await peopleService.patch( + null, + { $push: { friends: 'Adam' } }, + { + query: { name: { $gt: 'AAA' } } + } + ) + + assert.strictEqual(result[0].friends.length, 1) + + const patched = await peopleService.patch( + null, + { + $push: { friends: 'Bell' } + }, + { query: { name: { $gt: 'AAA' } } } + ) + + assert.strictEqual(patched[0].friends.length, 2) + }) + + it('overrides default index selection using hint param if present', async () => { + const indexed = await peopleService.create({ + name: 'Indexed', + team: 'blue' + }) + + const result = await peopleService.find({ + paginate: false, + query: {}, + mongodb: { hint: { name: 1 } } + }) + + assert.strictEqual(result[0].name, 'Indexed') + assert.strictEqual(result.length, 1) + + await peopleService.remove(indexed._id) + }) + }) + + testSuite(app, errors, 'people', '_id') + testSuite(app, errors, 'people-customid', 'customid') +}) diff --git a/packages/mongodb/tsconfig.json b/packages/mongodb/tsconfig.json new file mode 100644 index 0000000000..316fd41336 --- /dev/null +++ b/packages/mongodb/tsconfig.json @@ -0,0 +1,9 @@ +{ + "extends": "../../tsconfig", + "include": [ + "src/**/*.ts" + ], + "compilerOptions": { + "outDir": "lib" + } +} diff --git a/packages/rest-client/CHANGELOG.md b/packages/rest-client/CHANGELOG.md index 1b05a224f1..43aabc1182 100644 --- a/packages/rest-client/CHANGELOG.md +++ b/packages/rest-client/CHANGELOG.md @@ -3,545 +3,380 @@ All notable changes to this project will be documented in this file. See [Conventional Commits](https://conventionalcommits.org) for commit guidelines. -# [5.0.0-pre.16](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.15...v5.0.0-pre.16) (2022-01-12) - +# [5.0.0-pre.31](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.30...v5.0.0-pre.31) (2022-10-12) -### Features - -* **express, koa:** make transports similar ([#2486](https://github.com/feathersjs/feathers/issues/2486)) ([26aa937](https://github.com/feathersjs/feathers/commit/26aa937c114fb8596dfefc599b1f53cead69c159)) +**Note:** Version bump only for package @feathersjs/rest-client +# [5.0.0-pre.30](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.29...v5.0.0-pre.30) (2022-10-07) +### Features +- **core:** Allow to unregister services at runtime ([#2756](https://github.com/feathersjs/feathers/issues/2756)) ([d16601f](https://github.com/feathersjs/feathers/commit/d16601f2277dca5357866ffdefba2a611f6dc7fa)) +# [5.0.0-pre.29](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.28...v5.0.0-pre.29) (2022-09-16) -# [5.0.0-pre.15](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.14...v5.0.0-pre.15) (2021-11-27) +**Note:** Version bump only for package @feathersjs/rest-client +# [5.0.0-pre.28](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.27...v5.0.0-pre.28) (2022-08-03) ### Bug Fixes -* **typescript:** Overall typing improvements ([#2478](https://github.com/feathersjs/feathers/issues/2478)) ([b8eb804](https://github.com/feathersjs/feathers/commit/b8eb804158556d9651a8607e3c3fda15e0bfd110)) - - +- **cli:** Improve generated application and client ([#2701](https://github.com/feathersjs/feathers/issues/2701)) ([bd55ffb](https://github.com/feathersjs/feathers/commit/bd55ffb812e89bf215f4515e7f137656ea888c3f)) +# [5.0.0-pre.27](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.26...v5.0.0-pre.27) (2022-07-13) +**Note:** Version bump only for package @feathersjs/rest-client -# [5.0.0-pre.14](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.13...v5.0.0-pre.14) (2021-10-13) +# [5.0.0-pre.26](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.25...v5.0.0-pre.26) (2022-06-22) **Note:** Version bump only for package @feathersjs/rest-client +# [5.0.0-pre.25](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.24...v5.0.0-pre.25) (2022-06-22) +**Note:** Version bump only for package @feathersjs/rest-client +# [5.0.0-pre.24](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.23...v5.0.0-pre.24) (2022-06-21) +### Features -# [5.0.0-pre.13](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.12...v5.0.0-pre.13) (2021-10-13) +- **cli:** Add typed client to a generated app ([#2669](https://github.com/feathersjs/feathers/issues/2669)) ([5b801b5](https://github.com/feathersjs/feathers/commit/5b801b5017ddc3eaa95622b539f51d605916bc86)) -**Note:** Version bump only for package @feathersjs/rest-client +# [5.0.0-pre.23](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.22...v5.0.0-pre.23) (2022-06-06) +### Bug Fixes +- **express:** Ensure Express options can be set before configuring REST transport ([#2655](https://github.com/feathersjs/feathers/issues/2655)) ([c9b8f74](https://github.com/feathersjs/feathers/commit/c9b8f74a0196acb99be44ac5e0fff3f1128288cd)) +### Features +- **client:** Improve client side custom method support ([#2654](https://github.com/feathersjs/feathers/issues/2654)) ([c138acf](https://github.com/feathersjs/feathers/commit/c138acf50affbe6b66177d084d3c7a3e9220f09f)) -# [5.0.0-pre.12](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.11...v5.0.0-pre.12) (2021-10-12) +# [5.0.0-pre.22](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.21...v5.0.0-pre.22) (2022-05-24) **Note:** Version bump only for package @feathersjs/rest-client +# [5.0.0-pre.21](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.20...v5.0.0-pre.21) (2022-05-23) +**Note:** Version bump only for package @feathersjs/rest-client +# [5.0.0-pre.20](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.19...v5.0.0-pre.20) (2022-05-04) +### Bug Fixes -# [5.0.0-pre.11](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.10...v5.0.0-pre.11) (2021-10-06) +- **dependencies:** Lock monorepo package version numbers ([#2623](https://github.com/feathersjs/feathers/issues/2623)) ([5640c10](https://github.com/feathersjs/feathers/commit/5640c1020cc139994e695d658c08bad3494db507)) -**Note:** Version bump only for package @feathersjs/rest-client +# [5.0.0-pre.19](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.18...v5.0.0-pre.19) (2022-05-01) +### Features +- **typescript:** Improve adapter typings ([#2605](https://github.com/feathersjs/feathers/issues/2605)) ([3b2ca0a](https://github.com/feathersjs/feathers/commit/3b2ca0a6a8e03e8390272c4d7e930b4bffdaacf5)) +- **typescript:** Improve params and query typeability ([#2600](https://github.com/feathersjs/feathers/issues/2600)) ([df28b76](https://github.com/feathersjs/feathers/commit/df28b7619161f1df5e700326f52cca1a92dc5d28)) +# [5.0.0-pre.18](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.17...v5.0.0-pre.18) (2022-04-11) +**Note:** Version bump only for package @feathersjs/rest-client -# [5.0.0-pre.10](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.9...v5.0.0-pre.10) (2021-09-19) +# [5.0.0-pre.17](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.16...v5.0.0-pre.17) (2022-02-15) **Note:** Version bump only for package @feathersjs/rest-client +# [5.0.0-pre.16](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.15...v5.0.0-pre.16) (2022-01-12) +### Features +- **express, koa:** make transports similar ([#2486](https://github.com/feathersjs/feathers/issues/2486)) ([26aa937](https://github.com/feathersjs/feathers/commit/26aa937c114fb8596dfefc599b1f53cead69c159)) +# [5.0.0-pre.15](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.14...v5.0.0-pre.15) (2021-11-27) -# [5.0.0-pre.9](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.8...v5.0.0-pre.9) (2021-08-09) +### Bug Fixes -**Note:** Version bump only for package @feathersjs/rest-client +- **typescript:** Overall typing improvements ([#2478](https://github.com/feathersjs/feathers/issues/2478)) ([b8eb804](https://github.com/feathersjs/feathers/commit/b8eb804158556d9651a8607e3c3fda15e0bfd110)) +# [5.0.0-pre.14](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.13...v5.0.0-pre.14) (2021-10-13) +**Note:** Version bump only for package @feathersjs/rest-client +# [5.0.0-pre.13](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.12...v5.0.0-pre.13) (2021-10-13) +**Note:** Version bump only for package @feathersjs/rest-client -# [5.0.0-pre.8](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.7...v5.0.0-pre.8) (2021-08-09) +# [5.0.0-pre.12](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.11...v5.0.0-pre.12) (2021-10-12) **Note:** Version bump only for package @feathersjs/rest-client +# [5.0.0-pre.11](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.10...v5.0.0-pre.11) (2021-10-06) +**Note:** Version bump only for package @feathersjs/rest-client +# [5.0.0-pre.10](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.9...v5.0.0-pre.10) (2021-09-19) +**Note:** Version bump only for package @feathersjs/rest-client -# [5.0.0-pre.7](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.6...v5.0.0-pre.7) (2021-08-09) +# [5.0.0-pre.9](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.8...v5.0.0-pre.9) (2021-08-09) **Note:** Version bump only for package @feathersjs/rest-client +# [5.0.0-pre.8](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.7...v5.0.0-pre.8) (2021-08-09) +**Note:** Version bump only for package @feathersjs/rest-client +# [5.0.0-pre.7](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.6...v5.0.0-pre.7) (2021-08-09) +**Note:** Version bump only for package @feathersjs/rest-client # [5.0.0-pre.6](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.5...v5.0.0-pre.6) (2021-08-08) **Note:** Version bump only for package @feathersjs/rest-client - - - - # [5.0.0-pre.5](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.4...v5.0.0-pre.5) (2021-06-23) - ### Features -* **adapter-commons:** Add support for params.adapter option and move memory adapter to @feathersjs/memory ([#2367](https://github.com/feathersjs/feathers/issues/2367)) ([a43e7da](https://github.com/feathersjs/feathers/commit/a43e7da22b6b981a96d1321736ea9a0cb924fb4f)) - - - - +- **adapter-commons:** Add support for params.adapter option and move memory adapter to @feathersjs/memory ([#2367](https://github.com/feathersjs/feathers/issues/2367)) ([a43e7da](https://github.com/feathersjs/feathers/commit/a43e7da22b6b981a96d1321736ea9a0cb924fb4f)) # [5.0.0-pre.4](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.3...v5.0.0-pre.4) (2021-05-13) **Note:** Version bump only for package @feathersjs/rest-client - - - - # [5.0.0-pre.3](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.2...v5.0.0-pre.3) (2021-04-21) - ### Bug Fixes -* **typescript:** Improve TypeScript backwards compatibility ([#2310](https://github.com/feathersjs/feathers/issues/2310)) ([f33be73](https://github.com/feathersjs/feathers/commit/f33be73fc46a533efb15df9aab0658e3240d3897)) - - - - +- **typescript:** Improve TypeScript backwards compatibility ([#2310](https://github.com/feathersjs/feathers/issues/2310)) ([f33be73](https://github.com/feathersjs/feathers/commit/f33be73fc46a533efb15df9aab0658e3240d3897)) # [5.0.0-pre.2](https://github.com/feathersjs/feathers/compare/v5.0.0-beta.1...v5.0.0-pre.2) (2021-04-06) **Note:** Version bump only for package @feathersjs/rest-client - - - - # [5.0.0-beta.1](https://github.com/feathersjs/feathers/compare/v5.0.0-beta.0...v5.0.0-beta.1) (2021-04-03) - ### Bug Fixes -* **dependencies:** Fix transport-commons dependency and update other dependencies ([#2284](https://github.com/feathersjs/feathers/issues/2284)) ([05b03b2](https://github.com/feathersjs/feathers/commit/05b03b27b40604d956047e3021d8053c3a137616)) - - - - +- **dependencies:** Fix transport-commons dependency and update other dependencies ([#2284](https://github.com/feathersjs/feathers/issues/2284)) ([05b03b2](https://github.com/feathersjs/feathers/commit/05b03b27b40604d956047e3021d8053c3a137616)) # [5.0.0-beta.0](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.1...v5.0.0-beta.0) (2021-03-28) - ### Bug Fixes -* Update Grant usage and other dependencies ([#2264](https://github.com/feathersjs/feathers/issues/2264)) ([7b0f8fa](https://github.com/feathersjs/feathers/commit/7b0f8fad252419ed0ad0bf259cdf3104d322ab60)) - +- Update Grant usage and other dependencies ([#2264](https://github.com/feathersjs/feathers/issues/2264)) ([7b0f8fa](https://github.com/feathersjs/feathers/commit/7b0f8fad252419ed0ad0bf259cdf3104d322ab60)) ### Features -* **core:** Public custom service methods ([#2270](https://github.com/feathersjs/feathers/issues/2270)) ([e65abfb](https://github.com/feathersjs/feathers/commit/e65abfb5388df6c19a11c565cf1076a29f32668d)) -* Feathers v5 core refactoring and features ([#2255](https://github.com/feathersjs/feathers/issues/2255)) ([2dafb7c](https://github.com/feathersjs/feathers/commit/2dafb7ce14ba57406aeec13d10ca45b1e709bee9)) - - - - +- **core:** Public custom service methods ([#2270](https://github.com/feathersjs/feathers/issues/2270)) ([e65abfb](https://github.com/feathersjs/feathers/commit/e65abfb5388df6c19a11c565cf1076a29f32668d)) +- Feathers v5 core refactoring and features ([#2255](https://github.com/feathersjs/feathers/issues/2255)) ([2dafb7c](https://github.com/feathersjs/feathers/commit/2dafb7ce14ba57406aeec13d10ca45b1e709bee9)) # [5.0.0-pre.1](https://github.com/feathersjs/feathers/compare/v4.5.11...v5.0.0-pre.1) (2020-12-17) - - # [5.0.0-pre.0](https://github.com/feathersjs/feathers/compare/v4.5.4...v5.0.0-pre.0) (2020-05-19) **Note:** Version bump only for package @feathersjs/rest-client - - - - # [5.0.0-pre.0](https://github.com/feathersjs/feathers/compare/v4.5.4...v5.0.0-pre.0) (2020-05-19) - - ## [4.5.11](https://github.com/feathersjs/feathers/compare/v4.5.10...v4.5.11) (2020-12-05) **Note:** Version bump only for package @feathersjs/rest-client - - - - ## [4.5.10](https://github.com/feathersjs/feathers/compare/v4.5.9...v4.5.10) (2020-11-08) **Note:** Version bump only for package @feathersjs/rest-client - - ## [4.5.9](https://github.com/feathersjs/feathers/compare/v4.5.8...v4.5.9) (2020-10-09) - ### Bug Fixes -* **rest-client:** Handle non-JSON errors with fetch adapter ([#2086](https://github.com/feathersjs/feathers/issues/2086)) ([e24217a](https://github.com/feathersjs/feathers/commit/e24217ad1e784ad71cd9d64fe1727dd02f039991)) - - - - +- **rest-client:** Handle non-JSON errors with fetch adapter ([#2086](https://github.com/feathersjs/feathers/issues/2086)) ([e24217a](https://github.com/feathersjs/feathers/commit/e24217ad1e784ad71cd9d64fe1727dd02f039991)) ## [4.5.8](https://github.com/feathersjs/feathers/compare/v4.5.7...v4.5.8) (2020-08-12) **Note:** Version bump only for package @feathersjs/rest-client - - - - ## [4.5.7](https://github.com/feathersjs/feathers/compare/v4.5.6...v4.5.7) (2020-07-24) **Note:** Version bump only for package @feathersjs/rest-client - - - - ## [4.5.6](https://github.com/feathersjs/feathers/compare/v4.5.5...v4.5.6) (2020-07-12) **Note:** Version bump only for package @feathersjs/rest-client - - - - ## [4.5.5](https://github.com/feathersjs/feathers/compare/v4.5.4...v4.5.5) (2020-07-11) **Note:** Version bump only for package @feathersjs/rest-client - - - - ## [4.5.4](https://github.com/feathersjs/feathers/compare/v4.5.3...v4.5.4) (2020-04-29) **Note:** Version bump only for package @feathersjs/rest-client - - - - ## [4.5.3](https://github.com/feathersjs/feathers/compare/v4.5.2...v4.5.3) (2020-04-17) **Note:** Version bump only for package @feathersjs/rest-client - - - - ## [4.5.2](https://github.com/feathersjs/feathers/compare/v4.5.1...v4.5.2) (2020-03-04) **Note:** Version bump only for package @feathersjs/rest-client - - - - ## [4.5.1](https://github.com/feathersjs/feathers/compare/v4.5.0...v4.5.1) (2020-01-24) **Note:** Version bump only for package @feathersjs/rest-client - - - - # [4.5.0](https://github.com/feathersjs/feathers/compare/v4.4.3...v4.5.0) (2020-01-18) - ### Features -* **rest-client:** Allow for customising rest clients ([#1780](https://github.com/feathersjs/feathers/issues/1780)) ([c5cfec7](https://github.com/feathersjs/feathers/commit/c5cfec7a4aafcaffaab0cdacb9b5d297ff20320f)) - - - - +- **rest-client:** Allow for customising rest clients ([#1780](https://github.com/feathersjs/feathers/issues/1780)) ([c5cfec7](https://github.com/feathersjs/feathers/commit/c5cfec7a4aafcaffaab0cdacb9b5d297ff20320f)) ## [4.4.3](https://github.com/feathersjs/feathers/compare/v4.4.1...v4.4.3) (2019-12-06) **Note:** Version bump only for package @feathersjs/rest-client - - - - ## [4.4.1](https://github.com/feathersjs/feathers/compare/v4.4.0...v4.4.1) (2019-11-27) **Note:** Version bump only for package @feathersjs/rest-client - - - - # [4.4.0](https://github.com/feathersjs/feathers/compare/v4.3.11...v4.4.0) (2019-11-27) - ### Bug Fixes -* **core:** Improve hook missing parameter message by adding the service name ([#1703](https://github.com/feathersjs/feathers/issues/1703)) ([2331c2a](https://github.com/feathersjs/feathers/commit/2331c2a3dd70d432db7d62a76ed805d359cbbba5)) -* **rest-client:** Allow to customize getting the query ([#1594](https://github.com/feathersjs/feathers/issues/1594)) ([5f21272](https://github.com/feathersjs/feathers/commit/5f212729849414c4da6f0d51edd1986feca992ee)) - - - - +- **core:** Improve hook missing parameter message by adding the service name ([#1703](https://github.com/feathersjs/feathers/issues/1703)) ([2331c2a](https://github.com/feathersjs/feathers/commit/2331c2a3dd70d432db7d62a76ed805d359cbbba5)) +- **rest-client:** Allow to customize getting the query ([#1594](https://github.com/feathersjs/feathers/issues/1594)) ([5f21272](https://github.com/feathersjs/feathers/commit/5f212729849414c4da6f0d51edd1986feca992ee)) ## [4.3.11](https://github.com/feathersjs/feathers/compare/v4.3.10...v4.3.11) (2019-11-11) **Note:** Version bump only for package @feathersjs/rest-client - - - - ## [4.3.10](https://github.com/feathersjs/feathers/compare/v4.3.9...v4.3.10) (2019-10-26) **Note:** Version bump only for package @feathersjs/rest-client - - - - ## [4.3.9](https://github.com/feathersjs/feathers/compare/v4.3.8...v4.3.9) (2019-10-26) **Note:** Version bump only for package @feathersjs/rest-client - - - - ## [4.3.7](https://github.com/feathersjs/feathers/compare/v4.3.6...v4.3.7) (2019-10-14) **Note:** Version bump only for package @feathersjs/rest-client - - - - ## [4.3.5](https://github.com/feathersjs/feathers/compare/v4.3.4...v4.3.5) (2019-10-07) - ### Bug Fixes -* Change this reference in client libraries to explicitly passed app ([#1597](https://github.com/feathersjs/feathers/issues/1597)) ([4e4d10a](https://github.com/feathersjs/feathers/commit/4e4d10a)) - - - - +- Change this reference in client libraries to explicitly passed app ([#1597](https://github.com/feathersjs/feathers/issues/1597)) ([4e4d10a](https://github.com/feathersjs/feathers/commit/4e4d10a)) ## [4.3.4](https://github.com/feathersjs/feathers/compare/v4.3.3...v4.3.4) (2019-10-03) **Note:** Version bump only for package @feathersjs/rest-client - - - - ## [4.3.3](https://github.com/feathersjs/feathers/compare/v4.3.2...v4.3.3) (2019-09-21) **Note:** Version bump only for package @feathersjs/rest-client - - - - ## [4.3.2](https://github.com/feathersjs/feathers/compare/v4.3.1...v4.3.2) (2019-09-16) **Note:** Version bump only for package @feathersjs/rest-client - - - - ## [4.3.1](https://github.com/feathersjs/feathers/compare/v4.3.0...v4.3.1) (2019-09-09) **Note:** Version bump only for package @feathersjs/rest-client - - - - # [4.3.0](https://github.com/feathersjs/feathers/compare/v4.3.0-pre.4...v4.3.0) (2019-08-27) **Note:** Version bump only for package @feathersjs/rest-client - - - - # [4.3.0-pre.4](https://github.com/feathersjs/feathers/compare/v4.3.0-pre.3...v4.3.0-pre.4) (2019-08-22) **Note:** Version bump only for package @feathersjs/rest-client - - - - # [4.3.0-pre.3](https://github.com/feathersjs/feathers/compare/v4.3.0-pre.2...v4.3.0-pre.3) (2019-08-19) - ### Bug Fixes -* Update all dependencies ([7d53a00](https://github.com/feathersjs/feathers/commit/7d53a00)) - - - - +- Update all dependencies ([7d53a00](https://github.com/feathersjs/feathers/commit/7d53a00)) # [4.3.0-pre.2](https://github.com/feathersjs/feathers/compare/v4.3.0-pre.1...v4.3.0-pre.2) (2019-08-02) **Note:** Version bump only for package @feathersjs/rest-client - - - - # [4.3.0-pre.1](https://github.com/feathersjs/feathers/compare/v4.0.0-pre.5...v4.3.0-pre.1) (2019-07-11) **Note:** Version bump only for package @feathersjs/rest-client - - - - # [4.0.0-pre.5](https://github.com/feathersjs/feathers/compare/v4.0.0-pre.4...v4.0.0-pre.5) (2019-07-10) **Note:** Version bump only for package @feathersjs/rest-client - - - - # [4.0.0-pre.4](https://github.com/feathersjs/feathers/compare/v4.0.0-pre.3...v4.0.0-pre.4) (2019-07-05) **Note:** Version bump only for package @feathersjs/rest-client - - - - # [4.0.0-pre.3](https://github.com/feathersjs/feathers/compare/v4.0.0-pre.2...v4.0.0-pre.3) (2019-06-01) - ### Bug Fixes -* Update dependencies and fix tests ([#1373](https://github.com/feathersjs/feathers/issues/1373)) ([d743a7f](https://github.com/feathersjs/feathers/commit/d743a7f)) - - - - +- Update dependencies and fix tests ([#1373](https://github.com/feathersjs/feathers/issues/1373)) ([d743a7f](https://github.com/feathersjs/feathers/commit/d743a7f)) # [4.0.0-pre.2](https://github.com/feathersjs/feathers/compare/v4.0.0-pre.1...v4.0.0-pre.2) (2019-05-15) - ### Bug Fixes -* Use `export =` in TypeScript definitions ([#1285](https://github.com/feathersjs/feathers/issues/1285)) ([12d0f4b](https://github.com/feathersjs/feathers/commit/12d0f4b)) - - - - +- Use `export =` in TypeScript definitions ([#1285](https://github.com/feathersjs/feathers/issues/1285)) ([12d0f4b](https://github.com/feathersjs/feathers/commit/12d0f4b)) # [4.0.0-pre.1](https://github.com/feathersjs/feathers/compare/v4.0.0-pre.0...v4.0.0-pre.1) (2019-05-08) **Note:** Version bump only for package @feathersjs/rest-client - - - - # [4.0.0-pre.0](https://github.com/feathersjs/feathers/compare/v3.2.0-pre.1...v4.0.0-pre.0) (2019-04-21) - ### Bug Fixes -* Make Mocha a proper devDependency for every repository ([#1053](https://github.com/feathersjs/feathers/issues/1053)) ([9974803](https://github.com/feathersjs/feathers/commit/9974803)) -* Update adapter common tests ([#1135](https://github.com/feathersjs/feathers/issues/1135)) ([8166dda](https://github.com/feathersjs/feathers/commit/8166dda)) -* Update all dependencies to latest ([#1206](https://github.com/feathersjs/feathers/issues/1206)) ([e51e0f6](https://github.com/feathersjs/feathers/commit/e51e0f6)) - +- Make Mocha a proper devDependency for every repository ([#1053](https://github.com/feathersjs/feathers/issues/1053)) ([9974803](https://github.com/feathersjs/feathers/commit/9974803)) +- Update adapter common tests ([#1135](https://github.com/feathersjs/feathers/issues/1135)) ([8166dda](https://github.com/feathersjs/feathers/commit/8166dda)) +- Update all dependencies to latest ([#1206](https://github.com/feathersjs/feathers/issues/1206)) ([e51e0f6](https://github.com/feathersjs/feathers/commit/e51e0f6)) ### Features -* Add TypeScript definitions ([#1275](https://github.com/feathersjs/feathers/issues/1275)) ([9dd6713](https://github.com/feathersjs/feathers/commit/9dd6713)) -* Authentication v3 core server implementation ([#1205](https://github.com/feathersjs/feathers/issues/1205)) ([1bd7591](https://github.com/feathersjs/feathers/commit/1bd7591)) - - - - +- Add TypeScript definitions ([#1275](https://github.com/feathersjs/feathers/issues/1275)) ([9dd6713](https://github.com/feathersjs/feathers/commit/9dd6713)) +- Authentication v3 core server implementation ([#1205](https://github.com/feathersjs/feathers/issues/1205)) ([1bd7591](https://github.com/feathersjs/feathers/commit/1bd7591)) ## [1.4.7](https://github.com/feathersjs/feathers/compare/@feathersjs/rest-client@1.4.6...@feathersjs/rest-client@1.4.7) (2019-01-02) - ### Bug Fixes -* Update adapter common tests ([#1135](https://github.com/feathersjs/feathers/issues/1135)) ([8166dda](https://github.com/feathersjs/feathers/commit/8166dda)) - - - - +- Update adapter common tests ([#1135](https://github.com/feathersjs/feathers/issues/1135)) ([8166dda](https://github.com/feathersjs/feathers/commit/8166dda)) -## [1.4.6](https://github.com/feathersjs/feathers/compare/@feathersjs/rest-client@1.4.5...@feathersjs/rest-client@1.4.6) (2018-12-16) +## [1.4.6](https://github.com/feathersjs/feathers/compare/@feathersjs/rest-client@1.4.5...@feathersjs/rest-client@1.4.6) (2018-12-16) ### Bug Fixes -* Make Mocha a proper devDependency for every repository ([#1053](https://github.com/feathersjs/feathers/issues/1053)) ([9974803](https://github.com/feathersjs/feathers/commit/9974803)) - - - - +- Make Mocha a proper devDependency for every repository ([#1053](https://github.com/feathersjs/feathers/issues/1053)) ([9974803](https://github.com/feathersjs/feathers/commit/9974803)) + ## [1.4.5](https://github.com/feathersjs/feathers/compare/@feathersjs/rest-client@1.4.4...@feathersjs/rest-client@1.4.5) (2018-09-21) **Note:** Version bump only for package @feathersjs/rest-client - - - - + ## [1.4.4](https://github.com/feathersjs/feathers/compare/@feathersjs/rest-client@1.4.3...@feathersjs/rest-client@1.4.4) (2018-09-17) **Note:** Version bump only for package @feathersjs/rest-client - - - - + ## [1.4.3](https://github.com/feathersjs/feathers/compare/@feathersjs/rest-client@1.4.2...@feathersjs/rest-client@1.4.3) (2018-09-02) **Note:** Version bump only for package @feathersjs/rest-client + ## 1.4.2 - Migrate to Monorepo ([feathers#462](https://github.com/feathersjs/feathers/issues/462)) ## [v1.4.1](https://github.com/feathersjs/rest-client/tree/v1.4.1) (2018-06-27) + [Full Changelog](https://github.com/feathersjs/rest-client/compare/v1.4.0...v1.4.1) **Merged pull requests:** @@ -550,6 +385,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Update shx to the latest version 🚀 [\#31](https://github.com/feathersjs/rest-client/pull/31) ([greenkeeper[bot]](https://github.com/apps/greenkeeper)) ## [v1.4.0](https://github.com/feathersjs/rest-client/tree/v1.4.0) (2018-05-17) + [Full Changelog](https://github.com/feathersjs/rest-client/compare/v1.3.4...v1.4.0) **Closed issues:** @@ -563,6 +399,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Update dependencies to enable Greenkeeper 🌴 [\#28](https://github.com/feathersjs/rest-client/pull/28) ([greenkeeper[bot]](https://github.com/apps/greenkeeper)) ## [v1.3.4](https://github.com/feathersjs/rest-client/tree/v1.3.4) (2018-03-17) + [Full Changelog](https://github.com/feathersjs/rest-client/compare/v1.3.3...v1.3.4) **Closed issues:** @@ -578,6 +415,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Update mocha to the latest version 🚀 [\#21](https://github.com/feathersjs/rest-client/pull/21) ([greenkeeper[bot]](https://github.com/apps/greenkeeper)) ## [v1.3.3](https://github.com/feathersjs/rest-client/tree/v1.3.3) (2018-01-03) + [Full Changelog](https://github.com/feathersjs/rest-client/compare/v1.3.2...v1.3.3) **Closed issues:** @@ -592,6 +430,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Update feathers-memory to the latest version 🚀 [\#17](https://github.com/feathersjs/rest-client/pull/17) ([greenkeeper[bot]](https://github.com/apps/greenkeeper)) ## [v1.3.2](https://github.com/feathersjs/rest-client/tree/v1.3.2) (2017-11-16) + [Full Changelog](https://github.com/feathersjs/rest-client/compare/v1.3.1...v1.3.2) **Merged pull requests:** @@ -604,6 +443,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Update @angular/common to the latest version 🚀 [\#10](https://github.com/feathersjs/rest-client/pull/10) ([greenkeeper[bot]](https://github.com/apps/greenkeeper)) ## [v1.3.1](https://github.com/feathersjs/rest-client/tree/v1.3.1) (2017-11-01) + [Full Changelog](https://github.com/feathersjs/rest-client/compare/v1.3.0...v1.3.1) **Merged pull requests:** @@ -612,6 +452,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Update babelify to the latest version 🚀 [\#8](https://github.com/feathersjs/rest-client/pull/8) ([greenkeeper[bot]](https://github.com/apps/greenkeeper)) ## [v1.3.0](https://github.com/feathersjs/rest-client/tree/v1.3.0) (2017-10-23) + [Full Changelog](https://github.com/feathersjs/rest-client/compare/v1.2.0...v1.3.0) **Merged pull requests:** @@ -620,9 +461,11 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Update axios to the latest version 🚀 [\#6](https://github.com/feathersjs/rest-client/pull/6) ([greenkeeper[bot]](https://github.com/apps/greenkeeper)) ## [v1.2.0](https://github.com/feathersjs/rest-client/tree/v1.2.0) (2017-10-19) + [Full Changelog](https://github.com/feathersjs/rest-client/compare/v1.1.1-0...v1.2.0) ## [v1.1.1-0](https://github.com/feathersjs/rest-client/tree/v1.1.1-0) (2017-10-19) + [Full Changelog](https://github.com/feathersjs/rest-client/compare/v1.1.0...v1.1.1-0) **Merged pull requests:** @@ -632,6 +475,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Update mocha to the latest version 🚀 [\#3](https://github.com/feathersjs/rest-client/pull/3) ([greenkeeper[bot]](https://github.com/apps/greenkeeper)) ## [v1.1.0](https://github.com/feathersjs/rest-client/tree/v1.1.0) (2017-07-20) + [Full Changelog](https://github.com/feathersjs/rest-client/compare/v1.0.0...v1.1.0) **Merged pull requests:** @@ -639,10 +483,9 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - add support for @angular/common/http \(HttpClient\) [\#2](https://github.com/feathersjs/rest-client/pull/2) ([j2L4e](https://github.com/j2L4e)) ## [v1.0.0](https://github.com/feathersjs/rest-client/tree/v1.0.0) (2017-07-16) + **Merged pull requests:** - Update dependencies to enable Greenkeeper 🌴 [\#1](https://github.com/feathersjs/rest-client/pull/1) ([greenkeeper[bot]](https://github.com/apps/greenkeeper)) - - -\* *This Change Log was automatically generated by [github_changelog_generator](https://github.com/skywinder/Github-Changelog-Generator)* +\* _This Change Log was automatically generated by [github_changelog_generator](https://github.com/skywinder/Github-Changelog-Generator)_ diff --git a/packages/rest-client/LICENSE b/packages/rest-client/LICENSE index 3f395cc665..59604f46f3 100644 --- a/packages/rest-client/LICENSE +++ b/packages/rest-client/LICENSE @@ -1,6 +1,6 @@ The MIT License (MIT) -Copyright (c) 2021 Feathers +Copyright (c) 2022 Feathers Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated documentation files (the "Software"), to deal diff --git a/packages/rest-client/README.md b/packages/rest-client/README.md index 0521e4535d..22c9728d73 100644 --- a/packages/rest-client/README.md +++ b/packages/rest-client/README.md @@ -1,8 +1,8 @@ # @feathersjs/rest-client [![CI](https://github.com/feathersjs/feathers/workflows/CI/badge.svg)](https://github.com/feathersjs/feathers/actions?query=workflow%3ACI) -[![Dependency Status](https://img.shields.io/david/feathersjs/feathers.svg?style=flat-square&path=packages/rest-client)](https://david-dm.org/feathersjs/feathers?path=packages/rest-client) [![Download Status](https://img.shields.io/npm/dm/@feathersjs/rest-client.svg?style=flat-square)](https://www.npmjs.com/package/@feathersjs/rest-client) +[![Discord](https://badgen.net/badge/icon/discord?icon=discord&label)](https://discord.gg/qa8kez8QBx) > REST client services for different Ajax libraries @@ -18,6 +18,6 @@ Refer to the [Feathers REST client API documentation](https://docs.feathersjs.co ## License -Copyright (c) 2021 [Feathers contributors](https://github.com/feathersjs/feathers/graphs/contributors) +Copyright (c) 2022 [Feathers contributors](https://github.com/feathersjs/feathers/graphs/contributors) Licensed under the [MIT license](LICENSE). diff --git a/packages/rest-client/package.json b/packages/rest-client/package.json index f5de82820d..83dcd92480 100644 --- a/packages/rest-client/package.json +++ b/packages/rest-client/package.json @@ -1,9 +1,10 @@ { "name": "@feathersjs/rest-client", "description": "REST client services for different Ajax libraries", - "version": "5.0.0-pre.16", + "version": "5.0.0-pre.31", "homepage": "https://feathersjs.com", - "main": "lib/index.js", + "main": "lib/", + "types": "lib/", "keywords": [ "feathers", "feathers-plugin" @@ -15,7 +16,8 @@ }, "repository": { "type": "git", - "url": "git://github.com/feathersjs/feathers.git" + "url": "git://github.com/feathersjs/feathers.git", + "directory": "packages/rest-client" }, "author": { "name": "Feathers contributors", @@ -40,7 +42,8 @@ ], "scripts": { "prepublish": "npm run compile", - "compile": "shx rm -rf lib/ && tsc", + "pack": "npm pack --pack-destination ../cli/test/build", + "compile": "shx rm -rf lib/ && tsc && npm run pack", "test": "mocha --config ../../.mocharc.json --recursive test/**.test.ts test/**/*.test.ts" }, "directories": { @@ -50,28 +53,28 @@ "access": "public" }, "dependencies": { - "@feathersjs/commons": "^5.0.0-pre.16", - "@feathersjs/errors": "^5.0.0-pre.16", - "@types/node-fetch": "^3.0.2", - "@types/superagent": "^4.1.14", - "qs": "^6.10.2" + "@feathersjs/commons": "^5.0.0-pre.31", + "@feathersjs/errors": "^5.0.0-pre.31", + "@feathersjs/feathers": "^5.0.0-pre.31", + "@types/superagent": "^4.1.15", + "qs": "^6.11.0" }, "devDependencies": { - "@feathersjs/express": "^5.0.0-pre.16", - "@feathersjs/feathers": "^5.0.0-pre.16", - "@feathersjs/memory": "^5.0.0-pre.16", - "@feathersjs/tests": "^5.0.0-pre.16", - "@types/mocha": "^9.0.0", - "@types/node": "^17.0.5", + "@feathersjs/express": "^5.0.0-pre.31", + "@feathersjs/memory": "^5.0.0-pre.31", + "@feathersjs/tests": "^5.0.0-pre.31", + "@types/mocha": "^10.0.0", + "@types/node": "^18.8.2", + "@types/node-fetch": "^2.6.2", "@types/qs": "^6.9.7", - "axios": "^0.24.0", - "mocha": "^9.1.3", + "axios": "^0.27.2", + "mocha": "^10.0.0", "node-fetch": "^2.6.1", - "rxjs": "^7.5.1", - "shx": "^0.3.3", - "superagent": "^6.1.0", - "ts-node": "^10.4.0", - "typescript": "^4.5.4" + "rxjs": "^7.5.7", + "shx": "^0.3.4", + "superagent": "^8.0.0", + "ts-node": "^10.9.1", + "typescript": "^4.8.4" }, - "gitHead": "f0cd227a82d159b528193bd33747c97684a48773" + "gitHead": "4500dbeb8cea566678cf88b3313a88efd93a2ed9" } diff --git a/packages/rest-client/src/axios.ts b/packages/rest-client/src/axios.ts index e90b8b76f4..16a2194867 100644 --- a/packages/rest-client/src/axios.ts +++ b/packages/rest-client/src/axios.ts @@ -1,23 +1,31 @@ -import { Params } from '@feathersjs/feathers'; -import { Base } from './base'; +import { Params } from '@feathersjs/feathers' +import { Base, RestClientParams } from './base' -export class AxiosClient extends Base { - request (options: any, params: Params) { - const config = Object.assign({ - url: options.url, - method: options.method, - data: options.body, - headers: Object.assign({ - Accept: 'application/json' - }, this.options.headers, options.headers) - }, params.connection); +export class AxiosClient, P extends Params = RestClientParams> extends Base { + request(options: any, params: RestClientParams) { + const config = Object.assign( + { + url: options.url, + method: options.method, + data: options.body, + headers: Object.assign( + { + Accept: 'application/json' + }, + this.options.headers, + options.headers + ) + }, + params.connection + ) - return this.connection.request(config) + return this.connection + .request(config) .then((res: any) => res.data) .catch((error: any) => { - const response = error.response || error; + const response = error.response || error - throw response instanceof Error ? response : (response.data || response); - }); + throw response instanceof Error ? response : response.data || response + }) } } diff --git a/packages/rest-client/src/base.ts b/packages/rest-client/src/base.ts index 6ea113e1a7..cfc44019fc 100644 --- a/packages/rest-client/src/base.ts +++ b/packages/rest-client/src/base.ts @@ -1,142 +1,178 @@ -import qs from 'qs'; -import { Params, Id, Query, NullableId, ServiceInterface } from '@feathersjs/feathers'; -import { Unavailable, convert } from '@feathersjs/errors'; -import { _, stripSlashes } from '@feathersjs/commons'; +import qs from 'qs' +import { Params, Id, Query, NullableId, ServiceInterface } from '@feathersjs/feathers' +import { Unavailable, convert } from '@feathersjs/errors' +import { _, stripSlashes } from '@feathersjs/commons' -function toError (error: Error & { code: string }) { +function toError(error: Error & { code: string }) { if (error.code === 'ECONNREFUSED') { - throw new Unavailable(error.message, _.pick(error, 'address', 'port', 'config')); + throw new Unavailable(error.message, _.pick(error, 'address', 'port', 'config')) } - throw convert(error); + throw convert(error) +} + +export interface RestClientParams extends Params { + connection?: any } interface RestClientSettings { - name: string; - base: string; - connection: any; - options: any; + name: string + base: string + connection: any + options: any } -export abstract class Base> implements ServiceInterface { - name: string; - base: string; - connection: any; - options: any; - - constructor (settings: RestClientSettings) { - this.name = stripSlashes(settings.name); - this.options = settings.options; - this.connection = settings.connection; - this.base = `${settings.base}/${this.name}`; +export abstract class Base, P extends Params = RestClientParams> + implements ServiceInterface +{ + name: string + base: string + connection: any + options: any + + constructor(settings: RestClientSettings) { + this.name = stripSlashes(settings.name) + this.options = settings.options + this.connection = settings.connection + this.base = `${settings.base}/${this.name}` } - makeUrl (query: Query, id?: string|number|null) { - let url = this.base; + makeUrl(query: Query, id?: string | number | null) { + let url = this.base - query = query || {}; + query = query || {} if (typeof id !== 'undefined' && id !== null) { - url += `/${encodeURIComponent(id)}`; + url += `/${encodeURIComponent(id)}` } - return url + this.getQuery(query); + return url + this.getQuery(query) } - getQuery (query: Query) { + getQuery(query: Query) { if (Object.keys(query).length !== 0) { - const queryString = qs.stringify(query); + const queryString = qs.stringify(query) - return `?${queryString}`; + return `?${queryString}` } - return ''; + return '' } - abstract request (options: any, params: Params): any; + abstract request(options: any, params: P): any - methods (this: any, ...names: string[]) { - names.forEach(method => { + methods(this: any, ...names: string[]) { + names.forEach((method) => { this[method] = function (body: any, params: Params = {}) { - return this.request({ - body, - url: this.makeUrl(params.query), - method: 'POST', - headers: Object.assign({ - 'Content-Type': 'application/json', - 'X-Service-Method': method - }, params.headers) - }, params).catch(toError); + return this.request( + { + body, + url: this.makeUrl(params.query), + method: 'POST', + headers: Object.assign( + { + 'Content-Type': 'application/json', + 'X-Service-Method': method + }, + params.headers + ) + }, + params + ).catch(toError) } - }); + }) - return this; + return this } - find (params: Params = {}) { - return this.request({ - url: this.makeUrl(params.query), - method: 'GET', - headers: Object.assign({}, params.headers) - }, params).catch(toError); + find(params?: P) { + return this.request( + { + url: this.makeUrl(params.query), + method: 'GET', + headers: Object.assign({}, params.headers) + }, + params + ).catch(toError) } - get (id: Id, params: Params = {}) { + get(id: Id, params?: P) { if (typeof id === 'undefined') { - return Promise.reject(new Error('id for \'get\' can not be undefined')); + return Promise.reject(new Error("id for 'get' can not be undefined")) } - return this.request({ - url: this.makeUrl(params.query, id), - method: 'GET', - headers: Object.assign({}, params.headers) - }, params).catch(toError); + return this.request( + { + url: this.makeUrl(params.query, id), + method: 'GET', + headers: Object.assign({}, params.headers) + }, + params + ).catch(toError) } - create (body: D, params: Params = {}) { - return this.request({ - url: this.makeUrl(params.query), - body, - method: 'POST', - headers: Object.assign({ 'Content-Type': 'application/json' }, params.headers) - }, params).catch(toError); + create(body: D, params?: P) { + return this.request( + { + url: this.makeUrl(params.query), + body, + method: 'POST', + headers: Object.assign({ 'Content-Type': 'application/json' }, params.headers) + }, + params + ).catch(toError) } - update (id: NullableId, body: D, params: Params = {}) { + update(id: NullableId, body: D, params?: P) { if (typeof id === 'undefined') { - return Promise.reject(new Error('id for \'update\' can not be undefined, only \'null\' when updating multiple entries')); + return Promise.reject( + new Error("id for 'update' can not be undefined, only 'null' when updating multiple entries") + ) } - return this.request({ - url: this.makeUrl(params.query, id), - body, - method: 'PUT', - headers: Object.assign({ 'Content-Type': 'application/json' }, params.headers) - }, params).catch(toError); + return this.request( + { + url: this.makeUrl(params.query, id), + body, + method: 'PUT', + headers: Object.assign({ 'Content-Type': 'application/json' }, params.headers) + }, + params + ).catch(toError) } - patch (id: NullableId, body: D, params: Params = {}) { + patch(id: NullableId, body: D, params?: P) { if (typeof id === 'undefined') { - return Promise.reject(new Error('id for \'patch\' can not be undefined, only \'null\' when updating multiple entries')); + return Promise.reject( + new Error("id for 'patch' can not be undefined, only 'null' when updating multiple entries") + ) } - return this.request({ - url: this.makeUrl(params.query, id), - body, - method: 'PATCH', - headers: Object.assign({ 'Content-Type': 'application/json' }, params.headers) - }, params).catch(toError); + return this.request( + { + url: this.makeUrl(params.query, id), + body, + method: 'PATCH', + headers: Object.assign({ 'Content-Type': 'application/json' }, params.headers) + }, + params + ).catch(toError) } - remove (id: NullableId, params: Params = {}) { + remove(id: NullableId, params?: P) { if (typeof id === 'undefined') { - return Promise.reject(new Error('id for \'remove\' can not be undefined, only \'null\' when removing multiple entries')); + return Promise.reject( + new Error("id for 'remove' can not be undefined, only 'null' when removing multiple entries") + ) } - return this.request({ - url: this.makeUrl(params.query, id), - method: 'DELETE', - headers: Object.assign({}, params.headers) - }, params).catch(toError); + return this.request( + { + url: this.makeUrl(params.query, id), + method: 'DELETE', + headers: Object.assign({}, params.headers) + }, + params + ).catch(toError) } } diff --git a/packages/rest-client/src/fetch.ts b/packages/rest-client/src/fetch.ts index 5e0703974c..724fbfc293 100644 --- a/packages/rest-client/src/fetch.ts +++ b/packages/rest-client/src/fetch.ts @@ -1,42 +1,49 @@ -import { Params } from '@feathersjs/feathers'; -import { errors } from '@feathersjs/errors'; -import { Base } from './base'; - -export class FetchClient extends Base { - request (options: any, params: Params) { - const fetchOptions = Object.assign({}, options, params.connection); - - fetchOptions.headers = Object.assign({ - Accept: 'application/json' - }, this.options.headers, fetchOptions.headers); +import { errors } from '@feathersjs/errors' +import { Params } from '@feathersjs/feathers' +import { Base, RestClientParams } from './base' + +export class FetchClient, P extends Params = RestClientParams> extends Base { + request(options: any, params: RestClientParams) { + const fetchOptions = Object.assign({}, options, params.connection) + + fetchOptions.headers = Object.assign( + { + Accept: 'application/json' + }, + this.options.headers, + fetchOptions.headers + ) if (options.body) { - fetchOptions.body = JSON.stringify(options.body); + fetchOptions.body = JSON.stringify(options.body) } return this.connection(options.url, fetchOptions) .then(this.checkStatus) .then((response: any) => { if (response.status === 204) { - return null; + return null } - return response.json(); - }); + return response.json() + }) } - checkStatus (response: any) { + checkStatus(response: any) { if (response.ok) { - return response; + return response } - return response.json().catch(() => { - const ErrorClass = (errors as any)[response.status] || Error; - - return new ErrorClass('JSON parsing error'); - }).then((error: any) => { - error.response = response; - throw error; - }); + return response + .json() + .catch(() => { + const ErrorClass = (errors as any)[response.status] || Error + + return new ErrorClass('JSON parsing error') + }) + .then((error: any) => { + error.response = response + throw error + }) } } diff --git a/packages/rest-client/src/index.ts b/packages/rest-client/src/index.ts index 05cbb63df7..d0afbaf7a5 100644 --- a/packages/rest-client/src/index.ts +++ b/packages/rest-client/src/index.ts @@ -1,80 +1,76 @@ -import { Base } from './base'; -import { AxiosClient } from './axios'; -import { FetchClient } from './fetch'; -import { SuperagentClient } from './superagent'; +import { Application, TransportConnection, defaultServiceMethods } from '@feathersjs/feathers' -export { AxiosClient, FetchClient, SuperagentClient }; +import { Base } from './base' +import { AxiosClient } from './axios' +import { FetchClient } from './fetch' +import { SuperagentClient } from './superagent' + +export { AxiosClient, FetchClient, SuperagentClient } const transports = { superagent: SuperagentClient, fetch: FetchClient, axios: AxiosClient -}; - -interface HandlerResult extends Function { - /** - * initialize service - */ - (): void; - - /** - * Transport Service - */ - Service: any; - - /** - * default Service - */ - service: any; } -export type Handler = (connection: any, options?: any, Service?: any) => HandlerResult; +export type Handler = ( + connection: any, + options?: any, + Service?: any +) => TransportConnection -export interface Transport { - superagent: Handler; - fetch: Handler; - axios: Handler; +export interface Transport { + superagent: Handler + fetch: Handler + axios: Handler } -export type RestService> = Base; +export type RestService> = Base -export default function restClient (base = '') { - const result: any = { Base }; +export default function restClient(base = '') { + const result: any = { Base } - Object.keys(transports).forEach(key => { + Object.keys(transports).forEach((key) => { result[key] = function (connection: any, options: any = {}, Service: Base = (transports as any)[key]) { if (!connection) { - throw new Error(`${key} has to be provided to feathers-rest`); + throw new Error(`${key} has to be provided to feathers-rest`) } if (typeof options === 'function') { - Service = options; - options = {}; + Service = options + options = {} } const defaultService = function (name: string) { - return new (Service as any)({ base, name, connection, options }); - }; + return new (Service as any)({ base, name, connection, options }) + } - const initialize = (app: any) => { + const initialize = (app: Application & { rest: any }) => { if (app.rest !== undefined) { - throw new Error('Only one default client provider can be configured'); + throw new Error('Only one default client provider can be configured') } - app.rest = connection; - app.defaultService = defaultService; - }; + app.rest = connection + app.defaultService = defaultService + app.mixins.unshift((service, _location, options) => { + if (options && options.methods && service instanceof Base) { + const customMethods = options.methods.filter((name) => !defaultServiceMethods.includes(name)) + + service.methods(...customMethods) + } + }) + } - initialize.Service = Service; - initialize.service = defaultService; + initialize.Service = Service + initialize.service = defaultService - return initialize; - }; - }); + return initialize + } + }) - return result as Transport; + return result as Transport } if (typeof module !== 'undefined') { - module.exports = Object.assign(restClient, module.exports); + module.exports = Object.assign(restClient, module.exports) } diff --git a/packages/rest-client/src/superagent.ts b/packages/rest-client/src/superagent.ts index 7666a16dd3..d93474b69f 100644 --- a/packages/rest-client/src/superagent.ts +++ b/packages/rest-client/src/superagent.ts @@ -1,35 +1,39 @@ -import { Params } from '@feathersjs/feathers'; -import { Base } from './base'; +import { Params } from '@feathersjs/feathers' +import { Base, RestClientParams } from './base' -export class SuperagentClient extends Base { - request (options: any, params: Params) { +export class SuperagentClient, P extends Params = RestClientParams> extends Base< + T, + D, + P +> { + request(options: any, params: RestClientParams) { const superagent = this.connection(options.method, options.url) .set(this.options.headers || {}) .set('Accept', 'application/json') .set(params.connection || {}) .set(options.headers || {}) - .type(options.type || 'json'); + .type(options.type || 'json') return new Promise((resolve, reject) => { - superagent.set(options.headers); + superagent.set(options.headers) if (options.body) { - superagent.send(options.body); + superagent.send(options.body) } superagent.end(function (error: any, res: any) { if (error) { try { - const response = error.response; - error = JSON.parse(error.response.text); - error.response = response; + const response = error.response + error = JSON.parse(error.response.text) + error.response = response } catch (e: any) {} - return reject(error); + return reject(error) } - resolve(res && res.body); - }); - }); + resolve(res && res.body) + }) + }) } } diff --git a/packages/rest-client/test/axios.test.ts b/packages/rest-client/test/axios.test.ts index 8a1194c6c8..02b9e1aef7 100644 --- a/packages/rest-client/test/axios.test.ts +++ b/packages/rest-client/test/axios.test.ts @@ -1,37 +1,38 @@ -import { strict as assert } from 'assert'; +import { strict as assert } from 'assert' -import axios from 'axios'; -import { Server } from 'http'; -import { feathers } from '@feathersjs/feathers'; -import { clientTests } from '@feathersjs/tests'; -import { NotAcceptable } from '@feathersjs/errors'; - -import createServer from './server'; -import rest from '../src'; -import { ServiceTypes } from './declarations'; +import axios from 'axios' +import { Server } from 'http' +import { feathers } from '@feathersjs/feathers' +import { clientTests } from '@feathersjs/tests' +import { NotAcceptable } from '@feathersjs/errors' +import createServer from './server' +import rest from '../src' +import { ServiceTypes } from './declarations' describe('Axios REST connector', function () { - const url = 'http://localhost:8889'; - const setup = rest(url).axios(axios); - const app = feathers().configure(setup); - const service = app.service('todos'); - let server: Server; - - service.methods('customMethod'); + const url = 'http://localhost:8889' + const connection = rest(url).axios(axios) + const app = feathers() + .configure(connection) + .use('todos', connection.service('todos'), { + methods: ['get', 'find', 'create', 'patch', 'customMethod'] + }) + const service = app.service('todos') + let server: Server before(async () => { - server = await createServer().listen(8889); - }); + server = await createServer().listen(8889) + }) - after(done => server.close(done)); + after((done) => server.close(done)) it('supports custom headers', async () => { const headers = { - 'Authorization': 'let-me-in' - }; + Authorization: 'let-me-in' + } - const todo = await service.get(0, { headers }); + const todo = await service.get(0, { headers }) assert.deepStrictEqual(todo, { id: 0, @@ -39,17 +40,17 @@ describe('Axios REST connector', function () { text: 'some todo', complete: false, query: {} - }); - }); + }) + }) it('uses params.connection for additional options', async () => { const connection = { headers: { - 'Authorization': 'let-me-in' + Authorization: 'let-me-in' } - }; + } - const todo = await service.get(0, { connection }); + const todo = await service.get(0, { connection }) assert.deepStrictEqual(todo, { id: 0, @@ -57,76 +58,78 @@ describe('Axios REST connector', function () { text: 'some todo', complete: false, query: {} - }); - }); + }) + }) it('can initialize a client instance', async () => { - const init = rest(url).axios(axios); - const todoService = init.service('todos'); + const init = rest(url).axios(axios) + const todoService = init.service('todos') - assert.ok(todoService instanceof init.Service, 'Returned service is a client'); + assert.ok(todoService instanceof init.Service, 'Returned service is a client') - const todos = await todoService.find({}); + const todos = await todoService.find({}) - assert.deepStrictEqual(todos, [{ - text: 'some todo', - complete: false, - id: 0 - }]); - }); + assert.deepStrictEqual(todos, [ + { + text: 'some todo', + complete: false, + id: 0 + } + ]) + }) it('supports nested arrays in queries', async () => { - const query = { test: { $in: [ '0', '1', '2' ] } }; + const query = { test: { $in: ['0', '1', '2'] } } - const data = await service.get(0, { query }); + const data = await service.get(0, { query }) assert.deepStrictEqual(data.query, query) - }); + }) it('remove many', async () => { - const todo: any = await service.remove(null); + const todo: any = await service.remove(null) - assert.strictEqual(todo.id, null); - assert.strictEqual(todo.text, 'deleted many'); - }); + assert.strictEqual(todo.id, null) + assert.strictEqual(todo.text, 'deleted many') + }) it('converts feathers errors (#50)', async () => { try { - await service.get(0, { query: { feathersError: true } }); - assert.fail('Should never get here'); + await service.get(0, { query: { feathersError: true } }) + assert.fail('Should never get here') } catch (error: any) { - assert.ok(error instanceof NotAcceptable); - assert.strictEqual(error.message, 'This is a Feathers error'); - assert.strictEqual(error.code, 406); + assert.ok(error instanceof NotAcceptable) + assert.strictEqual(error.message, 'This is a Feathers error') + assert.strictEqual(error.code, 406) } - }); + }) it('ECONNREFUSED errors are serializable', async () => { - const url = 'http://localhost:60000'; - const setup = rest(url).axios(axios); - const app = feathers().configure(setup); + const url = 'http://localhost:60000' + const setup = rest(url).axios(axios) + const app = feathers().configure(setup) try { - await app.service('something').find(); - assert.fail('Should never get here'); + await app.service('something').find() + assert.fail('Should never get here') } catch (e: any) { - const err = JSON.parse(JSON.stringify(e)); + const err = JSON.parse(JSON.stringify(e)) - assert.strictEqual(err.name, 'Unavailable'); - assert.strictEqual(err.message, 'connect ECONNREFUSED 127.0.0.1:60000'); - assert.ok(e.data.config); + assert.strictEqual(err.name, 'Unavailable') + assert.ok(err.message.startsWith('connect ECONNREFUSED')) + assert.ok(e.data.config) } - }); + }) it('works with custom method .customMethod', async () => { - const result = await service.customMethod({ message: 'hi' }); + const result = await service.customMethod({ message: 'hi' }) assert.deepEqual(result, { data: { message: 'hi' }, provider: 'rest', type: 'customMethod' - }); - }); + }) + }) - clientTests(service, 'todos'); -}); + clientTests(service, 'todos') +}) diff --git a/packages/rest-client/test/declarations.ts b/packages/rest-client/test/declarations.ts index 06f94766c2..a29a067e10 100644 --- a/packages/rest-client/test/declarations.ts +++ b/packages/rest-client/test/declarations.ts @@ -1,6 +1,15 @@ -import { CustomMethods } from '@feathersjs/feathers'; -import { RestService } from '../src'; +import { CustomMethod } from '@feathersjs/feathers' +import { RestService } from '../src' + +type Data = { message: string } +type Result = { + data: Data + provider: string + type: string +} export type ServiceTypes = { - todos: RestService & CustomMethods<{customMethod: any}> + todos: RestService & { + customMethod: CustomMethod + } } diff --git a/packages/rest-client/test/fetch.test.ts b/packages/rest-client/test/fetch.test.ts index 4f51025116..54ea3cec8e 100644 --- a/packages/rest-client/test/fetch.test.ts +++ b/packages/rest-client/test/fetch.test.ts @@ -1,37 +1,48 @@ -import { strict as assert } from 'assert'; +import { strict as assert } from 'assert' +import fetch from 'node-fetch' +import { feathers } from '@feathersjs/feathers' +import { clientTests } from '@feathersjs/tests' +import { NotAcceptable } from '@feathersjs/errors' +import { Server } from 'http' -//@ts-ignore -import fetch from 'node-fetch'; -import { feathers } from '@feathersjs/feathers'; -import { clientTests } from '@feathersjs/tests'; -import { NotAcceptable } from '@feathersjs/errors'; -import { Server } from 'http'; - -import rest from '../src'; -import createServer from './server'; -import { ServiceTypes } from './declarations'; +import rest from '../src' +import createServer from './server' +import { ServiceTypes } from './declarations' describe('fetch REST connector', function () { - const url = 'http://localhost:8889'; - const setup = rest(url).fetch(fetch); - const app = feathers().configure(setup); - const service = app.service('todos'); - let server: Server; + const url = 'http://localhost:8889' + const connection = rest(url).fetch(fetch) + const app = feathers() + .configure(connection) + .use('todos', connection.service('todos'), { + methods: ['get', 'find', 'create', 'patch', 'customMethod'] + }) + + const service = app.service('todos') + let server: Server - service.methods('customMethod'); + service.hooks({ + after: { + customMethod: [ + (context) => { + context.result.data.message += '!' + } + ] + } + }) before(async () => { - server = await createServer().listen(8889); - }); + server = await createServer().listen(8889) + }) - after(done => server.close(done)); + after((done) => server.close(done)) it('supports custom headers', async () => { const headers = { - 'Authorization': 'let-me-in' - }; + Authorization: 'let-me-in' + } - const todo = await service.get(0, { headers }); + const todo = await service.get(0, { headers }) assert.deepStrictEqual(todo, { id: 0, @@ -40,16 +51,16 @@ describe('fetch REST connector', function () { complete: false, query: {} }) - }); + }) it('supports params.connection', async () => { const connection = { headers: { - 'Authorization': 'let-me-in' + Authorization: 'let-me-in' } - }; + } - const todo = await service.get(0, { connection }); + const todo = await service.get(0, { connection }) assert.deepStrictEqual(todo, { id: 0, @@ -58,77 +69,79 @@ describe('fetch REST connector', function () { complete: false, query: {} }) - }); + }) it('handles errors properly', async () => { try { - await service.get(-1, {}); - assert.fail('Should never get here'); + await service.get(-1, {}) + assert.fail('Should never get here') } catch (error: any) { assert.strictEqual(error.code, 404) } - }); + }) it('supports nested arrays in queries', async () => { - const query = { test: { $in: [ '0', '1', '2' ] } }; + const query = { test: { $in: ['0', '1', '2'] } } - const data = await service.get(0, { query }); + const data = await service.get(0, { query }) assert.deepStrictEqual(data.query, query) - }); + }) it('can initialize a client instance', async () => { - const init = rest(url).fetch(fetch); - const todoService = init.service('todos'); + const init = rest(url).fetch(fetch) + const todoService = init.service('todos') - assert.ok(todoService instanceof init.Service, 'Returned service is a client'); + assert.ok(todoService instanceof init.Service, 'Returned service is a client') - const todos = await todoService.find({}); + const todos = await todoService.find({}) - assert.deepStrictEqual(todos, [{ - text: 'some todo', - complete: false, - id: 0 - }]); - }); + assert.deepStrictEqual(todos, [ + { + text: 'some todo', + complete: false, + id: 0 + } + ]) + }) it('remove many', async () => { - const todo: any = await service.remove(null); + const todo: any = await service.remove(null) - assert.strictEqual(todo.id, null); - assert.strictEqual(todo.text, 'deleted many'); - }); + assert.strictEqual(todo.id, null) + assert.strictEqual(todo.text, 'deleted many') + }) it('converts feathers errors (#50)', async () => { try { - await service.get(0, { query: { feathersError: true } }); - assert.fail('Should never get here'); + await service.get(0, { query: { feathersError: true } }) + assert.fail('Should never get here') } catch (error: any) { - assert.ok(error.response); - assert.ok(error instanceof NotAcceptable); - assert.strictEqual(error.message, 'This is a Feathers error'); - assert.strictEqual(error.code, 406); - assert.deepStrictEqual(error.data, { data: true }); + assert.ok(error.response) + assert.ok(error instanceof NotAcceptable) + assert.strictEqual(error.message, 'This is a Feathers error') + assert.strictEqual(error.code, 406) + assert.deepStrictEqual(error.data, { data: true }) } - }); + }) it('returns null for 204 responses', async () => { const response = await service.remove(0, { query: { noContent: true } - }); + }) assert.strictEqual(response, null) - }); + }) it('works with custom method .customMethod', async () => { - const result = await service.customMethod({ message: 'hi' }); + const result = await service.customMethod({ message: 'hi' }) assert.deepEqual(result, { - data: { message: 'hi' }, + data: { message: 'hi!' }, provider: 'rest', type: 'customMethod' - }); - }); + }) + }) - clientTests(service, 'todos'); -}); + clientTests(service, 'todos') +}) diff --git a/packages/rest-client/test/index.test.ts b/packages/rest-client/test/index.test.ts index 265edfe58b..5ca9a61098 100644 --- a/packages/rest-client/test/index.test.ts +++ b/packages/rest-client/test/index.test.ts @@ -1,118 +1,117 @@ - -//@ts-ignore -import fetch from 'node-fetch'; -import { strict as assert } from 'assert'; -import { feathers } from '@feathersjs/feathers'; -import { default as init, FetchClient } from '../src'; +/* eslint-disable @typescript-eslint/ban-ts-comment */ +// @ts-ignore +import fetch from 'node-fetch' +import { strict as assert } from 'assert' +import { feathers } from '@feathersjs/feathers' +import { default as init, FetchClient } from '../src' describe('REST client tests', function () { it('is built correctly', () => { - const transports = init(); + const transports = init() - assert.strictEqual(typeof init, 'function'); - assert.strictEqual(typeof transports.superagent, 'function'); - assert.strictEqual(typeof transports.fetch, 'function'); - assert.strictEqual(typeof transports.axios, 'function'); - }); + assert.strictEqual(typeof init, 'function') + assert.strictEqual(typeof transports.superagent, 'function') + assert.strictEqual(typeof transports.fetch, 'function') + assert.strictEqual(typeof transports.axios, 'function') + }) it('throw errors when no connection is provided', () => { - const transports = init(); + const transports = init() try { // @ts-ignore - transports.fetch(); + transports.fetch() } catch (e: any) { - assert.strictEqual(e.message, 'fetch has to be provided to feathers-rest'); + assert.strictEqual(e.message, 'fetch has to be provided to feathers-rest') } - }); + }) it('app has the rest attribute', () => { - const app = feathers(); + const app = feathers() - app.configure(init('http://localhost:8889').fetch(fetch)); + app.configure(init('http://localhost:8889').fetch(fetch)) - assert.ok((app as any).rest); - }); + assert.ok((app as any).rest) + }) it('throws an error when configured twice', () => { - const app = feathers(); + const app = feathers() - app.configure(init('http://localhost:8889').fetch(fetch)); + app.configure(init('http://localhost:8889').fetch(fetch)) try { - app.configure(init('http://localhost:8889').fetch(fetch)); - assert.ok(false, 'Should never get here'); + app.configure(init('http://localhost:8889').fetch(fetch)) + assert.ok(false, 'Should never get here') } catch (e: any) { - assert.strictEqual(e.message, 'Only one default client provider can be configured'); + assert.strictEqual(e.message, 'Only one default client provider can be configured') } - }); + }) it('errors when id property for get, patch, update or remove is undefined', async () => { - const app = feathers().configure(init('http://localhost:8889') - .fetch(fetch)); + const app = feathers().configure(init('http://localhost:8889').fetch(fetch)) - const service = app.service('todos'); + const service = app.service('todos') await assert.rejects(() => service.get(undefined), { - message: 'id for \'get\' can not be undefined' - }); + message: "id for 'get' can not be undefined" + }) await assert.rejects(() => service.remove(undefined), { - message: 'id for \'remove\' can not be undefined, only \'null\' when removing multiple entries' - }); + message: "id for 'remove' can not be undefined, only 'null' when removing multiple entries" + }) await assert.rejects(() => service.update(undefined, {}), { - message: 'id for \'update\' can not be undefined, only \'null\' when updating multiple entries' - }); + message: "id for 'update' can not be undefined, only 'null' when updating multiple entries" + }) await assert.rejects(() => service.patch(undefined, {}), { - message: 'id for \'patch\' can not be undefined, only \'null\' when updating multiple entries' - }); - }); + message: "id for 'patch' can not be undefined, only 'null' when updating multiple entries" + }) + }) it('uses a custom client', async () => { - const app = feathers(); + const app = feathers() class MyFetchClient extends FetchClient { - find () { + find() { return Promise.resolve({ connection: this.connection, base: this.base, message: 'Custom fetch client' - }); + }) } } - app.configure(init('http://localhost:8889').fetch(fetch, {}, MyFetchClient)); + app.configure(init('http://localhost:8889').fetch(fetch, {}, MyFetchClient)) - const data = await app.service('messages').find(); + const data = await app.service('messages').find() assert.deepStrictEqual(data, { connection: fetch, base: 'http://localhost:8889/messages', message: 'Custom fetch client' - }); - }); + }) + }) it('uses a custom client as second arg', async () => { - const app = feathers(); + const app = feathers() class MyFetchClient extends FetchClient { - find () { + find() { return Promise.resolve({ connection: this.connection, base: this.base, message: 'Custom fetch client' - }); + }) } } - app.configure(init('http://localhost:8889').fetch(fetch, MyFetchClient)); + app.configure(init('http://localhost:8889').fetch(fetch, MyFetchClient)) - const data = await app.service('messages').find(); + const data = await app.service('messages').find() assert.deepStrictEqual(data, { connection: fetch, base: 'http://localhost:8889/messages', message: 'Custom fetch client' - }); - }); -}); + }) + }) +}) diff --git a/packages/rest-client/test/server.ts b/packages/rest-client/test/server.ts index c738499612..7035774c1e 100644 --- a/packages/rest-client/test/server.ts +++ b/packages/rest-client/test/server.ts @@ -1,72 +1,77 @@ -import { feathers, Id, NullableId, Params } from '@feathersjs/feathers'; -import expressify, { rest, urlencoded, json } from '@feathersjs/express'; -import { Service } from '@feathersjs/memory'; -import { FeathersError, NotAcceptable } from '@feathersjs/errors'; +import { feathers, Id, NullableId, Params } from '@feathersjs/feathers' +import expressify, { rest, urlencoded, json } from '@feathersjs/express' +import { MemoryService } from '@feathersjs/memory' +import { FeathersError, NotAcceptable } from '@feathersjs/errors' // eslint-disable-next-line no-extend-native Object.defineProperty(Error.prototype, 'toJSON', { - value () { - const alt: any = {}; + value() { + const alt: any = {} Object.getOwnPropertyNames(this).forEach((key: string) => { - alt[key] = this[key]; - }, this); + alt[key] = this[key] + }, this) - return alt; + return alt }, configurable: true, writable: true -}); +}) -const errorHandler = function (error: FeathersError, _req: any, res: any, _next: any) { // eslint-disable-line @typescript-eslint/no-unused-vars - const code = !isNaN(parseInt(error.code as any, 10)) ? parseInt(error.code as any, 10) : 500; - res.status(code); +const errorHandler = function (error: FeathersError, _req: any, res: any, _next: any) { + // eslint-disable-line @typescript-eslint/no-unused-vars + const code = !isNaN(parseInt(error.code as any, 10)) ? parseInt(error.code as any, 10) : 500 + res.status(code) res.format({ - 'application/json' () { - res.json(Object.assign({}, error.toJSON())); + 'application/json'() { + res.json(Object.assign({}, error.toJSON())) } - }); -}; + }) +} + +interface TodoServiceParams extends Params { + authorization: any +} // Create an in-memory CRUD service for our Todos -class TodoService extends Service { - get (id: Id, params: Params) { +class TodoService extends MemoryService { + get(id: Id, params: TodoServiceParams) { if (params.query.error) { - throw new Error('Something went wrong'); + throw new Error('Something went wrong') } if (params.query.feathersError) { - throw new NotAcceptable('This is a Feathers error', { data: true }); + throw new NotAcceptable('This is a Feathers error', { data: true }) } - return super.get(id) - .then(data => { - const result = Object.assign({ query: params.query }, data); + return super.get(id).then((data) => { + const result = Object.assign({ query: params.query }, data) - if (params.authorization) { - result.authorization = params.authorization; - } + if (params.authorization) { + result.authorization = params.authorization + } - return result; - }); + return result + }) } - remove (id: NullableId, params: Params) { + remove(id: NullableId, params: Params) { if (id === null) { return Promise.resolve({ - id, text: 'deleted many' - }); + id, + text: 'deleted many' + }) } if (params.query.noContent) { - return Promise.resolve(); + return Promise.resolve() } - return super.remove(id, params); + return super.remove(id, params) } - async customMethod (data: any, { provider }: Params) { + async customMethod(data: any, { provider }: Params) { return { data, provider, @@ -78,45 +83,48 @@ class TodoService extends Service { export default (configurer?: any) => { const app = expressify(feathers()) .use(function (req, res, next) { - res.header('Access-Control-Allow-Origin', '*'); - res.header('Access-Control-Allow-Headers', 'Authorization'); - req.feathers.authorization = req.headers.authorization; - next(); + res.header('Access-Control-Allow-Origin', '*') + res.header('Access-Control-Allow-Headers', 'Authorization') + req.feathers = { + ...req.feathers, + authorization: req.headers.authorization + } + next() }) // Parse HTTP bodies .use(json()) .use(urlencoded({ extended: true })) - .configure(rest(function formatter (_req, res, next) { - if (!res.data) { - next(); - } - - res.format({ - html () { - res.end('

This is HTML content. You should not see it.

'); - }, - - json () { - res.json(res.data); + .configure( + rest(function formatter(_req, res, next) { + if (!res.data) { + next() } - }); - })) + + res.format({ + html() { + res.end('

This is HTML content. You should not see it.

') + }, + + json() { + res.json(res.data) + } + }) + }) + ) // Host our Todos service on the /todos path - .use('/todos', new TodoService(), { - methods: [ - 'find', 'get', 'create', 'patch', 'update', 'remove', 'customMethod' - ] + .use('todos', new TodoService(), { + methods: ['find', 'get', 'create', 'patch', 'update', 'remove', 'customMethod'] }) - .use(errorHandler); + .use(errorHandler) if (typeof configurer === 'function') { - configurer.call(app); + configurer.call(app) } app.service('todos').create({ text: 'some todo', complete: false - }); + }) - return app; -}; + return app +} diff --git a/packages/rest-client/test/superagent.test.ts b/packages/rest-client/test/superagent.test.ts index f3ce481c2b..7e705b4288 100644 --- a/packages/rest-client/test/superagent.test.ts +++ b/packages/rest-client/test/superagent.test.ts @@ -1,37 +1,37 @@ -import { strict as assert } from 'assert'; +import { strict as assert } from 'assert' -import superagent from 'superagent'; -import { Server } from 'http'; -import { feathers } from '@feathersjs/feathers'; -import { clientTests } from '@feathersjs/tests'; -import { NotAcceptable } from '@feathersjs/errors'; +import superagent from 'superagent' +import { Server } from 'http' +import { feathers } from '@feathersjs/feathers' +import { clientTests } from '@feathersjs/tests' +import { NotAcceptable } from '@feathersjs/errors' -import rest from '../src'; -import createServer from './server'; -import { ServiceTypes } from './declarations'; +import rest from '../src' +import createServer from './server' +import { ServiceTypes } from './declarations' describe('Superagent REST connector', function () { - let server: Server; + let server: Server - const url = 'http://localhost:8889'; - const setup = rest(url).superagent(superagent); - const app = feathers().configure(setup); - const service = app.service('todos'); - - service.methods('customMethod'); + const url = 'http://localhost:8889' + const setup = rest(url).superagent(superagent) + const app = feathers().configure(setup) + const service = app.service('todos') + + service.methods('customMethod') before(async () => { - server = await createServer().listen(8889); - }); + server = await createServer().listen(8889) + }) - after(done => server.close(done)); + after((done) => server.close(done)) it('supports custom headers', async () => { const headers = { - 'Authorization': 'let-me-in' - }; + Authorization: 'let-me-in' + } - const todo = await service.get(0, { headers }); + const todo = await service.get(0, { headers }) assert.deepStrictEqual(todo, { id: 0, @@ -40,14 +40,14 @@ describe('Superagent REST connector', function () { complete: false, query: {} }) - }); + }) it('supports params.connection', async () => { const connection = { - 'Authorization': 'let-me-in' - }; + Authorization: 'let-me-in' + } - const todo = await service.get(0, { connection }); + const todo = await service.get(0, { connection }) assert.deepStrictEqual(todo, { id: 0, @@ -56,59 +56,61 @@ describe('Superagent REST connector', function () { complete: false, query: {} }) - }); + }) it('can initialize a client instance', async () => { - const init = rest(url).superagent(superagent); - const todoService = init.service('todos'); + const init = rest(url).superagent(superagent) + const todoService = init.service('todos') - assert.ok(todoService instanceof init.Service, 'Returned service is a client'); + assert.ok(todoService instanceof init.Service, 'Returned service is a client') - const todos = await todoService.find({}); + const todos = await todoService.find({}) - assert.deepStrictEqual(todos, [{ - text: 'some todo', - complete: false, - id: 0 - }]) - }); + assert.deepStrictEqual(todos, [ + { + text: 'some todo', + complete: false, + id: 0 + } + ]) + }) it('supports nested arrays in queries', async () => { - const query = { test: { $in: [ '0', '1', '2' ] } }; + const query = { test: { $in: ['0', '1', '2'] } } - const data = await service.get(0, { query }); + const data = await service.get(0, { query }) assert.deepStrictEqual(data.query, query) - }); + }) it('remove many', async () => { - const todo: any = await service.remove(null); + const todo: any = await service.remove(null) - assert.strictEqual(todo.id, null); - assert.strictEqual(todo.text, 'deleted many'); - }); + assert.strictEqual(todo.id, null) + assert.strictEqual(todo.text, 'deleted many') + }) it('converts feathers errors (#50)', async () => { try { - await service.get(0, { query: { feathersError: true } }); - assert.fail('Should never get here'); + await service.get(0, { query: { feathersError: true } }) + assert.fail('Should never get here') } catch (error: any) { - assert.ok(error instanceof NotAcceptable); - assert.strictEqual(error.message, 'This is a Feathers error'); - assert.strictEqual(error.code, 406); - assert.ok((error as any).response); + assert.ok(error.response) + assert.ok(error instanceof NotAcceptable) + assert.strictEqual(error.message, 'This is a Feathers error') + assert.strictEqual(error.code, 406) } - }); + }) it('works with custom method .customMethod', async () => { - const result = await service.customMethod({ message: 'hi' }); + const result = await service.customMethod({ message: 'hi' }) assert.deepEqual(result, { data: { message: 'hi' }, provider: 'rest', type: 'customMethod' - }); - }); + }) + }) - clientTests(service, 'todos'); -}); + clientTests(service, 'todos') +}) diff --git a/packages/schema/CHANGELOG.md b/packages/schema/CHANGELOG.md index 1cf2f8f02c..a2ea67b3fd 100644 --- a/packages/schema/CHANGELOG.md +++ b/packages/schema/CHANGELOG.md @@ -3,73 +3,164 @@ All notable changes to this project will be documented in this file. See [Conventional Commits](https://conventionalcommits.org) for commit guidelines. -# [5.0.0-pre.16](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.15...v5.0.0-pre.16) (2022-01-12) +# [5.0.0-pre.31](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.30...v5.0.0-pre.31) (2022-10-12) + +### Features + +- **cli:** Generate full client test suite and improve typed client ([#2788](https://github.com/feathersjs/feathers/issues/2788)) ([57119b6](https://github.com/feathersjs/feathers/commit/57119b6bb2797f7297cf054268a248c093ecd538)) +- **cli:** Improve generated schema definitions ([#2783](https://github.com/feathersjs/feathers/issues/2783)) ([474a9fd](https://github.com/feathersjs/feathers/commit/474a9fda2107e9bcf357746320a8e00cda8182b6)) + +# [5.0.0-pre.30](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.29...v5.0.0-pre.30) (2022-10-07) + +### Features + +- **core:** Allow to unregister services at runtime ([#2756](https://github.com/feathersjs/feathers/issues/2756)) ([d16601f](https://github.com/feathersjs/feathers/commit/d16601f2277dca5357866ffdefba2a611f6dc7fa)) +- **schema:** Make schemas validation library independent and add TypeBox support ([#2772](https://github.com/feathersjs/feathers/issues/2772)) ([44172d9](https://github.com/feathersjs/feathers/commit/44172d99b566d11d9ceda04f1d0bf72b6d05ce76)) + +# [5.0.0-pre.29](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.28...v5.0.0-pre.29) (2022-09-16) + +### Bug Fixes + +- **schema:** Fix for Ajv global collision bug [#2681](https://github.com/feathersjs/feathers/issues/2681) ([#2702](https://github.com/feathersjs/feathers/issues/2702)) ([0b2def6](https://github.com/feathersjs/feathers/commit/0b2def6ca483fad6ca22fcc4ea9873bc027925d8)) + +### Features + +- **authentication-oauth:** Koa and transport independent oAuth authentication ([#2737](https://github.com/feathersjs/feathers/issues/2737)) ([9231525](https://github.com/feathersjs/feathers/commit/9231525a24bb790ba9c5d940f2867a9c727691c9)) + +# [5.0.0-pre.28](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.27...v5.0.0-pre.28) (2022-08-03) + +### Bug Fixes + +- **cli:** Improve generated application and client ([#2701](https://github.com/feathersjs/feathers/issues/2701)) ([bd55ffb](https://github.com/feathersjs/feathers/commit/bd55ffb812e89bf215f4515e7f137656ea888c3f)) +# [5.0.0-pre.27](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.26...v5.0.0-pre.27) (2022-07-13) ### Bug Fixes -* **schema:** Do not error for schemas without properties ([#2519](https://github.com/feathersjs/feathers/issues/2519)) ([96fdb47](https://github.com/feathersjs/feathers/commit/96fdb47d45fd88a8039aa9cc9ec8aebd98672b95)) -* **schema:** Fix resolver data type and use new validation feature in test fixture ([#2523](https://github.com/feathersjs/feathers/issues/2523)) ([1093f12](https://github.com/feathersjs/feathers/commit/1093f124b60524cbd9050fcf07ddaf1d558973da)) +- Freeze the resolver context ([#2685](https://github.com/feathersjs/feathers/issues/2685)) ([247dccb](https://github.com/feathersjs/feathers/commit/247dccb2eb72551962030321cb1c0ecb11b0181e)) + +# [5.0.0-pre.26](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.25...v5.0.0-pre.26) (2022-06-22) + +**Note:** Version bump only for package @feathersjs/schema +# [5.0.0-pre.25](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.24...v5.0.0-pre.25) (2022-06-22) + +**Note:** Version bump only for package @feathersjs/schema + +# [5.0.0-pre.24](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.23...v5.0.0-pre.24) (2022-06-21) + +### Bug Fixes + +- **schema:** Fix dispatch resovler hook to convert actually resolved data ([#2663](https://github.com/feathersjs/feathers/issues/2663)) ([f7e87db](https://github.com/feathersjs/feathers/commit/f7e87dbb9a0bc8d89aee47318dddbaa4d6ba5b91)) ### Features -* **schema:** Allow to use custom AJV and test with ajv-formats ([#2513](https://github.com/feathersjs/feathers/issues/2513)) ([ecfa4df](https://github.com/feathersjs/feathers/commit/ecfa4df29f029f6ca8517cacf518c14b46ffeb4e)) -* **schema:** Improve schema typing, validation and extensibility ([#2521](https://github.com/feathersjs/feathers/issues/2521)) ([8c1b350](https://github.com/feathersjs/feathers/commit/8c1b35052792e82d13be03c06583534284fbae82)) +- **cli:** Add typed client to a generated app ([#2669](https://github.com/feathersjs/feathers/issues/2669)) ([5b801b5](https://github.com/feathersjs/feathers/commit/5b801b5017ddc3eaa95622b539f51d605916bc86)) +# [5.0.0-pre.23](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.22...v5.0.0-pre.23) (2022-06-06) +### Bug Fixes +- **schema:** Always resolve dispatch in resolveAll and add getDispatch method ([#2645](https://github.com/feathersjs/feathers/issues/2645)) ([145b366](https://github.com/feathersjs/feathers/commit/145b366435695438fbc8db9fdb161162ca9049ad)) +- **schema:** remove `default` from queryProperty schemas ([#2646](https://github.com/feathersjs/feathers/issues/2646)) ([940a2b6](https://github.com/feathersjs/feathers/commit/940a2b6868d2f77f81edb1661f6417ec2ea6e372)) +### Features -# [5.0.0-pre.15](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.14...v5.0.0-pre.15) (2021-11-27) +- **core:** Rename async hooks to around hooks, allow usual registration format ([#2652](https://github.com/feathersjs/feathers/issues/2652)) ([2a485a0](https://github.com/feathersjs/feathers/commit/2a485a07929184261f27437fc0fdfe5a44694834)) +# [5.0.0-pre.22](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.21...v5.0.0-pre.22) (2022-05-24) ### Bug Fixes -* **typescript:** Overall typing improvements ([#2478](https://github.com/feathersjs/feathers/issues/2478)) ([b8eb804](https://github.com/feathersjs/feathers/commit/b8eb804158556d9651a8607e3c3fda15e0bfd110)) +- **schema:** Allows resolveData with different resolvers based on method ([#2644](https://github.com/feathersjs/feathers/issues/2644)) ([be71fa2](https://github.com/feathersjs/feathers/commit/be71fa2fe260e05b7dcc0d5f439e33f2e9ec2434)) +# [5.0.0-pre.21](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.20...v5.0.0-pre.21) (2022-05-23) +### Bug Fixes +- **schema:** Add Combine helper to allow merging schema types that use ([#2637](https://github.com/feathersjs/feathers/issues/2637)) ([06d03e9](https://github.com/feathersjs/feathers/commit/06d03e91abb1347576c2351c12322d01c58473e5)) +- **typescript:** Make additional types generic to work with extended types ([#2625](https://github.com/feathersjs/feathers/issues/2625)) ([269fdec](https://github.com/feathersjs/feathers/commit/269fdecc5961092dc8608b3cbe16f433c80bfa96)) +### Features -# [5.0.0-pre.14](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.13...v5.0.0-pre.14) (2021-10-13) +- **schema:** Add resolveAll hook ([#2643](https://github.com/feathersjs/feathers/issues/2643)) ([85527d7](https://github.com/feathersjs/feathers/commit/85527d71cb78852880696e5d96abdcdf24593934)) +- **schema:** Add resolver for safe external data dispatching ([#2641](https://github.com/feathersjs/feathers/issues/2641)) ([72b980e](https://github.com/feathersjs/feathers/commit/72b980e05631136d30c8f1468dee45ec6a8d2503)) +- **schema:** Add schema resolver converter functionality ([#2640](https://github.com/feathersjs/feathers/issues/2640)) ([26d9e05](https://github.com/feathersjs/feathers/commit/26d9e05327d6e0144466cd57d6fcc11ac7ecb06a)) -**Note:** Version bump only for package @feathersjs/schema +# [5.0.0-pre.20](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.19...v5.0.0-pre.20) (2022-05-04) +### Bug Fixes +- **dependencies:** Lock monorepo package version numbers ([#2623](https://github.com/feathersjs/feathers/issues/2623)) ([5640c10](https://github.com/feathersjs/feathers/commit/5640c1020cc139994e695d658c08bad3494db507)) +### Features +- **schema:** Add querySyntax helper to create full query schemas ([#2621](https://github.com/feathersjs/feathers/issues/2621)) ([2bbb103](https://github.com/feathersjs/feathers/commit/2bbb103b2f3e30fb0fff935f92ad3276a1a67e41)) -# [5.0.0-pre.13](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.12...v5.0.0-pre.13) (2021-10-13) +# [5.0.0-pre.19](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.18...v5.0.0-pre.19) (2022-05-01) -**Note:** Version bump only for package @feathersjs/schema +### Features +- **schema:** Allow hooks to run resolvers in sequence ([#2609](https://github.com/feathersjs/feathers/issues/2609)) ([d85c507](https://github.com/feathersjs/feathers/commit/d85c507c76d07e48fc8e7e28ff7de0ef435e0ef8)) +- **typescript:** Improve adapter typings ([#2605](https://github.com/feathersjs/feathers/issues/2605)) ([3b2ca0a](https://github.com/feathersjs/feathers/commit/3b2ca0a6a8e03e8390272c4d7e930b4bffdaacf5)) +- **typescript:** Improve params and query typeability ([#2600](https://github.com/feathersjs/feathers/issues/2600)) ([df28b76](https://github.com/feathersjs/feathers/commit/df28b7619161f1df5e700326f52cca1a92dc5d28)) +# [5.0.0-pre.18](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.17...v5.0.0-pre.18) (2022-04-11) +### Bug Fixes +- **schema:** result resolver correctly resolves paginated find result ([#2594](https://github.com/feathersjs/feathers/issues/2594)) ([6511e45](https://github.com/feathersjs/feathers/commit/6511e45bd0624f1a629530719709f4b27fecbe0b)) -# [5.0.0-pre.12](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.11...v5.0.0-pre.12) (2021-10-12) +### Features -**Note:** Version bump only for package @feathersjs/schema +- **configuration:** Allow app configuration to be validated against a schema ([#2590](https://github.com/feathersjs/feathers/issues/2590)) ([a268f86](https://github.com/feathersjs/feathers/commit/a268f86da92a8ada14ed11ab456aac0a4bba5bb0)) +# [5.0.0-pre.17](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.16...v5.0.0-pre.17) (2022-02-15) +### Bug Fixes +- **hooks:** Allow all built-in hooks to be used the async and regular way ([#2559](https://github.com/feathersjs/feathers/issues/2559)) ([8f9f631](https://github.com/feathersjs/feathers/commit/8f9f631e0ce89de349207db72def84e7ab496a4a)) +- **queryProperty:** allow compound oneOf ([#2545](https://github.com/feathersjs/feathers/issues/2545)) ([3077d2d](https://github.com/feathersjs/feathers/commit/3077d2d896a38d579ce4d5b530e21ad332bcf221)) +- **schema:** Properly handle resolver errors ([#2540](https://github.com/feathersjs/feathers/issues/2540)) ([31fbdff](https://github.com/feathersjs/feathers/commit/31fbdff8bd848ac7e0eda56e307ac34b1bfcf17f)) +# [5.0.0-pre.16](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.15...v5.0.0-pre.16) (2022-01-12) -# [5.0.0-pre.11](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.10...v5.0.0-pre.11) (2021-10-06) +### Bug Fixes +- **schema:** Do not error for schemas without properties ([#2519](https://github.com/feathersjs/feathers/issues/2519)) ([96fdb47](https://github.com/feathersjs/feathers/commit/96fdb47d45fd88a8039aa9cc9ec8aebd98672b95)) +- **schema:** Fix resolver data type and use new validation feature in test fixture ([#2523](https://github.com/feathersjs/feathers/issues/2523)) ([1093f12](https://github.com/feathersjs/feathers/commit/1093f124b60524cbd9050fcf07ddaf1d558973da)) ### Features -* **schema:** Allow resolvers to validate a schema ([#2465](https://github.com/feathersjs/feathers/issues/2465)) ([7d9590b](https://github.com/feathersjs/feathers/commit/7d9590bbe12b94b8b5a7987684f5d4968e426481)) +- **schema:** Allow to use custom AJV and test with ajv-formats ([#2513](https://github.com/feathersjs/feathers/issues/2513)) ([ecfa4df](https://github.com/feathersjs/feathers/commit/ecfa4df29f029f6ca8517cacf518c14b46ffeb4e)) +- **schema:** Improve schema typing, validation and extensibility ([#2521](https://github.com/feathersjs/feathers/issues/2521)) ([8c1b350](https://github.com/feathersjs/feathers/commit/8c1b35052792e82d13be03c06583534284fbae82)) +# [5.0.0-pre.15](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.14...v5.0.0-pre.15) (2021-11-27) +### Bug Fixes +- **typescript:** Overall typing improvements ([#2478](https://github.com/feathersjs/feathers/issues/2478)) ([b8eb804](https://github.com/feathersjs/feathers/commit/b8eb804158556d9651a8607e3c3fda15e0bfd110)) +# [5.0.0-pre.14](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.13...v5.0.0-pre.14) (2021-10-13) -# [5.0.0-pre.10](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.9...v5.0.0-pre.10) (2021-09-19) +**Note:** Version bump only for package @feathersjs/schema + +# [5.0.0-pre.13](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.12...v5.0.0-pre.13) (2021-10-13) + +**Note:** Version bump only for package @feathersjs/schema + +# [5.0.0-pre.12](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.11...v5.0.0-pre.12) (2021-10-12) +**Note:** Version bump only for package @feathersjs/schema + +# [5.0.0-pre.11](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.10...v5.0.0-pre.11) (2021-10-06) + +### Features + +- **schema:** Allow resolvers to validate a schema ([#2465](https://github.com/feathersjs/feathers/issues/2465)) ([7d9590b](https://github.com/feathersjs/feathers/commit/7d9590bbe12b94b8b5a7987684f5d4968e426481)) + +# [5.0.0-pre.10](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.9...v5.0.0-pre.10) (2021-09-19) ### Features -* **schema:** Initial version of schema definitions and resolvers ([#2441](https://github.com/feathersjs/feathers/issues/2441)) ([c57a5cd](https://github.com/feathersjs/feathers/commit/c57a5cd56699a121647be4506d8f967e6d72ecae)) +- **schema:** Initial version of schema definitions and resolvers ([#2441](https://github.com/feathersjs/feathers/issues/2441)) ([c57a5cd](https://github.com/feathersjs/feathers/commit/c57a5cd56699a121647be4506d8f967e6d72ecae)) diff --git a/packages/schema/LICENSE b/packages/schema/LICENSE index 3f395cc665..59604f46f3 100644 --- a/packages/schema/LICENSE +++ b/packages/schema/LICENSE @@ -1,6 +1,6 @@ The MIT License (MIT) -Copyright (c) 2021 Feathers +Copyright (c) 2022 Feathers Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated documentation files (the "Software"), to deal diff --git a/packages/schema/README.md b/packages/schema/README.md index 5da33163eb..232e46f25c 100644 --- a/packages/schema/README.md +++ b/packages/schema/README.md @@ -1,8 +1,8 @@ # @feathersjs/schema [![CI](https://github.com/feathersjs/feathers/workflows/CI/badge.svg)](https://github.com/feathersjs/feathers/actions?query=workflow%3ACI) -[![Dependency Status](https://img.shields.io/david/feathersjs/feathers.svg?style=flat-square&path=packages/socketio)](https://david-dm.org/feathersjs/feathers?path=packages/schema) [![Download Status](https://img.shields.io/npm/dm/@feathersjs/schema.svg?style=flat-square)](https://www.npmjs.com/package/@feathersjs/schema) +[![Discord](https://badgen.net/badge/icon/discord?icon=discord&label)](https://discord.gg/qa8kez8QBx) > A common data schema definition format @@ -18,6 +18,6 @@ Refer to the [Feathers documentation](https://docs.feathersjs.com) for more deta ## License -Copyright (c) 2021 [Feathers contributors](https://github.com/feathersjs/feathers/graphs/contributors) +Copyright (c) 2022 [Feathers contributors](https://github.com/feathersjs/feathers/graphs/contributors) Licensed under the [MIT license](LICENSE). diff --git a/packages/schema/package.json b/packages/schema/package.json index fbc7c75504..a7b59e929b 100644 --- a/packages/schema/package.json +++ b/packages/schema/package.json @@ -1,9 +1,10 @@ { "name": "@feathersjs/schema", "description": "A common data schema definition format", - "version": "5.0.0-pre.16", + "version": "5.0.0-pre.31", "homepage": "https://feathersjs.com", "main": "lib/", + "types": "lib/", "keywords": [ "feathers", "feathers-plugin" @@ -15,7 +16,8 @@ }, "repository": { "type": "git", - "url": "git://github.com/feathersjs/feathers.git" + "url": "git://github.com/feathersjs/feathers.git", + "directory": "packages/schema" }, "author": { "name": "Feathers contributors", @@ -40,8 +42,10 @@ ], "scripts": { "prepublish": "npm run compile", - "compile": "shx rm -rf lib/ && tsc", - "test": "mocha --config ../../.mocharc.json --recursive test/**.test.ts test/**/*.test.ts" + "pack": "npm pack --pack-destination ../cli/test/build", + "compile": "shx rm -rf lib/ && tsc && npm run pack", + "mocha": "mocha --config ../../.mocharc.json --recursive test/**.test.ts test/**/*.test.ts", + "test": "npm run compile && npm run mocha" }, "directories": { "lib": "lib" @@ -50,21 +54,23 @@ "access": "public" }, "dependencies": { - "@feathersjs/errors": "^5.0.0-pre.16", - "@feathersjs/feathers": "^5.0.0-pre.16", - "@types/json-schema": "^7.0.9", - "ajv": "^8.8.2", - "json-schema": "^0.4.0", - "json-schema-to-ts": "^1.6.4" + "@feathersjs/commons": "^5.0.0-pre.31", + "@feathersjs/errors": "^5.0.0-pre.31", + "@feathersjs/feathers": "^5.0.0-pre.31", + "@feathersjs/hooks": "^0.7.5", + "@types/json-schema": "^7.0.11", + "ajv": "^8.11.0", + "ajv-formats": "^2.1.1", + "json-schema-to-ts": "^2.5.5" }, "devDependencies": { - "@feathersjs/memory": "^5.0.0-pre.16", - "@types/mocha": "^9.0.0", - "@types/node": "^17.0.5", + "@feathersjs/memory": "^5.0.0-pre.31", + "@types/mocha": "^10.0.0", + "@types/node": "^18.8.2", "ajv-formats": "^2.1.1", - "mocha": "^9.1.3", - "shx": "^0.3.3", - "typescript": "^4.5.4" + "mocha": "^10.0.0", + "shx": "^0.3.4", + "typescript": "^4.8.4" }, - "gitHead": "f0cd227a82d159b528193bd33747c97684a48773" + "gitHead": "4500dbeb8cea566678cf88b3313a88efd93a2ed9" } diff --git a/packages/schema/src/default-schemas.ts b/packages/schema/src/default-schemas.ts new file mode 100644 index 0000000000..a3ef7726c3 --- /dev/null +++ b/packages/schema/src/default-schemas.ts @@ -0,0 +1,157 @@ +import { FromSchema } from 'json-schema-to-ts' + +export const authenticationSettingsSchema = { + type: 'object', + required: ['secret', 'entity', 'authStrategies'], + properties: { + secret: { + type: 'string', + description: 'The JWT signing secret' + }, + entity: { + oneOf: [ + { + type: 'null' + }, + { + type: 'string' + } + ], + description: 'The name of the authentication entity (e.g. user)' + }, + entityId: { + type: 'string', + description: 'The name of the authentication entity id property' + }, + service: { + type: 'string', + description: 'The path of the entity service' + }, + authStrategies: { + type: 'array', + items: { type: 'string' }, + description: 'A list of authentication strategy names that are allowed to create JWT access tokens' + }, + parseStrategies: { + type: 'array', + items: { type: 'string' }, + description: + 'A list of authentication strategy names that should parse HTTP headers for authentication information (defaults to `authStrategies`)' + }, + jwtOptions: { + type: 'object' + }, + jwt: { + type: 'object', + properties: { + header: { + type: 'string', + default: 'Authorization', + description: 'The HTTP header containing the JWT' + }, + schemes: { + type: 'array', + items: { type: 'string' }, + description: 'An array of schemes to support' + } + } + }, + local: { + type: 'object', + required: ['usernameField', 'passwordField'], + properties: { + usernameField: { + type: 'string', + description: 'Name of the username field (e.g. `email`)' + }, + passwordField: { + type: 'string', + description: 'Name of the password field (e.g. `password`)' + }, + hashSize: { + type: 'number', + description: 'The BCrypt salt length' + }, + errorMessage: { + type: 'string', + default: 'Invalid login', + description: 'The error message to return on errors' + }, + entityUsernameField: { + type: 'string', + description: + 'Name of the username field on the entity if authentication request data and entity field names are different' + }, + entityPasswordField: { + type: 'string', + description: + 'Name of the password field on the entity if authentication request data and entity field names are different' + } + } + }, + oauth: { + type: 'object', + properties: { + redirect: { + type: 'string' + }, + origins: { + type: 'array', + items: { type: 'string' } + }, + defaults: { + type: 'object', + properties: { + key: { type: 'string' }, + secret: { type: 'string' } + } + } + } + } + } +} as const + +export type AuthenticationConfiguration = FromSchema + +export const sqlSettingsSchema = { + type: 'object', + properties: { + client: { type: 'string' }, + connection: { type: 'string' } + } +} as const + +/** + * Schema for properties that are available in a standard Feathers application. + */ +export const defaultAppSettings = { + authentication: authenticationSettingsSchema, + origins: { + type: 'array', + items: { + type: 'string' + } + }, + paginate: { + type: 'object', + additionalProperties: false, + required: ['default', 'max'], + properties: { + default: { type: 'number' }, + max: { type: 'number' } + } + }, + mongodb: { type: 'string' }, + mysql: sqlSettingsSchema, + postgresql: sqlSettingsSchema, + sqlite: sqlSettingsSchema, + mssql: sqlSettingsSchema +} as const + +export const defaultAppConfiguration = { + type: 'object', + additionalProperties: false, + properties: defaultAppSettings +} as const + +export type DefaultAppConfiguration = FromSchema diff --git a/packages/schema/src/hooks.ts b/packages/schema/src/hooks.ts deleted file mode 100644 index f2c9bd94e4..0000000000 --- a/packages/schema/src/hooks.ts +++ /dev/null @@ -1,117 +0,0 @@ -import { HookContext, NextFunction } from '@feathersjs/feathers'; -import { BadRequest } from '../../errors/lib'; -import { Resolver } from './resolver'; -import { Schema } from './schema'; - -const getContext = (context: HookContext) => { - return { - ...context, - params: { - ...context.params, - query: {} - } - } -} - -export const resolveQuery = (resolver: Resolver) => - async (context: HookContext, next: NextFunction) => { - const ctx = getContext(context); - const data = context?.params?.query || {}; - const query = await resolver.resolve(data, ctx, { - originalContext: context - }); - - context.params = { - ...context.params, - query - } - - return next(); - }; - -export const resolveData = (resolver: Resolver) => - async (context: HookContext, next: NextFunction) => { - const ctx = getContext(context); - const data = context.data; - const status = { - originalContext: context - }; - - if (Array.isArray(data)) { - context.data = await Promise.all(data.map(current => - resolver.resolve(current, ctx, status) - )); - } else { - context.data = await resolver.resolve(data, ctx, status); - } - - return next(); - }; - -export const resolveResult = (resolver: Resolver) => - async (context: HookContext, next: NextFunction) => { - const { $resolve: properties, ...query } = context.params?.query || {}; - const { resolve } = context.params; - const status = { - originalContext: context, - ...resolve, - properties - }; - - context.params = { - ...context.params, - query - } - - await next(); - - const ctx = getContext(context); - const data = context.method === 'find' && context.result.data - ? context.result.data - : context.result; - - if (Array.isArray(data)) { - context.result = await Promise.all(data.map(current => - resolver.resolve(current, ctx, status) - )); - } else { - context.result = await resolver.resolve(data, ctx, status); - } - }; - -export const validateQuery = (schema: Schema) => - async (context: HookContext, next: NextFunction) => { - const data = context?.params?.query || {}; - - try { - const query = await schema.validate(data); - - context.params = { - ...context.params, - query - } - - return next(); - } catch (error: any) { - throw (error.ajv ? new BadRequest(error.message, error.errors) : error); - } - }; - -export const validateData = (schema: Schema) => - async (context: HookContext, next: NextFunction) => { - const data = context.data; - - try { - if (Array.isArray(data)) { - context.data = await Promise.all(data.map(current => - schema.validate(current) - )); - } else { - context.data = await schema.validate(data); - } - } catch (error: any) { - throw (error.ajv ? new BadRequest(error.message, error.errors) : error); - } - - return next(); - }; diff --git a/packages/schema/src/hooks/index.ts b/packages/schema/src/hooks/index.ts new file mode 100644 index 0000000000..935ab76328 --- /dev/null +++ b/packages/schema/src/hooks/index.ts @@ -0,0 +1,2 @@ +export * from './resolve' +export * from './validate' diff --git a/packages/schema/src/hooks/resolve.ts b/packages/schema/src/hooks/resolve.ts new file mode 100644 index 0000000000..8312c450a9 --- /dev/null +++ b/packages/schema/src/hooks/resolve.ts @@ -0,0 +1,193 @@ +import { HookContext, NextFunction } from '@feathersjs/feathers' +import { compose } from '@feathersjs/hooks' +import { Resolver, ResolverStatus } from '../resolver' + +const getContext = (context: H) => { + return Object.freeze({ + ...context, + params: Object.freeze({ + ...context.params, + query: Object.freeze({}) + }) + }) +} + +const getData = (context: H) => { + const isPaginated = context.method === 'find' && context.result.data + const data = isPaginated ? context.result.data : context.result + + return { isPaginated, data } +} + +const runResolvers = async ( + resolvers: Resolver[], + data: any, + ctx: H, + status?: Partial> +) => { + let current: any = data + + for (const resolver of resolvers) { + if (resolver && typeof resolver.resolve === 'function') { + current = await resolver.resolve(current, ctx, status) + } + } + + return current as T +} + +export type ResolverSetting = Resolver | Resolver[] + +export type DataResolvers = { + create: Resolver + patch: Resolver + update: Resolver +} + +export type ResolveAllSettings = { + data?: DataResolvers + query?: Resolver + result?: Resolver + dispatch?: Resolver +} + +export const DISPATCH = Symbol('@feathersjs/schema/dispatch') + +export const getDispatch = (value: any) => + typeof value === 'object' && value !== null && value[DISPATCH] !== undefined ? value[DISPATCH] : value + +export const resolveQuery = + (...resolvers: Resolver[]) => + async (context: H, next?: NextFunction) => { + const ctx = getContext(context) + const data = context?.params?.query || {} + const query = await runResolvers(resolvers, data, ctx) + + context.params = { + ...context.params, + query + } + + if (typeof next === 'function') { + return next() + } + } + +export const resolveData = + (settings: DataResolvers | Resolver) => + async (context: H, next?: NextFunction) => { + if (context.method === 'create' || context.method === 'patch' || context.method === 'update') { + const resolvers = settings instanceof Resolver ? [settings] : [settings[context.method]] + const ctx = getContext(context) + const data = context.data + + const status = { + originalContext: context + } + + if (Array.isArray(data)) { + context.data = await Promise.all(data.map((current) => runResolvers(resolvers, current, ctx, status))) + } else { + context.data = await runResolvers(resolvers, data, ctx, status) + } + } + + if (typeof next === 'function') { + return next() + } + } + +export const resolveResult = + (...resolvers: Resolver[]) => + async (context: H, next?: NextFunction) => { + if (typeof next === 'function') { + const { $resolve: properties, ...query } = context.params?.query || {} + const resolve = { + originalContext: context, + ...context.params.resolve, + properties + } + + context.params = { + ...context.params, + resolve, + query + } + + await next() + } + + const ctx = getContext(context) + const status = context.params.resolve + const { isPaginated, data } = getData(context) + + const result = Array.isArray(data) + ? await Promise.all(data.map(async (current) => runResolvers(resolvers, current, ctx, status))) + : await runResolvers(resolvers, data, ctx, status) + + if (isPaginated) { + context.result.data = result + } else { + context.result = result + } + } + +export const resolveDispatch = + (...resolvers: Resolver[]) => + async (context: H, next?: NextFunction) => { + if (typeof next === 'function') { + await next() + } + + const ctx = getContext(context) + const status = context.params.resolve + const { isPaginated, data } = getData(context) + const resolveAndGetDispatch = async (current: any) => { + const resolved: any = await runResolvers(resolvers, current, ctx, status) + + return Object.keys(resolved).reduce((res, key) => { + res[key] = getDispatch(resolved[key]) + + return res + }, {} as any) + } + + const result = await (Array.isArray(data) + ? Promise.all(data.map(resolveAndGetDispatch)) + : resolveAndGetDispatch(data)) + const dispatch = isPaginated + ? { + ...context.result, + data: result + } + : result + + context.dispatch = dispatch + Object.defineProperty(context.result, DISPATCH, { + value: dispatch, + enumerable: false, + configurable: false + }) + } + +export const resolveExternal = resolveDispatch + +export const resolveAll = (map: ResolveAllSettings) => { + const middleware = [] + + middleware.push(resolveDispatch(map.dispatch)) + + if (map.result) { + middleware.push(resolveResult(map.result)) + } + + if (map.query) { + middleware.push(resolveQuery(map.query)) + } + + if (map.data) { + middleware.push(resolveData(map.data)) + } + + return compose(middleware) +} diff --git a/packages/schema/src/hooks/validate.ts b/packages/schema/src/hooks/validate.ts new file mode 100644 index 0000000000..8c1b37a8da --- /dev/null +++ b/packages/schema/src/hooks/validate.ts @@ -0,0 +1,53 @@ +import { HookContext, NextFunction } from '@feathersjs/feathers' +import { BadRequest } from '@feathersjs/errors' +import { Schema, Validator } from '../schema' +import { DataValidatorMap } from '../json-schema' + +export const validateQuery = (schema: Schema | Validator) => { + const validator: Validator = typeof schema === 'function' ? schema : schema.validate.bind(schema) + + return async (context: H, next?: NextFunction) => { + const data = context?.params?.query || {} + + try { + const query = await validator(data) + + context.params = { + ...context.params, + query + } + + if (typeof next === 'function') { + return next() + } + } catch (error: any) { + throw error.ajv ? new BadRequest(error.message, error.errors) : error + } + } +} + +export const validateData = (schema: Schema | DataValidatorMap) => { + return async (context: H, next?: NextFunction) => { + const data = context.data + const validator = + typeof (schema as Schema).validate === 'function' + ? (schema as Schema).validate.bind(schema) + : (schema as any)[context.method] + + if (validator) { + try { + if (Array.isArray(data)) { + context.data = await Promise.all(data.map((current) => validator(current))) + } else { + context.data = await validator(data) + } + } catch (error: any) { + throw error.ajv ? new BadRequest(error.message, error.errors) : error + } + } + + if (typeof next === 'function') { + return next() + } + } +} diff --git a/packages/schema/src/index.ts b/packages/schema/src/index.ts index 98135393c8..6e5e2ba8fa 100644 --- a/packages/schema/src/index.ts +++ b/packages/schema/src/index.ts @@ -1,14 +1,24 @@ -import { ResolverStatus } from './resolver'; +import addFormats, { FormatName, FormatOptions, FormatsPluginOptions } from 'ajv-formats' +import { ResolverStatus } from './resolver' -export * from './schema'; -export * from './resolver'; -export * from './hooks'; -export * from './query'; +export type { FromSchema } from 'json-schema-to-ts' +export { addFormats, FormatName, FormatOptions, FormatsPluginOptions } -export type Infer = S['_type']; +export * from './schema' +export * from './resolver' +export * from './hooks' +export * from './json-schema' +export * from './default-schemas' + +export * as hooks from './hooks' +export * as jsonSchema from './json-schema' + +export type Infer = S['_type'] + +export type Combine = Pick, Exclude, keyof U>> & U declare module '@feathersjs/feathers/lib/declarations' { interface Params { - resolve?: ResolverStatus; + resolve?: ResolverStatus } } diff --git a/packages/schema/src/json-schema.ts b/packages/schema/src/json-schema.ts new file mode 100644 index 0000000000..08798fcbd2 --- /dev/null +++ b/packages/schema/src/json-schema.ts @@ -0,0 +1,179 @@ +import { _ } from '@feathersjs/commons' +import { JSONSchema } from 'json-schema-to-ts' +import { JSONSchemaDefinition, Ajv, Validator } from './schema' + +export type DataSchemaMap = { + create: JSONSchemaDefinition + update?: JSONSchemaDefinition + patch?: JSONSchemaDefinition +} + +export type DataValidatorMap = { + create: Validator + update: Validator + patch: Validator +} + +/** + * Returns a compiled validation function for a schema and AJV validator instance. + * + * @param schema The JSON schema definition + * @param validator The AJV validation instance + * @returns A compiled validation function + */ +export const getValidator = (schema: JSONSchemaDefinition, validator: Ajv): Validator => + validator.compile({ + $async: true, + ...(schema as any) + }) as any as Validator + +/** + * Returns compiled validation functions to validate data for the `create`, `update` and `patch` + * service methods. If not passed explicitly, the `update` validator will be the same as the `create` + * and `patch` will be the `create` validator with no required fields. + * + * @param def Either general JSON schema definition or a mapping of `create`, `update` and `patch` + * to their respecitve JSON schema + * @param validator The Ajv instance to use as the validator + * @returns A map of validator functions + */ +export const getDataValidator = ( + def: JSONSchemaDefinition | DataSchemaMap, + validator: Ajv +): DataValidatorMap => { + const schema = ((def as any).create ? def : { create: def }) as DataSchemaMap + + return { + create: getValidator(schema.create, validator), + update: getValidator( + schema.update || { + ...(schema.create as any), + $id: `${schema.create.$id}Update` + }, + validator + ), + patch: getValidator( + schema.patch || { + ...(schema.create as any), + $id: `${schema.create.$id}Patch`, + required: [] + }, + validator + ) + } +} + +export type PropertyQuery = { + anyOf: [ + D, + { + type: 'object' + additionalProperties: false + properties: { + $gt: D + $gte: D + $lt: D + $lte: D + $ne: D + $in: { + type: 'array' + items: D + } + $nin: { + type: 'array' + items: D + } + } + } + ] +} + +/** + * Create a Feathers query syntax compatible JSON schema definition for a property definition. + * + * @param def The property definition (e.g. `{ type: 'string' }`) + * @returns A JSON schema definition for the Feathers query syntax for this property. + */ +export const queryProperty = (def: T) => { + const definition = _.omit(def, 'default') + return { + anyOf: [ + definition, + { + type: 'object', + additionalProperties: false, + properties: { + $gt: definition, + $gte: definition, + $lt: definition, + $lte: definition, + $ne: definition, + $in: { + type: 'array', + items: definition + }, + $nin: { + type: 'array', + items: definition + } + } + } + ] + } as const +} + +/** + * Creates Feathers a query syntax compatible JSON schema for multiple properties. + * + * @param definitions A map of property definitions + * @returns The JSON schema definition for the Feathers query syntax for multiple properties + */ +export const queryProperties = (definitions: T) => + Object.keys(definitions).reduce((res, key) => { + const result = res as any + const definition = definitions[key] + + result[key] = queryProperty(definition) + + return result + }, {} as { [K in keyof T]: PropertyQuery }) + +/** + * Creates a JSON schema for the complete Feathers query syntax including `$limit`, $skip` + * and `$sort` and `$select` for the allowed properties. + * + * @param definition The property definitions to create the query syntax schema for + * @returns A JSON schema for the complete query syntax + */ +export const querySyntax = (definition: T) => + ({ + $limit: { + type: 'number', + minimum: 0 + }, + $skip: { + type: 'number', + minimum: 0 + }, + $sort: { + type: 'object', + properties: Object.keys(definition).reduce((res, key) => { + const result = res as any + + result[key] = { + type: 'number', + enum: [1, -1] + } + + return result + }, {} as { [K in keyof T]: { readonly type: 'number'; readonly enum: [1, -1] } }) + }, + $select: { + type: 'array', + items: { + type: 'string', + enum: Object.keys(definition) as any as (keyof T)[] + } + }, + ...queryProperties(definition) + } as const) diff --git a/packages/schema/src/query.ts b/packages/schema/src/query.ts deleted file mode 100644 index 712a4ed8a0..0000000000 --- a/packages/schema/src/query.ts +++ /dev/null @@ -1,26 +0,0 @@ -import { JSONSchema } from 'json-schema-to-ts'; - -export const queryProperty = (definition: T) => ({ - oneOf: [ - definition, - { - type: 'object', - additionalProperties: false, - properties: { - $gt: definition, - $gte: definition, - $lt: definition, - $lte: definition, - $ne: definition, - $in: { - type: 'array', - items: definition - }, - $nin: { - type: 'array', - items: definition - } - } - } - ] -} as const); diff --git a/packages/schema/src/resolver.ts b/packages/schema/src/resolver.ts index e891ef7a2a..26ad0af727 100644 --- a/packages/schema/src/resolver.ts +++ b/packages/schema/src/resolver.ts @@ -1,49 +1,74 @@ -import { BadRequest } from '@feathersjs/errors'; -import { Schema } from './schema'; +import { BadRequest } from '@feathersjs/errors' +import { Schema } from './schema' export type PropertyResolver = ( - value: V|undefined, + value: V | undefined, obj: T, context: C, status: ResolverStatus -) => Promise; +) => Promise export type PropertyResolverMap = { [key in keyof T]?: PropertyResolver } +export type ResolverConverter = ( + obj: any, + context: C, + status: ResolverStatus +) => Promise + export interface ResolverConfig { - schema?: Schema, - validate?: 'before'|'after'|false, + schema?: Schema + /** + * @deprecated Use the `validateData` and `validateQuery` hooks explicitly instead + */ + validate?: 'before' | 'after' | false + /** + * The properties to resolve + */ properties: PropertyResolverMap + /** + * A converter function that is run before property resolvers + * to transform the initial data into a different format. + */ + converter?: ResolverConverter } export interface ResolverStatus { - path: string[]; - originalContext?: C; - properties?: (keyof T)[]; - stack: PropertyResolver[]; + path: string[] + originalContext?: C + properties?: string[] + stack: PropertyResolver[] } export class Resolver { - readonly _type!: T; - - constructor (public options: ResolverConfig) { - } - - async resolveProperty ( + readonly _type!: T + + constructor(public options: ResolverConfig) {} + + /** + * Resolve a single property + * + * @param name The name of the property + * @param data The current data + * @param context The current resolver context + * @param status The current resolver status + * @returns The resolver property + */ + async resolveProperty( name: K, data: D, context: C, status: Partial> = {} ): Promise { - const resolver = this.options.properties[name]; - const value = (data as any)[name]; - const { path = [], stack = [] } = status || {}; + const resolver = this.options.properties[name] + const value = (data as any)[name] + const { path = [], stack = [] } = status || {} // This prevents circular dependencies if (stack.includes(resolver)) { - return undefined; + return undefined } const resolverStatus = { @@ -52,57 +77,76 @@ export class Resolver { stack: [...stack, resolver] } - return resolver(value, data as any, context, resolverStatus); + return resolver(value, data as any, context, resolverStatus) } - async resolve (_data: D, context: C, status?: Partial>): Promise { - const { properties: resolvers, schema, validate } = this.options; - const data = schema && validate === 'before' ? await schema.validate(_data) : _data; - const propertyList = (Array.isArray(status?.properties) - ? status?.properties - // By default get all data and resolver keys but remove duplicates - : [...new Set(Object.keys(data).concat(Object.keys(resolvers)))] - ) as (keyof T)[]; + async convert(data: D, context: C, status?: Partial>) { + if (this.options.converter) { + const { path = [], stack = [] } = status || {} - const result: any = {}; - const errors: any = {}; - let hasErrors = false; + return this.options.converter(data, context, { ...status, path, stack }) + } - // Not the most elegant but better performance - await Promise.all(propertyList.map(async name => { - const value = data[name]; + return data + } - if (resolvers[name]) { - try { - const resolved = await this.resolveProperty(name, data, context, status); + async resolve(_data: D, context: C, status?: Partial>): Promise { + const { properties: resolvers, schema, validate } = this.options + const payload = await this.convert(_data, context, status) + const data = schema && validate === 'before' ? await schema.validate(payload) : payload + const propertyList = ( + Array.isArray(status?.properties) + ? status?.properties + : // By default get all data and resolver keys but remove duplicates + [...new Set(Object.keys(data).concat(Object.keys(resolvers)))] + ) as (keyof T)[] + + const result: any = {} + const errors: any = {} + let hasErrors = false - if (resolved !== undefined) { - result[name] = resolved; + // Not the most elegant but better performance + await Promise.all( + propertyList.map(async (name) => { + const value = (data as any)[name] + + if (resolvers[name]) { + try { + const resolved = await this.resolveProperty(name, data, context, status) + + if (resolved !== undefined) { + result[name] = resolved + } + } catch (error: any) { + // TODO add error stacks + const convertedError = + typeof error.toJSON === 'function' ? error.toJSON() : { message: error.message || error } + + errors[name] = convertedError + hasErrors = true } - } catch (error: any) { - // TODO add error stacks - const convertedError = typeof error.toJSON === 'function' - ? error.toJSON() - : { message: error.message || error }; - - errors[name] = convertedError; - hasErrors = true; + } else if (value !== undefined) { + result[name] = value } - } else if (value !== undefined) { - result[name] = value; - } - })); + }) + ) if (hasErrors) { - throw new BadRequest(`Error resolving data ${status?.properties.join('.')}`, errors); + const propertyName = status?.properties ? ` ${status.properties.join('.')}` : '' + + throw new BadRequest('Error resolving data' + (propertyName ? ` ${propertyName}` : ''), errors) } - return schema && validate === 'after' - ? await schema.validate(result) - : result; + return schema && validate === 'after' ? await schema.validate(result) : result } } -export function resolve (options: ResolverConfig) { - return new Resolver(options); +/** + * Create a new resolver with ``. + * + * @param options The configuration for the returned resolver + * @returns A new resolver instance + */ +export function resolve(options: ResolverConfig) { + return new Resolver(options) } diff --git a/packages/schema/src/schema.ts b/packages/schema/src/schema.ts index 329aa73e49..293d086d52 100644 --- a/packages/schema/src/schema.ts +++ b/packages/schema/src/schema.ts @@ -1,41 +1,67 @@ -import Ajv, { AsyncValidateFunction, ValidateFunction } from 'ajv'; -import { FromSchema, JSONSchema } from 'json-schema-to-ts'; -import { BadRequest } from '@feathersjs/errors'; +import Ajv, { AsyncValidateFunction, ValidateFunction } from 'ajv' +import { FromSchema, JSONSchema } from 'json-schema-to-ts' +import { BadRequest } from '@feathersjs/errors' -export const AJV = new Ajv({ - coerceTypes: true -}); +export const DEFAULT_AJV = new Ajv({ + coerceTypes: true, + addUsedSchema: false +}) -export type JSONSchemaDefinition = JSONSchema & { $id: string, $async?: boolean }; +export { Ajv } -export class Schema { - ajv: Ajv; - validator: AsyncValidateFunction; - readonly _type!: FromSchema; +/** + * A validation function that takes data and returns the (possibly coerced) + * data or throws a validation error. + */ +export type Validator = (data: T) => Promise - constructor (public definition: S, ajv: Ajv = AJV) { - this.ajv = ajv; +export type JSONSchemaDefinition = JSONSchema & { + $id: string + $async?: true + properties?: { [key: string]: JSONSchema } + required?: readonly string[] +} + +export interface Schema { + validate(...args: Parameters>): Promise +} + +export class SchemaWrapper implements Schema> { + ajv: Ajv + validator: AsyncValidateFunction + readonly _type!: FromSchema + + constructor(public definition: S, ajv: Ajv = DEFAULT_AJV) { + this.ajv = ajv this.validator = this.ajv.compile({ $async: true, ...(this.definition as any) - }) as AsyncValidateFunction; + }) as AsyncValidateFunction + } + + get properties() { + return this.definition.properties as S['properties'] + } + + get required() { + return this.definition.required as S['required'] } - async validate > (...args: Parameters>) { + async validate>(...args: Parameters>) { try { - const validated = await this.validator(...args) as T; + const validated = (await this.validator(...args)) as T - return validated; + return validated } catch (error: any) { - throw new BadRequest(error.message, error.errors); + throw new BadRequest(error.message, error.errors) } } - toJSON () { - return this.definition; + toJSON() { + return this.definition } } -export function schema (definition: S, ajv: Ajv = AJV) { - return new Schema(definition, ajv); +export function schema(definition: S, ajv: Ajv = DEFAULT_AJV) { + return new SchemaWrapper(definition, ajv) } diff --git a/packages/schema/test/fixture.ts b/packages/schema/test/fixture.ts index 2e0b340224..e2b429cd3f 100644 --- a/packages/schema/test/fixture.ts +++ b/packages/schema/test/fixture.ts @@ -1,14 +1,30 @@ -import { - feathers, HookContext, Application as FeathersApplication -} from '@feathersjs/feathers'; -import { memory, Service } from '@feathersjs/memory'; +import { feathers, HookContext, Application as FeathersApplication } from '@feathersjs/feathers' +import { memory, MemoryService } from '@feathersjs/memory' +import { GeneralError } from '@feathersjs/errors' import { - schema, resolve, Infer, resolveResult, - queryProperty, resolveQuery, resolveData -} from '../src'; - -export const userSchema = schema({ + resolve, + resolveResult, + resolveQuery, + resolveData, + validateData, + validateQuery, + querySyntax, + resolveDispatch, + resolveAll, + Ajv, + FromSchema, + getValidator, + getDataValidator +} from '../src' +import { AdapterParams } from '../../memory/node_modules/@feathersjs/adapter-commons/lib' + +const fixtureAjv = new Ajv({ + coerceTypes: true, + addUsedSchema: false +}) + +export const userDataSchema = { $id: 'UserData', type: 'object', additionalProperties: false, @@ -17,42 +33,54 @@ export const userSchema = schema({ email: { type: 'string' }, password: { type: 'string' } } -} as const); +} as const + +export const userDataValidator = getDataValidator(userDataSchema, fixtureAjv) + +export type UserData = FromSchema -export const userResultSchema = schema({ - $id: 'UserResult', +export const userDataResolver = resolve>({ + properties: { + password: async () => { + return 'hashed' + } + } +}) + +export const userSchema = { + $id: 'User', type: 'object', additionalProperties: false, - required: ['id', ...userSchema.definition.required], + required: ['id', ...userDataSchema.required], properties: { - ...userSchema.definition.properties, - id: { type: 'number' } + ...userDataSchema.properties, + id: { type: 'number' }, + name: { type: 'string' } } -} as const); +} as const -export type User = Infer; -export type UserResult = Infer; +export type User = FromSchema -export const userDataResolver = resolve>({ - schema: userSchema, - validate: 'before', +export const userResolver = resolve>({ properties: { - password: async () => { - return 'hashed'; - } + name: async (_value, user) => user.email.split('@')[0] } -}); +}) -export const userResultResolver = resolve>({ - schema: userResultSchema, +export const userExternalResolver = resolve>({ properties: { - password: async (value, _user, context) => { - return context.params.provider ? undefined : value; - } + password: async () => undefined, + email: async () => '[redacted]' } -}); +}) -export const messageSchema = schema({ +export const secondUserResolver = resolve>({ + properties: { + name: async (value, user) => `${value} (${user.email})` + } +}) + +export const messageDataSchema = { $id: 'MessageData', type: 'object', additionalProperties: false, @@ -61,100 +89,127 @@ export const messageSchema = schema({ text: { type: 'string' }, userId: { type: 'number' } } -} as const); +} as const + +export type MessageData = FromSchema -export const messageResultSchema = schema({ +export const messageSchema = { $id: 'MessageResult', type: 'object', additionalProperties: false, - required: ['id', 'user', ...messageSchema.definition.required], + required: ['id', ...messageDataSchema.required], properties: { - ...messageSchema.definition.properties, + ...messageDataSchema.properties, id: { type: 'number' }, - user: { $ref: 'UserResult' } + user: { $ref: 'User' } } -} as const); +} as const -export type Message = Infer; -export type MessageResult = Infer & { - user: User; -}; +export type Message = FromSchema< + typeof messageSchema, + { + references: [typeof userSchema] + } +> -export const messageResultResolver = resolve>({ - schema: messageResultSchema, +export const messageResolver = resolve>({ properties: { user: async (_value, message, context) => { - const { userId } = message; + const { userId } = message - return context.app.service('users').get(userId, context.params); + if (context.params.error === true) { + throw new GeneralError('This is an error') + } + + const user = await context.app.service('users').get(userId, context.params) + + return user as Message['user'] } } -}); +}) -export const messageQuerySchema = schema({ +export const messageQuerySchema = { $id: 'MessageQuery', type: 'object', additionalProperties: false, + required: [], properties: { - $limit: { - type: 'number', - minimum: 0, - maximum: 100 - }, - $skip: { - type: 'number' - }, + ...querySyntax(messageDataSchema.properties), $resolve: { type: 'array', items: { type: 'string' } - }, - userId: queryProperty({ - type: 'number' - }) + } } -} as const); +} as const + +export type MessageQuery = FromSchema -export type MessageQuery = Infer; +export const messageQueryValidator = getValidator(messageQuerySchema, fixtureAjv) export const messageQueryResolver = resolve>({ - schema: messageQuerySchema, - validate: 'before', properties: { userId: async (value, _query, context) => { if (context.params?.user) { - return context.params.user.id; + return context.params.user.id } - return value; + return value } } -}); +}) + +interface ServiceParams extends AdapterParams { + user?: User + error?: boolean +} type ServiceTypes = { - users: Service, - messages: Service + users: MemoryService + messages: MemoryService + paginatedMessages: MemoryService } -type Application = FeathersApplication; +type Application = FeathersApplication const app = feathers() - .use('users', memory({ + +app.use( + 'users', + memory({ multi: ['create'] - })) - .use('messages', memory()); + }) +) +app.use('messages', memory()) +app.use('paginatedMessages', memory({ paginate: { default: 10 } })) app.service('messages').hooks([ - resolveQuery(messageQueryResolver), - resolveResult(messageResultResolver) -]); - -app.service('users').hooks([ - resolveResult(userResultResolver) -]); + resolveAll({ + result: messageResolver, + query: messageQueryResolver + }), + validateQuery(messageQueryValidator) +]) + +app + .service('paginatedMessages') + .hooks([ + validateQuery(messageQueryValidator), + resolveQuery(messageQueryResolver), + resolveResult(messageResolver) + ]) + +app + .service('users') + .hooks([resolveDispatch(userExternalResolver), resolveResult(userResolver, secondUserResolver)]) app.service('users').hooks({ create: [ - resolveData(userDataResolver) + validateData(userDataValidator), + resolveData({ + create: userDataResolver, + patch: userDataResolver, + update: userDataResolver + }) ] -}); +}) -export { app }; +export { app } diff --git a/packages/schema/test/hooks.test.ts b/packages/schema/test/hooks.test.ts index 0f0aa6a0d7..ec5ccb147a 100644 --- a/packages/schema/test/hooks.test.ts +++ b/packages/schema/test/hooks.test.ts @@ -1,110 +1,231 @@ -import assert from 'assert'; -import { app, MessageResult, UserResult } from './fixture'; +import { createContext } from '@feathersjs/feathers' +import assert from 'assert' +import { app, Message, User } from './fixture' describe('@feathersjs/schema/hooks', () => { - const text = 'Hi there'; + const text = 'Hi there' - let message: MessageResult; - let user: UserResult; + let message: Message + let messageOnPaginatedService: Message + let user: User before(async () => { - user = (await app.service('users').create([{ - email: 'hello@feathersjs.com', - password: 'supersecret' - }]))[0]; + user = ( + await app.service('users').create([ + { + email: 'hello@feathersjs.com', + password: 'supersecret' + } + ]) + )[0] message = await app.service('messages').create({ text, userId: user.id - }); - }); + }) + messageOnPaginatedService = await app.service('paginatedMessages').create({ + text, + userId: user.id + }) + }) + + it('ran resolvers in sequence', async () => { + assert.strictEqual(user.name, 'hello (hello@feathersjs.com)') + }) it('validates data', async () => { - assert.rejects(() => app.service('users').create({ password: 'failing' }), { + assert.rejects(() => app.service('users').create({ password: 'failing' } as any), { name: 'BadRequest' - }); - }); + }) + }) - it('resolves results', async () => { - // eslint-disable-next-line - const { password, ...externalUser } = user; + it('resolves results and handles resolver errors (#2534)', async () => { const payload = { userId: user.id, text } - assert.ok(user); - assert.strictEqual(user.password, 'hashed', 'Resolved data'); + assert.ok(user) + assert.strictEqual(user.password, 'hashed', 'Resolved data') assert.deepStrictEqual(message, { id: 0, user, ...payload - }); + }) const messages = await app.service('messages').find({ provider: 'external' - }); + }) + + assert.deepStrictEqual(messages, [ + { + id: 0, + user, + ...payload + } + ]) + + await assert.rejects( + () => + app.service('messages').find({ + provider: 'external', + error: true + }), + { + name: 'BadRequest', + message: 'Error resolving data', + code: 400, + className: 'bad-request', + data: { + user: { + name: 'GeneralError', + message: 'This is an error', + code: 500, + className: 'general-error' + } + } + } + ) + }) + + it('resolves get result with the object on result', async () => { + const payload = { + userId: user.id, + text + } + + assert.ok(user) + assert.strictEqual(user.password, 'hashed', 'Resolved data') + assert.deepStrictEqual(message, { + id: 0, + user, + ...payload + }) + + const result = await app.service('messages').get(0, { + provider: 'external' + }) - assert.deepStrictEqual(messages, [{ + assert.deepStrictEqual(result, { id: 0, - user: externalUser, + user, ...payload - }]); - }); + }) + }) + + it('resolves find results with paginated result object', async () => { + const payload = { + userId: user.id, + text + } + + assert.ok(user) + assert.strictEqual(user.password, 'hashed', 'Resolved data') + assert.deepStrictEqual(messageOnPaginatedService, { + id: 0, + user, + ...payload + }) + + const messages = await app.service('paginatedMessages').find({ + provider: 'external', + query: { + $limit: 1, + $skip: 0 + } + }) + + assert.deepStrictEqual(messages, { + limit: 1, + skip: 0, + total: 1, + data: [ + { + id: 0, + user, + ...payload + } + ] + }) + }) + + it('resolves safe dispatch data recursively', async () => { + const service = app.service('messages') + const context = await service.get(0, {}, createContext(service as any, 'get')) + + assert.strictEqual(context.result.user.password, 'hashed') + + assert.deepStrictEqual(context.dispatch, { + text: 'Hi there', + userId: 0, + id: 0, + user: { + id: 0, + email: '[redacted]', + name: 'hello (hello@feathersjs.com)' + } + }) + }) it('validates and converts the query', async () => { const otherUser = await app.service('users').create({ email: 'helloagain@feathersjs.com', password: 'supersecret' - }); + }) await app.service('messages').create({ text, userId: otherUser.id - }); + }) const messages = await app.service('messages').find({ + paginate: false, query: { userId: `${user.id}` } - }) as MessageResult[]; + }) - assert.strictEqual(messages.length, 1); + assert.strictEqual(messages.length, 1) const userMessages = await app.service('messages').find({ + paginate: false, user - }) as MessageResult[]; + }) - assert.strictEqual(userMessages.length, 1); - assert.strictEqual(userMessages[0].userId, user.id); + assert.strictEqual(userMessages.length, 1) + assert.strictEqual(userMessages[0].userId, user.id) const msg = await app.service('messages').get(userMessages[0].id, { query: { $resolve: ['user'] } - }); + }) assert.deepStrictEqual(msg, { user - }); - - assert.rejects(() => app.service('messages').find({ - query: { - thing: 'me' + }) + + assert.rejects( + () => + app.service('messages').find({ + query: { + thing: 'me' + } + }), + { + name: 'BadRequest', + message: 'validation failed', + code: 400, + className: 'bad-request', + data: [ + { + instancePath: '', + schemaPath: '#/additionalProperties', + keyword: 'additionalProperties', + params: { additionalProperty: 'thing' }, + message: 'must NOT have additional properties' + } + ] } - }), { - name: 'BadRequest', - message: 'validation failed', - code: 400, - className: 'bad-request', - data: [ - { - instancePath: '', - schemaPath: '#/additionalProperties', - keyword: 'additionalProperties', - params: { additionalProperty: 'thing' }, - message: 'must NOT have additional properties' - } - ] - }); - }); -}); + ) + }) +}) diff --git a/packages/schema/test/resolver.test.ts b/packages/schema/test/resolver.test.ts index 2e5de4ca54..5177ecb039 100644 --- a/packages/schema/test/resolver.test.ts +++ b/packages/schema/test/resolver.test.ts @@ -1,7 +1,7 @@ -import assert from 'assert'; -import { BadRequest } from '@feathersjs/errors'; +import assert from 'assert' +import { BadRequest } from '@feathersjs/errors' -import { schema, resolve, Infer } from '../src'; +import { schema, resolve, Infer } from '../src' describe('@feathersjs/schema/resolver', () => { const userSchema = schema({ @@ -14,55 +14,62 @@ describe('@feathersjs/schema/resolver', () => { lastName: { type: 'string' }, password: { type: 'string' } } - } as const); + } as const) const context = { isContext: true - }; + } type User = Infer & { name: string - }; + } it('simple resolver', async () => { const userResolver = resolve({ properties: { password: async (): Promise => { - return undefined; + return undefined }, name: async (_name, user, ctx, status) => { - assert.deepStrictEqual(ctx, context); - assert.deepStrictEqual(status.path, ['name']); - assert.strictEqual(typeof status.stack[0], 'function'); + assert.deepStrictEqual(ctx, context) + assert.deepStrictEqual(status.path, ['name']) + assert.strictEqual(typeof status.stack[0], 'function') - return `${user.firstName} ${user.lastName}`; + return `${user.firstName} ${user.lastName}` } } - }); + }) - const u = await userResolver.resolve({ - firstName: 'Dave', - lastName: 'L.' - }, context); + const u = await userResolver.resolve( + { + firstName: 'Dave', + lastName: 'L.' + }, + context + ) assert.deepStrictEqual(u, { firstName: 'Dave', lastName: 'L.', name: 'Dave L.' - }); - - const withProps: any = await userResolver.resolve({ - firstName: 'David', - lastName: 'L' - }, context, { - properties: ['name', 'lastName'] - }); + }) + + const withProps: any = await userResolver.resolve( + { + firstName: 'David', + lastName: 'L' + }, + context, + { + properties: ['name', 'lastName'] + } + ) assert.deepStrictEqual(withProps, { name: 'David L', lastName: 'L' - }); - }); + }) + }) it('simple resolver with schema and validation', async () => { const userBeforeResolver = resolve({ @@ -71,63 +78,100 @@ describe('@feathersjs/schema/resolver', () => { properties: { name: async (_name, user) => `${user.firstName} ${user.lastName}` } - }); + }) const userAfterResolver = resolve({ schema: userSchema, validate: 'after', properties: { firstName: async () => undefined } - }); + }) await assert.rejects(() => userBeforeResolver.resolve({}, context), { message: 'validation failed' - }); - await assert.rejects(() => userAfterResolver.resolve({ - firstName: 'Test', - lastName: 'Me' - }, context), { - message: 'validation failed' - }); - }); + }) + await assert.rejects( + () => + userAfterResolver.resolve( + { + firstName: 'Test', + lastName: 'Me' + }, + context + ), + { + message: 'validation failed' + } + ) + }) + + it('simple resolver with converter', async () => { + const userConverterResolver = resolve({ + schema: userSchema, + validate: 'before', + converter: async (data) => ({ + firstName: 'Default', + lastName: 'Name', + ...data + }), + properties: { + name: async (_name, user) => `${user.firstName} ${user.lastName}` + } + }) + + const u = await userConverterResolver.resolve({}, context) + + assert.deepStrictEqual(u, { + firstName: 'Default', + lastName: 'Name', + name: 'Default Name' + }) + }) it('resolving with errors', async () => { const dummyResolver = resolve({ properties: { - name: async value => { + name: async (value) => { if (value === 'Dave') { - throw new Error(`No ${value}s allowed`); + throw new Error(`No ${value}s allowed`) } - return value; + return value }, - age: async value => { + age: async (value) => { if (value < 18) { - throw new BadRequest('Invalid age'); + throw new BadRequest('Invalid age') } - return value; + return value } } - }); - - assert.rejects(() => dummyResolver.resolve({ - name: 'Dave', - age: 16 - }, {}), { - name: 'BadRequest', - message: 'Error resolving data', - code: 400, - className: 'bad-request', - data: { - name: { message: 'No Daves allowed' }, - age: { - name: 'BadRequest', - message: 'Invalid age', - code: 400, - className: 'bad-request' + }) + + assert.rejects( + () => + dummyResolver.resolve( + { + name: 'Dave', + age: 16 + }, + {} + ), + { + name: 'BadRequest', + message: 'Error resolving data', + code: 400, + className: 'bad-request', + data: { + name: { message: 'No Daves allowed' }, + age: { + name: 'BadRequest', + message: 'Invalid age', + code: 400, + className: 'bad-request' + } } } - }); - }); -}); \ No newline at end of file + ) + }) +}) diff --git a/packages/schema/test/schema.test.ts b/packages/schema/test/schema.test.ts index f838159593..413393db5a 100644 --- a/packages/schema/test/schema.test.ts +++ b/packages/schema/test/schema.test.ts @@ -1,8 +1,8 @@ -import assert from 'assert'; +import assert from 'assert' -import { schema, Infer, queryProperty } from '../src'; -import Ajv, { AnySchemaObject } from 'ajv'; -import addFormats from 'ajv-formats'; +import { schema, Infer, queryProperty } from '../src' +import Ajv, { AnySchemaObject } from 'ajv' +import addFormats from 'ajv-formats' const customAjv = new Ajv({ coerceTypes: true @@ -13,24 +13,24 @@ addFormats(customAjv) customAjv.addKeyword({ keyword: 'convert', type: 'string', - compile (schemaVal: boolean, parentSchema: AnySchemaObject) { + compile(schemaVal: boolean, parentSchema: AnySchemaObject) { return ['date-time', 'date'].includes(parentSchema.format) && schemaVal ? function (value: string, obj: any) { - const { parentData, parentDataProperty } = obj; + const { parentData, parentDataProperty } = obj // Update date-time string to Date object - parentData[parentDataProperty] = new Date(value); - return true; + parentData[parentDataProperty] = new Date(value) + return true } - : () => true; + : () => true } -}); +}) describe('@feathersjs/schema/schema', () => { it('type inference and validation', async () => { const messageSchema = schema({ $id: 'message-test', type: 'object', - required: [ 'text', 'read' ], + required: ['text', 'read'], additionalProperties: false, properties: { text: { @@ -43,101 +43,109 @@ describe('@feathersjs/schema/schema', () => { type: 'number' } } - } as const); - type Message = Infer; + } as const) + type Message = Infer const message = await messageSchema.validate({ text: 'hi', read: 0, upvotes: '10' - }); + }) - assert.deepStrictEqual(messageSchema.toJSON(), messageSchema.definition); + assert.deepStrictEqual(messageSchema.toJSON(), messageSchema.definition) assert.deepStrictEqual(message, { text: 'hi', read: false, upvotes: 10 - }); + }) await assert.rejects(() => messageSchema.validate({ text: 'failing' }), { name: 'BadRequest', - data: [{ - instancePath: '', - keyword: 'required', - message: 'must have required property \'read\'', - params: { - missingProperty: 'read' - }, - schemaPath: '#/required' - }] - }); - }); + data: [ + { + instancePath: '', + keyword: 'required', + message: "must have required property 'read'", + params: { + missingProperty: 'read' + }, + schemaPath: '#/required' + } + ] + }) + }) it('uses custom AJV with format validation', async () => { - const formatsSchema = schema({ - $id: 'formats-test', - type: 'object', - required: [], - additionalProperties: false, - properties: { - dobString: { - type: 'string', - format: 'date' - }, - createdAt: { - type: 'string', - format: 'date-time' + const formatsSchema = schema( + { + $id: 'formats-test', + type: 'object', + required: [], + additionalProperties: false, + properties: { + dobString: { + type: 'string', + format: 'date' + }, + createdAt: { + type: 'string', + format: 'date-time' + } } - } - } as const, customAjv); + } as const, + customAjv + ) await formatsSchema.validate({ createdAt: '2021-12-22T23:59:59.999Z' - }); + }) try { await formatsSchema.validate({ createdAt: '2021-12-22T23:59:59.bbb' - }); + }) } catch (error: any) { assert.equal(error.data[0].message, 'must match format "date-time"') } - }); + }) it('custom AJV can convert dates', async () => { - const formatsSchema = schema({ - $id: 'converts-formats-test', - type: 'object', - required: [], - additionalProperties: false, - properties: { - dobString: queryProperty({ - type: 'string', - format: 'date', - convert: true - }), - createdAt: { - type: 'string', - format: 'date-time', - convert: true + const formatsSchema = schema( + { + $id: 'converts-formats-test', + type: 'object', + required: [], + additionalProperties: false, + properties: { + dobString: queryProperty({ + type: 'string', + format: 'date', + convert: true + }), + createdAt: { + type: 'string', + format: 'date-time', + convert: true + } } - } - } as const, customAjv); + } as const, + customAjv + ) const validated = await formatsSchema.validate({ dobString: { $gt: '2025-04-25' }, createdAt: '2021-12-22T23:59:59.999Z' - }); + }) - assert.ok((validated.dobString as any).$gt instanceof Date) - assert.ok(validated.createdAt as any instanceof Date) - }); + assert.ok((validated.dobString as any).$gt instanceof Date) + assert.ok((validated.createdAt as any) instanceof Date) + }) it('schema extension and type inference', async () => { const messageSchema = schema({ $id: 'message-ext', type: 'object', - required: [ 'text', 'read' ], + required: ['text', 'read'], additionalProperties: false, properties: { text: { @@ -147,12 +155,12 @@ describe('@feathersjs/schema/schema', () => { type: 'boolean' } } - } as const); + } as const) const messageResultSchema = schema({ $id: 'message-ext-vote', type: 'object', - required: [ 'upvotes', ...messageSchema.definition.required ], + required: ['upvotes', ...messageSchema.definition.required], additionalProperties: false, properties: { ...messageSchema.definition.properties, @@ -160,53 +168,59 @@ describe('@feathersjs/schema/schema', () => { type: 'number' } } - } as const); + } as const) - type MessageResult = Infer; + type MessageResult = Infer const m = await messageResultSchema.validate({ text: 'Hi', read: 'false', upvotes: '23' - }); + }) assert.deepStrictEqual(m, { text: 'Hi', read: false, upvotes: 23 - }); - }); + }) + }) it('with references', async () => { - const userSchema = schema({ - $id: 'ref-user', - type: 'object', - required: [ 'email' ], - additionalProperties: false, - properties: { - email: { type: 'string' }, - age: { type: 'number' } - } - } as const); - const messageSchema = schema({ - $id: 'ref-message', - type: 'object', - required: [ 'text', 'user' ], - additionalProperties: false, - properties: { - text: { - type: 'string' - }, - user: { - $ref: 'ref-user' + const userSchema = schema( + { + $id: 'ref-user', + type: 'object', + required: ['email'], + additionalProperties: false, + properties: { + email: { type: 'string' }, + age: { type: 'number' } } - } - } as const); + } as const, + customAjv + ) + const messageSchema = schema( + { + $id: 'ref-message', + type: 'object', + required: ['text', 'user'], + additionalProperties: false, + properties: { + text: { + type: 'string' + }, + user: { + $ref: 'ref-user' + } + } + } as const, + customAjv + ) - type User = Infer; + type User = Infer type Message = Infer & { user: User - }; + } const res = await messageSchema.validate({ text: 'Hello', @@ -214,14 +228,14 @@ describe('@feathersjs/schema/schema', () => { email: 'hello@feathersjs.com', age: '42' } - }); + }) - assert.ok(userSchema); + assert.ok(userSchema) assert.deepStrictEqual(res, { text: 'Hello', user: { email: 'hello@feathersjs.com', age: 42 } - }); - }); + }) + }) it('works with oneOf properties (#2508)', async () => { const oneOfSchema = schema({ @@ -232,7 +246,7 @@ describe('@feathersjs/schema/schema', () => { additionalProperties: false, required: ['x'], properties: { - x: { type:'number'} + x: { type: 'number' } } }, { @@ -240,16 +254,89 @@ describe('@feathersjs/schema/schema', () => { additionalProperties: false, required: ['y'], properties: { - y: { type:'number'} + y: { type: 'number' } } } ] - } as const); + } as const) const res = await oneOfSchema.validate({ x: '3' - }); + }) + + assert.deepStrictEqual(res, { x: 3 }) + }) - assert.deepStrictEqual(res, { x: 3 }); - }); -}); + it('can handle compound queryProperty', async () => { + const formatsSchema = schema( + { + $id: 'compoundQueryProperty', + type: 'object', + required: [], + additionalProperties: false, + properties: { + dobString: queryProperty({ + oneOf: [ + { type: 'string', format: 'date', convert: true }, + { type: 'string', format: 'date-time', convert: true }, + { type: 'object' } + ] + }) + } + } as const, + customAjv + ) + + const validated = await formatsSchema.validate({ + dobString: { $gt: '2025-04-25', $lte: new Date('2027-04-25') } + }) + + assert.ok(validated) + }) + + it('can still fail queryProperty validation', async () => { + const formatsSchema = schema( + { + $id: 'compoundQueryPropertyFail', + type: 'object', + required: [], + additionalProperties: false, + properties: { + dobString: queryProperty({ type: 'string' }) + } + } as const, + customAjv + ) + + try { + const validated = await formatsSchema.validate({ + dobString: { $moose: 'test' } + }) + assert(!validated, 'should not have gotten here') + } catch (error: any) { + assert.ok(error.data?.length > 0) + } + }) + + it('removes default from queryProperty schemas like $gt', async () => { + const validator = schema( + { + $id: 'noDefault$gt', + type: 'object', + required: [], + additionalProperties: false, + properties: { + someDate: queryProperty({ default: '0000-00-00', type: 'string' }) + } + } as const, + customAjv + ) + + assert.equal( + validator.definition.properties.someDate.anyOf[1].properties.$gt.type, + 'string', + 'type is found under $gt' + ) + assert(!validator.definition.properties.someDate.anyOf[1].properties.$gt.default, 'no default under $gt') + }) +}) diff --git a/packages/socketio-client/CHANGELOG.md b/packages/socketio-client/CHANGELOG.md index 8098c0947b..4941e18b11 100644 --- a/packages/socketio-client/CHANGELOG.md +++ b/packages/socketio-client/CHANGELOG.md @@ -3,550 +3,381 @@ All notable changes to this project will be documented in this file. See [Conventional Commits](https://conventionalcommits.org) for commit guidelines. -# [5.0.0-pre.16](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.15...v5.0.0-pre.16) (2022-01-12) +# [5.0.0-pre.31](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.30...v5.0.0-pre.31) (2022-10-12) **Note:** Version bump only for package @feathersjs/socketio-client +# [5.0.0-pre.30](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.29...v5.0.0-pre.30) (2022-10-07) +### Features +- **core:** Allow to unregister services at runtime ([#2756](https://github.com/feathersjs/feathers/issues/2756)) ([d16601f](https://github.com/feathersjs/feathers/commit/d16601f2277dca5357866ffdefba2a611f6dc7fa)) +# [5.0.0-pre.29](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.28...v5.0.0-pre.29) (2022-09-16) -# [5.0.0-pre.15](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.14...v5.0.0-pre.15) (2021-11-27) +**Note:** Version bump only for package @feathersjs/socketio-client +# [5.0.0-pre.28](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.27...v5.0.0-pre.28) (2022-08-03) ### Bug Fixes -* **typescript:** Overall typing improvements ([#2478](https://github.com/feathersjs/feathers/issues/2478)) ([b8eb804](https://github.com/feathersjs/feathers/commit/b8eb804158556d9651a8607e3c3fda15e0bfd110)) - +- **cli:** Improve generated application and client ([#2701](https://github.com/feathersjs/feathers/issues/2701)) ([bd55ffb](https://github.com/feathersjs/feathers/commit/bd55ffb812e89bf215f4515e7f137656ea888c3f)) +# [5.0.0-pre.27](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.26...v5.0.0-pre.27) (2022-07-13) +### Bug Fixes +- **socketio-client:** Make Socket.io client event target compatible ([#2686](https://github.com/feathersjs/feathers/issues/2686)) ([716c49a](https://github.com/feathersjs/feathers/commit/716c49a270e4be5e5276192092c292f72ffcfa19)) -# [5.0.0-pre.14](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.13...v5.0.0-pre.14) (2021-10-13) +# [5.0.0-pre.26](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.25...v5.0.0-pre.26) (2022-06-22) **Note:** Version bump only for package @feathersjs/socketio-client +# [5.0.0-pre.25](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.24...v5.0.0-pre.25) (2022-06-22) +**Note:** Version bump only for package @feathersjs/socketio-client +# [5.0.0-pre.24](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.23...v5.0.0-pre.24) (2022-06-21) +### Features -# [5.0.0-pre.13](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.12...v5.0.0-pre.13) (2021-10-13) +- **cli:** Add typed client to a generated app ([#2669](https://github.com/feathersjs/feathers/issues/2669)) ([5b801b5](https://github.com/feathersjs/feathers/commit/5b801b5017ddc3eaa95622b539f51d605916bc86)) -**Note:** Version bump only for package @feathersjs/socketio-client +# [5.0.0-pre.23](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.22...v5.0.0-pre.23) (2022-06-06) +### Features +- **client:** Improve client side custom method support ([#2654](https://github.com/feathersjs/feathers/issues/2654)) ([c138acf](https://github.com/feathersjs/feathers/commit/c138acf50affbe6b66177d084d3c7a3e9220f09f)) +# [5.0.0-pre.22](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.21...v5.0.0-pre.22) (2022-05-24) +**Note:** Version bump only for package @feathersjs/socketio-client -# [5.0.0-pre.12](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.11...v5.0.0-pre.12) (2021-10-12) +# [5.0.0-pre.21](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.20...v5.0.0-pre.21) (2022-05-23) **Note:** Version bump only for package @feathersjs/socketio-client +# [5.0.0-pre.20](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.19...v5.0.0-pre.20) (2022-05-04) +### Bug Fixes +- **dependencies:** Lock monorepo package version numbers ([#2623](https://github.com/feathersjs/feathers/issues/2623)) ([5640c10](https://github.com/feathersjs/feathers/commit/5640c1020cc139994e695d658c08bad3494db507)) +# [5.0.0-pre.19](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.18...v5.0.0-pre.19) (2022-05-01) -# [5.0.0-pre.11](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.10...v5.0.0-pre.11) (2021-10-06) +### Features -**Note:** Version bump only for package @feathersjs/socketio-client +- **typescript:** Improve adapter typings ([#2605](https://github.com/feathersjs/feathers/issues/2605)) ([3b2ca0a](https://github.com/feathersjs/feathers/commit/3b2ca0a6a8e03e8390272c4d7e930b4bffdaacf5)) +# [5.0.0-pre.18](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.17...v5.0.0-pre.18) (2022-04-11) +**Note:** Version bump only for package @feathersjs/socketio-client +# [5.0.0-pre.17](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.16...v5.0.0-pre.17) (2022-02-15) +**Note:** Version bump only for package @feathersjs/socketio-client -# [5.0.0-pre.10](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.9...v5.0.0-pre.10) (2021-09-19) +# [5.0.0-pre.16](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.15...v5.0.0-pre.16) (2022-01-12) **Note:** Version bump only for package @feathersjs/socketio-client +# [5.0.0-pre.15](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.14...v5.0.0-pre.15) (2021-11-27) +### Bug Fixes +- **typescript:** Overall typing improvements ([#2478](https://github.com/feathersjs/feathers/issues/2478)) ([b8eb804](https://github.com/feathersjs/feathers/commit/b8eb804158556d9651a8607e3c3fda15e0bfd110)) - -# [5.0.0-pre.9](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.8...v5.0.0-pre.9) (2021-08-09) +# [5.0.0-pre.14](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.13...v5.0.0-pre.14) (2021-10-13) **Note:** Version bump only for package @feathersjs/socketio-client +# [5.0.0-pre.13](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.12...v5.0.0-pre.13) (2021-10-13) +**Note:** Version bump only for package @feathersjs/socketio-client - - -# [5.0.0-pre.8](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.7...v5.0.0-pre.8) (2021-08-09) +# [5.0.0-pre.12](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.11...v5.0.0-pre.12) (2021-10-12) **Note:** Version bump only for package @feathersjs/socketio-client +# [5.0.0-pre.11](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.10...v5.0.0-pre.11) (2021-10-06) +**Note:** Version bump only for package @feathersjs/socketio-client +# [5.0.0-pre.10](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.9...v5.0.0-pre.10) (2021-09-19) +**Note:** Version bump only for package @feathersjs/socketio-client -# [5.0.0-pre.7](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.6...v5.0.0-pre.7) (2021-08-09) +# [5.0.0-pre.9](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.8...v5.0.0-pre.9) (2021-08-09) **Note:** Version bump only for package @feathersjs/socketio-client +# [5.0.0-pre.8](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.7...v5.0.0-pre.8) (2021-08-09) +**Note:** Version bump only for package @feathersjs/socketio-client +# [5.0.0-pre.7](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.6...v5.0.0-pre.7) (2021-08-09) +**Note:** Version bump only for package @feathersjs/socketio-client # [5.0.0-pre.6](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.5...v5.0.0-pre.6) (2021-08-08) **Note:** Version bump only for package @feathersjs/socketio-client - - - - # [5.0.0-pre.5](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.4...v5.0.0-pre.5) (2021-06-23) - ### Features -* **adapter-commons:** Add support for params.adapter option and move memory adapter to @feathersjs/memory ([#2367](https://github.com/feathersjs/feathers/issues/2367)) ([a43e7da](https://github.com/feathersjs/feathers/commit/a43e7da22b6b981a96d1321736ea9a0cb924fb4f)) - - - - +- **adapter-commons:** Add support for params.adapter option and move memory adapter to @feathersjs/memory ([#2367](https://github.com/feathersjs/feathers/issues/2367)) ([a43e7da](https://github.com/feathersjs/feathers/commit/a43e7da22b6b981a96d1321736ea9a0cb924fb4f)) # [5.0.0-pre.4](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.3...v5.0.0-pre.4) (2021-05-13) **Note:** Version bump only for package @feathersjs/socketio-client - - - - # [5.0.0-pre.3](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.2...v5.0.0-pre.3) (2021-04-21) - ### Bug Fixes -* **typescript:** Improve TypeScript backwards compatibility ([#2310](https://github.com/feathersjs/feathers/issues/2310)) ([f33be73](https://github.com/feathersjs/feathers/commit/f33be73fc46a533efb15df9aab0658e3240d3897)) - - - - +- **typescript:** Improve TypeScript backwards compatibility ([#2310](https://github.com/feathersjs/feathers/issues/2310)) ([f33be73](https://github.com/feathersjs/feathers/commit/f33be73fc46a533efb15df9aab0658e3240d3897)) # [5.0.0-pre.2](https://github.com/feathersjs/feathers/compare/v5.0.0-beta.1...v5.0.0-pre.2) (2021-04-06) **Note:** Version bump only for package @feathersjs/socketio-client - - - - # [5.0.0-beta.1](https://github.com/feathersjs/feathers/compare/v5.0.0-beta.0...v5.0.0-beta.1) (2021-04-03) - ### Bug Fixes -* **dependencies:** Fix transport-commons dependency and update other dependencies ([#2284](https://github.com/feathersjs/feathers/issues/2284)) ([05b03b2](https://github.com/feathersjs/feathers/commit/05b03b27b40604d956047e3021d8053c3a137616)) - - - - +- **dependencies:** Fix transport-commons dependency and update other dependencies ([#2284](https://github.com/feathersjs/feathers/issues/2284)) ([05b03b2](https://github.com/feathersjs/feathers/commit/05b03b27b40604d956047e3021d8053c3a137616)) # [5.0.0-beta.0](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.1...v5.0.0-beta.0) (2021-03-28) - ### Bug Fixes -* Update Grant usage and other dependencies ([#2264](https://github.com/feathersjs/feathers/issues/2264)) ([7b0f8fa](https://github.com/feathersjs/feathers/commit/7b0f8fad252419ed0ad0bf259cdf3104d322ab60)) -* **socketio-client:** Fix client transport-commons reference ([#2164](https://github.com/feathersjs/feathers/issues/2164)) ([3a42c54](https://github.com/feathersjs/feathers/commit/3a42c544058456b19c7e21827226541bfa6ad621)) - +- Update Grant usage and other dependencies ([#2264](https://github.com/feathersjs/feathers/issues/2264)) ([7b0f8fa](https://github.com/feathersjs/feathers/commit/7b0f8fad252419ed0ad0bf259cdf3104d322ab60)) +- **socketio-client:** Fix client transport-commons reference ([#2164](https://github.com/feathersjs/feathers/issues/2164)) ([3a42c54](https://github.com/feathersjs/feathers/commit/3a42c544058456b19c7e21827226541bfa6ad621)) ### Features -* **core:** Public custom service methods ([#2270](https://github.com/feathersjs/feathers/issues/2270)) ([e65abfb](https://github.com/feathersjs/feathers/commit/e65abfb5388df6c19a11c565cf1076a29f32668d)) -* Feathers v5 core refactoring and features ([#2255](https://github.com/feathersjs/feathers/issues/2255)) ([2dafb7c](https://github.com/feathersjs/feathers/commit/2dafb7ce14ba57406aeec13d10ca45b1e709bee9)) -* **transport-commons:** New built-in high performance radix router ([#2177](https://github.com/feathersjs/feathers/issues/2177)) ([6d18065](https://github.com/feathersjs/feathers/commit/6d180651b4eb40289ecea3df3575f207aa6c5d1f)) - - - - +- **core:** Public custom service methods ([#2270](https://github.com/feathersjs/feathers/issues/2270)) ([e65abfb](https://github.com/feathersjs/feathers/commit/e65abfb5388df6c19a11c565cf1076a29f32668d)) +- Feathers v5 core refactoring and features ([#2255](https://github.com/feathersjs/feathers/issues/2255)) ([2dafb7c](https://github.com/feathersjs/feathers/commit/2dafb7ce14ba57406aeec13d10ca45b1e709bee9)) +- **transport-commons:** New built-in high performance radix router ([#2177](https://github.com/feathersjs/feathers/issues/2177)) ([6d18065](https://github.com/feathersjs/feathers/commit/6d180651b4eb40289ecea3df3575f207aa6c5d1f)) # [5.0.0-pre.1](https://github.com/feathersjs/feathers/compare/v4.5.11...v5.0.0-pre.1) (2020-12-17) - - # [5.0.0-pre.0](https://github.com/feathersjs/feathers/compare/v4.5.4...v5.0.0-pre.0) (2020-05-19) **Note:** Version bump only for package @feathersjs/socketio-client - - - - # [5.0.0-pre.0](https://github.com/feathersjs/feathers/compare/v4.5.4...v5.0.0-pre.0) (2020-05-19) - ## [4.5.11](https://github.com/feathersjs/feathers/compare/v4.5.10...v4.5.11) (2020-12-05) - ### Bug Fixes -* **socketio-client:** Throw an error and show a warning if someone tries to use socket.io-client v3 ([#2135](https://github.com/feathersjs/feathers/issues/2135)) ([cc3521c](https://github.com/feathersjs/feathers/commit/cc3521c935a1cbd690e29b7057998e3898f282db)) - - - - +- **socketio-client:** Throw an error and show a warning if someone tries to use socket.io-client v3 ([#2135](https://github.com/feathersjs/feathers/issues/2135)) ([cc3521c](https://github.com/feathersjs/feathers/commit/cc3521c935a1cbd690e29b7057998e3898f282db)) ## [4.5.10](https://github.com/feathersjs/feathers/compare/v4.5.9...v4.5.10) (2020-11-08) **Note:** Version bump only for package @feathersjs/socketio-client - - - - ## [4.5.9](https://github.com/feathersjs/feathers/compare/v4.5.8...v4.5.9) (2020-10-09) - - ## [4.5.9](https://github.com/feathersjs/feathers/compare/v4.5.8...v4.5.9) (2020-10-09) **Note:** Version bump only for package @feathersjs/socketio-client - - ## [4.5.8](https://github.com/feathersjs/feathers/compare/v4.5.7...v4.5.8) (2020-08-12) **Note:** Version bump only for package @feathersjs/socketio-client - - - - ## [4.5.7](https://github.com/feathersjs/feathers/compare/v4.5.6...v4.5.7) (2020-07-24) **Note:** Version bump only for package @feathersjs/socketio-client - - - - ## [4.5.6](https://github.com/feathersjs/feathers/compare/v4.5.5...v4.5.6) (2020-07-12) **Note:** Version bump only for package @feathersjs/socketio-client - - - - ## [4.5.5](https://github.com/feathersjs/feathers/compare/v4.5.4...v4.5.5) (2020-07-11) **Note:** Version bump only for package @feathersjs/socketio-client - - - - ## [4.5.4](https://github.com/feathersjs/feathers/compare/v4.5.3...v4.5.4) (2020-04-29) **Note:** Version bump only for package @feathersjs/socketio-client - - - - ## [4.5.3](https://github.com/feathersjs/feathers/compare/v4.5.2...v4.5.3) (2020-04-17) **Note:** Version bump only for package @feathersjs/socketio-client - - - - ## [4.5.2](https://github.com/feathersjs/feathers/compare/v4.5.1...v4.5.2) (2020-03-04) **Note:** Version bump only for package @feathersjs/socketio-client - - - - ## [4.5.1](https://github.com/feathersjs/feathers/compare/v4.5.0...v4.5.1) (2020-01-24) **Note:** Version bump only for package @feathersjs/socketio-client - - - - # [4.5.0](https://github.com/feathersjs/feathers/compare/v4.4.3...v4.5.0) (2020-01-18) **Note:** Version bump only for package @feathersjs/socketio-client - - - - ## [4.4.3](https://github.com/feathersjs/feathers/compare/v4.4.1...v4.4.3) (2019-12-06) **Note:** Version bump only for package @feathersjs/socketio-client - - - - ## [4.4.1](https://github.com/feathersjs/feathers/compare/v4.4.0...v4.4.1) (2019-11-27) **Note:** Version bump only for package @feathersjs/socketio-client - - - - # [4.4.0](https://github.com/feathersjs/feathers/compare/v4.3.11...v4.4.0) (2019-11-27) **Note:** Version bump only for package @feathersjs/socketio-client - - - - ## [4.3.11](https://github.com/feathersjs/feathers/compare/v4.3.10...v4.3.11) (2019-11-11) **Note:** Version bump only for package @feathersjs/socketio-client - - - - ## [4.3.10](https://github.com/feathersjs/feathers/compare/v4.3.9...v4.3.10) (2019-10-26) **Note:** Version bump only for package @feathersjs/socketio-client - - - - ## [4.3.9](https://github.com/feathersjs/feathers/compare/v4.3.8...v4.3.9) (2019-10-26) **Note:** Version bump only for package @feathersjs/socketio-client - - - - ## [4.3.7](https://github.com/feathersjs/feathers/compare/v4.3.6...v4.3.7) (2019-10-14) **Note:** Version bump only for package @feathersjs/socketio-client - - - - ## [4.3.5](https://github.com/feathersjs/feathers/compare/v4.3.4...v4.3.5) (2019-10-07) - ### Bug Fixes -* Change this reference in client libraries to explicitly passed app ([#1597](https://github.com/feathersjs/feathers/issues/1597)) ([4e4d10a](https://github.com/feathersjs/feathers/commit/4e4d10a)) - - - - +- Change this reference in client libraries to explicitly passed app ([#1597](https://github.com/feathersjs/feathers/issues/1597)) ([4e4d10a](https://github.com/feathersjs/feathers/commit/4e4d10a)) ## [4.3.4](https://github.com/feathersjs/feathers/compare/v4.3.3...v4.3.4) (2019-10-03) **Note:** Version bump only for package @feathersjs/socketio-client - - - - ## [4.3.3](https://github.com/feathersjs/feathers/compare/v4.3.2...v4.3.3) (2019-09-21) **Note:** Version bump only for package @feathersjs/socketio-client - - - - ## [4.3.2](https://github.com/feathersjs/feathers/compare/v4.3.1...v4.3.2) (2019-09-16) **Note:** Version bump only for package @feathersjs/socketio-client - - - - ## [4.3.1](https://github.com/feathersjs/feathers/compare/v4.3.0...v4.3.1) (2019-09-09) **Note:** Version bump only for package @feathersjs/socketio-client - - - - # [4.3.0](https://github.com/feathersjs/feathers/compare/v4.3.0-pre.4...v4.3.0) (2019-08-27) **Note:** Version bump only for package @feathersjs/socketio-client - - - - # [4.3.0-pre.4](https://github.com/feathersjs/feathers/compare/v4.3.0-pre.3...v4.3.0-pre.4) (2019-08-22) **Note:** Version bump only for package @feathersjs/socketio-client - - - - # [4.3.0-pre.3](https://github.com/feathersjs/feathers/compare/v4.3.0-pre.2...v4.3.0-pre.3) (2019-08-19) **Note:** Version bump only for package @feathersjs/socketio-client - - - - # [4.3.0-pre.2](https://github.com/feathersjs/feathers/compare/v4.3.0-pre.1...v4.3.0-pre.2) (2019-08-02) **Note:** Version bump only for package @feathersjs/socketio-client - - - - # [4.3.0-pre.1](https://github.com/feathersjs/feathers/compare/v4.0.0-pre.5...v4.3.0-pre.1) (2019-07-11) **Note:** Version bump only for package @feathersjs/socketio-client - - - - # [4.0.0-pre.5](https://github.com/feathersjs/feathers/compare/v4.0.0-pre.4...v4.0.0-pre.5) (2019-07-10) **Note:** Version bump only for package @feathersjs/socketio-client - - - - # [4.0.0-pre.4](https://github.com/feathersjs/feathers/compare/v4.0.0-pre.3...v4.0.0-pre.4) (2019-07-05) **Note:** Version bump only for package @feathersjs/socketio-client - - - - # [4.0.0-pre.3](https://github.com/feathersjs/feathers/compare/v4.0.0-pre.2...v4.0.0-pre.3) (2019-06-01) - ### Bug Fixes -* Update dependencies and fix tests ([#1373](https://github.com/feathersjs/feathers/issues/1373)) ([d743a7f](https://github.com/feathersjs/feathers/commit/d743a7f)) - - - - +- Update dependencies and fix tests ([#1373](https://github.com/feathersjs/feathers/issues/1373)) ([d743a7f](https://github.com/feathersjs/feathers/commit/d743a7f)) # [4.0.0-pre.2](https://github.com/feathersjs/feathers/compare/v4.0.0-pre.1...v4.0.0-pre.2) (2019-05-15) - ### Bug Fixes -* Use `export =` in TypeScript definitions ([#1285](https://github.com/feathersjs/feathers/issues/1285)) ([12d0f4b](https://github.com/feathersjs/feathers/commit/12d0f4b)) - - - - +- Use `export =` in TypeScript definitions ([#1285](https://github.com/feathersjs/feathers/issues/1285)) ([12d0f4b](https://github.com/feathersjs/feathers/commit/12d0f4b)) # [4.0.0-pre.1](https://github.com/feathersjs/feathers/compare/v4.0.0-pre.0...v4.0.0-pre.1) (2019-05-08) **Note:** Version bump only for package @feathersjs/socketio-client - - - - # [4.0.0-pre.0](https://github.com/feathersjs/feathers/compare/v3.2.0-pre.1...v4.0.0-pre.0) (2019-04-21) - ### Bug Fixes -* Make Mocha a proper devDependency for every repository ([#1053](https://github.com/feathersjs/feathers/issues/1053)) ([9974803](https://github.com/feathersjs/feathers/commit/9974803)) -* Update adapter common tests ([#1135](https://github.com/feathersjs/feathers/issues/1135)) ([8166dda](https://github.com/feathersjs/feathers/commit/8166dda)) -* Update all dependencies to latest ([#1206](https://github.com/feathersjs/feathers/issues/1206)) ([e51e0f6](https://github.com/feathersjs/feathers/commit/e51e0f6)) - +- Make Mocha a proper devDependency for every repository ([#1053](https://github.com/feathersjs/feathers/issues/1053)) ([9974803](https://github.com/feathersjs/feathers/commit/9974803)) +- Update adapter common tests ([#1135](https://github.com/feathersjs/feathers/issues/1135)) ([8166dda](https://github.com/feathersjs/feathers/commit/8166dda)) +- Update all dependencies to latest ([#1206](https://github.com/feathersjs/feathers/issues/1206)) ([e51e0f6](https://github.com/feathersjs/feathers/commit/e51e0f6)) ### Features -* Add TypeScript definitions ([#1275](https://github.com/feathersjs/feathers/issues/1275)) ([9dd6713](https://github.com/feathersjs/feathers/commit/9dd6713)) -* Allow registering a service at the root level ([#1115](https://github.com/feathersjs/feathers/issues/1115)) ([c73d322](https://github.com/feathersjs/feathers/commit/c73d322)) -* Authentication v3 core server implementation ([#1205](https://github.com/feathersjs/feathers/issues/1205)) ([1bd7591](https://github.com/feathersjs/feathers/commit/1bd7591)) - - - - +- Add TypeScript definitions ([#1275](https://github.com/feathersjs/feathers/issues/1275)) ([9dd6713](https://github.com/feathersjs/feathers/commit/9dd6713)) +- Allow registering a service at the root level ([#1115](https://github.com/feathersjs/feathers/issues/1115)) ([c73d322](https://github.com/feathersjs/feathers/commit/c73d322)) +- Authentication v3 core server implementation ([#1205](https://github.com/feathersjs/feathers/issues/1205)) ([1bd7591](https://github.com/feathersjs/feathers/commit/1bd7591)) ## [1.2.1](https://github.com/feathersjs/feathers/compare/@feathersjs/socketio-client@1.2.0...@feathersjs/socketio-client@1.2.1) (2019-01-02) - ### Bug Fixes -* Update adapter common tests ([#1135](https://github.com/feathersjs/feathers/issues/1135)) ([8166dda](https://github.com/feathersjs/feathers/commit/8166dda)) - - - - +- Update adapter common tests ([#1135](https://github.com/feathersjs/feathers/issues/1135)) ([8166dda](https://github.com/feathersjs/feathers/commit/8166dda)) -# [1.2.0](https://github.com/feathersjs/feathers/compare/@feathersjs/socketio-client@1.1.5...@feathersjs/socketio-client@1.2.0) (2018-12-16) +# [1.2.0](https://github.com/feathersjs/feathers/compare/@feathersjs/socketio-client@1.1.5...@feathersjs/socketio-client@1.2.0) (2018-12-16) ### Features -* Allow registering a service at the root level ([#1115](https://github.com/feathersjs/feathers/issues/1115)) ([c73d322](https://github.com/feathersjs/feathers/commit/c73d322)) - - - - +- Allow registering a service at the root level ([#1115](https://github.com/feathersjs/feathers/issues/1115)) ([c73d322](https://github.com/feathersjs/feathers/commit/c73d322)) -## [1.1.5](https://github.com/feathersjs/feathers/compare/@feathersjs/socketio-client@1.1.4...@feathersjs/socketio-client@1.1.5) (2018-10-25) +## [1.1.5](https://github.com/feathersjs/feathers/compare/@feathersjs/socketio-client@1.1.4...@feathersjs/socketio-client@1.1.5) (2018-10-25) ### Bug Fixes -* Make Mocha a proper devDependency for every repository ([#1053](https://github.com/feathersjs/feathers/issues/1053)) ([9974803](https://github.com/feathersjs/feathers/commit/9974803)) - - - - +- Make Mocha a proper devDependency for every repository ([#1053](https://github.com/feathersjs/feathers/issues/1053)) ([9974803](https://github.com/feathersjs/feathers/commit/9974803)) + ## [1.1.4](https://github.com/feathersjs/feathers/compare/@feathersjs/socketio-client@1.1.3...@feathersjs/socketio-client@1.1.4) (2018-09-21) **Note:** Version bump only for package @feathersjs/socketio-client - - - - + ## [1.1.3](https://github.com/feathersjs/feathers/compare/@feathersjs/socketio-client@1.1.2...@feathersjs/socketio-client@1.1.3) (2018-09-17) **Note:** Version bump only for package @feathersjs/socketio-client - - - - + ## [1.1.2](https://github.com/feathersjs/feathers/compare/@feathersjs/socketio-client@1.1.1...@feathersjs/socketio-client@1.1.2) (2018-09-02) **Note:** Version bump only for package @feathersjs/socketio-client + ## 1.1.1 - Migrate to Monorepo ([feathers#462](https://github.com/feathersjs/feathers/issues/462)) ## [v1.1.0](https://github.com/feathersjs/socketio-client/tree/v1.1.0) (2018-02-09) + [Full Changelog](https://github.com/feathersjs/socketio-client/compare/v1.0.3...v1.1.0) **Closed issues:** @@ -559,6 +390,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Update @feathersjs/transport-commons to the latest version 🚀 [\#12](https://github.com/feathersjs/socketio-client/pull/12) ([greenkeeper[bot]](https://github.com/apps/greenkeeper)) ## [v1.0.3](https://github.com/feathersjs/socketio-client/tree/v1.0.3) (2018-02-05) + [Full Changelog](https://github.com/feathersjs/socketio-client/compare/v1.0.2...v1.0.3) **Merged pull requests:** @@ -567,6 +399,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Update mocha to the latest version 🚀 [\#8](https://github.com/feathersjs/socketio-client/pull/8) ([greenkeeper[bot]](https://github.com/apps/greenkeeper)) ## [v1.0.2](https://github.com/feathersjs/socketio-client/tree/v1.0.2) (2018-01-03) + [Full Changelog](https://github.com/feathersjs/socketio-client/compare/v1.0.1...v1.0.2) **Merged pull requests:** @@ -576,6 +409,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Update feathers-memory to the latest version 🚀 [\#5](https://github.com/feathersjs/socketio-client/pull/5) ([greenkeeper[bot]](https://github.com/apps/greenkeeper)) ## [v1.0.1](https://github.com/feathersjs/socketio-client/tree/v1.0.1) (2017-11-16) + [Full Changelog](https://github.com/feathersjs/socketio-client/compare/v1.0.0...v1.0.1) **Merged pull requests:** @@ -583,6 +417,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Add default export for better ES module \(TypeScript\) compatibility [\#4](https://github.com/feathersjs/socketio-client/pull/4) ([daffl](https://github.com/daffl)) ## [v1.0.0](https://github.com/feathersjs/socketio-client/tree/v1.0.0) (2017-11-01) + [Full Changelog](https://github.com/feathersjs/socketio-client/compare/v1.0.0-pre.3...v1.0.0) **Merged pull requests:** @@ -590,6 +425,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Update dependencies for release [\#3](https://github.com/feathersjs/socketio-client/pull/3) ([daffl](https://github.com/daffl)) ## [v1.0.0-pre.3](https://github.com/feathersjs/socketio-client/tree/v1.0.0-pre.3) (2017-10-23) + [Full Changelog](https://github.com/feathersjs/socketio-client/compare/v1.0.0-pre.2...v1.0.0-pre.3) **Merged pull requests:** @@ -597,6 +433,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Use scoped npm packages [\#2](https://github.com/feathersjs/socketio-client/pull/2) ([daffl](https://github.com/daffl)) ## [v1.0.0-pre.2](https://github.com/feathersjs/socketio-client/tree/v1.0.0-pre.2) (2017-10-19) + [Full Changelog](https://github.com/feathersjs/socketio-client/compare/v1.0.0-pre.1...v1.0.0-pre.2) **Merged pull requests:** @@ -605,5 +442,4 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline ## [v1.0.0-pre.1](https://github.com/feathersjs/socketio-client/tree/v1.0.0-pre.1) (2017-10-18) - -\* *This Change Log was automatically generated by [github_changelog_generator](https://github.com/skywinder/Github-Changelog-Generator)* +\* _This Change Log was automatically generated by [github_changelog_generator](https://github.com/skywinder/Github-Changelog-Generator)_ diff --git a/packages/socketio-client/LICENSE b/packages/socketio-client/LICENSE index 3f395cc665..59604f46f3 100644 --- a/packages/socketio-client/LICENSE +++ b/packages/socketio-client/LICENSE @@ -1,6 +1,6 @@ The MIT License (MIT) -Copyright (c) 2021 Feathers +Copyright (c) 2022 Feathers Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated documentation files (the "Software"), to deal diff --git a/packages/socketio-client/README.md b/packages/socketio-client/README.md index 6147e1d9c9..5d3241877d 100644 --- a/packages/socketio-client/README.md +++ b/packages/socketio-client/README.md @@ -1,8 +1,8 @@ # @feathersjs/socketio-client [![CI](https://github.com/feathersjs/feathers/workflows/CI/badge.svg)](https://github.com/feathersjs/feathers/actions?query=workflow%3ACI) -[![Dependency Status](https://img.shields.io/david/feathersjs/feathers.svg?style=flat-square&path=packages/socketio-client)](https://david-dm.org/feathersjs/feathers?path=packages/socketio-client) [![Download Status](https://img.shields.io/npm/dm/@feathersjs/socketio-client.svg?style=flat-square)](https://www.npmjs.com/package/@feathersjs/socketio-client) +[![Discord](https://badgen.net/badge/icon/discord?icon=discord&label)](https://discord.gg/qa8kez8QBx) > The client for Socket.io Feathers connections @@ -18,6 +18,6 @@ Refer to the [Feathers SocketIO API documentation](https://docs.feathersjs.com/a ## License -Copyright (c) 2021 [Feathers contributors](https://github.com/feathersjs/feathers/graphs/contributors) +Copyright (c) 2022 [Feathers contributors](https://github.com/feathersjs/feathers/graphs/contributors) Licensed under the [MIT license](LICENSE). diff --git a/packages/socketio-client/package.json b/packages/socketio-client/package.json index 5b7b57241f..5972688916 100644 --- a/packages/socketio-client/package.json +++ b/packages/socketio-client/package.json @@ -1,9 +1,10 @@ { "name": "@feathersjs/socketio-client", "description": "The client for Socket.io through feathers-socketio", - "version": "5.0.0-pre.16", + "version": "5.0.0-pre.31", "homepage": "https://feathersjs.com", - "main": "lib/index.js", + "main": "lib/", + "types": "lib/", "keywords": [ "feathers", "feathers-plugin" @@ -15,7 +16,8 @@ }, "repository": { "type": "git", - "url": "git://github.com/feathersjs/feathers.git" + "url": "git://github.com/feathersjs/feathers.git", + "directory": "packages/socketio-client" }, "author": { "name": "Feathers contributors", @@ -31,8 +33,10 @@ }, "scripts": { "prepublish": "npm run compile", - "compile": "shx rm -rf lib/ && tsc", - "test": "mocha --config ../../.mocharc.json --recursive test/**.test.ts test/**/*.test.ts" + "pack": "npm pack --pack-destination ../cli/test/build", + "compile": "shx rm -rf lib/ && tsc && npm run pack", + "mocha": "mocha --config ../../.mocharc.json --recursive test/**.test.ts test/**/*.test.ts", + "test": "npm run mocha" }, "directories": { "lib": "lib" @@ -50,21 +54,21 @@ "access": "public" }, "dependencies": { - "@feathersjs/transport-commons": "^5.0.0-pre.16" + "@feathersjs/transport-commons": "^5.0.0-pre.31" }, "devDependencies": { - "@feathersjs/commons": "^5.0.0-pre.16", - "@feathersjs/feathers": "^5.0.0-pre.16", - "@feathersjs/memory": "^5.0.0-pre.16", - "@feathersjs/socketio": "^5.0.0-pre.16", - "@feathersjs/tests": "^5.0.0-pre.16", - "@types/mocha": "^9.0.0", - "@types/node": "^17.0.5", - "mocha": "^9.1.3", - "shx": "^0.3.3", - "socket.io-client": "^4.4.0", - "ts-node": "^10.4.0", - "typescript": "^4.5.4" + "@feathersjs/commons": "^5.0.0-pre.31", + "@feathersjs/feathers": "^5.0.0-pre.31", + "@feathersjs/memory": "^5.0.0-pre.31", + "@feathersjs/socketio": "^5.0.0-pre.31", + "@feathersjs/tests": "^5.0.0-pre.31", + "@types/mocha": "^10.0.0", + "@types/node": "^18.8.2", + "mocha": "^10.0.0", + "shx": "^0.3.4", + "socket.io-client": "^4.5.2", + "ts-node": "^10.9.1", + "typescript": "^4.8.4" }, - "gitHead": "f0cd227a82d159b528193bd33747c97684a48773" + "gitHead": "4500dbeb8cea566678cf88b3313a88efd93a2ed9" } diff --git a/packages/socketio-client/src/index.ts b/packages/socketio-client/src/index.ts index f4d5ed2ba4..af4000a1ec 100644 --- a/packages/socketio-client/src/index.ts +++ b/packages/socketio-client/src/index.ts @@ -1,41 +1,64 @@ -import { Service, SocketService } from '@feathersjs/transport-commons/client'; -import { Socket } from 'socket.io-client'; -import { defaultEventMap } from '@feathersjs/feathers'; +import { Service, SocketService } from '@feathersjs/transport-commons/client' +import { Socket } from 'socket.io-client' +import { + Application, + TransportConnection, + defaultEventMap, + defaultServiceMethods +} from '@feathersjs/feathers' -export { SocketService }; +export { SocketService } -export default function socketioClient (connection: Socket, options?: any) { +declare module '@feathersjs/feathers/lib/declarations' { + // eslint-disable-next-line @typescript-eslint/no-unused-vars + interface FeathersApplication { + /** + * The Socket.io client instance. Usually does not need + * to be accessed directly. + */ + io?: Socket + } +} + +export default function socketioClient(connection: Socket, options?: any) { if (!connection) { - throw new Error('Socket.io connection needs to be provided'); + throw new Error('Socket.io connection needs to be provided') } const defaultService = function (this: any, name: string) { - const events = Object.values(defaultEventMap); + const events = Object.values(defaultEventMap) const settings = Object.assign({}, options, { events, name, connection, method: 'emit' - }); + }) - return new Service(settings); - }; + return new Service(settings) as any + } - const initialize = function (app: any) { + const initialize = function (app: Application) { if (app.io !== undefined) { - throw new Error('Only one default client provider can be configured'); + throw new Error('Only one default client provider can be configured') } - app.io = connection; - app.defaultService = defaultService; - }; + app.io = connection as any + app.defaultService = defaultService + app.mixins.unshift((service, _location, options) => { + if (options && options.methods && service instanceof Service) { + const customMethods = options.methods.filter((name) => !defaultServiceMethods.includes(name)) + + service.methods(...customMethods) + } + }) + } - initialize.Service = Service; - initialize.service = defaultService; + initialize.Service = Service + initialize.service = defaultService - return initialize; + return initialize as TransportConnection } if (typeof module !== 'undefined') { - module.exports = Object.assign(socketioClient, module.exports); + module.exports = Object.assign(socketioClient, module.exports) } diff --git a/packages/socketio-client/test/index.test.ts b/packages/socketio-client/test/index.test.ts index 9bd3350c17..a39f8f84e6 100644 --- a/packages/socketio-client/test/index.test.ts +++ b/packages/socketio-client/test/index.test.ts @@ -1,100 +1,108 @@ -import { strict as assert } from 'assert'; -import { Server } from 'http'; -import { CustomMethods, feathers } from '@feathersjs/feathers'; -import { io, Socket } from 'socket.io-client'; -import { clientTests } from '@feathersjs/tests'; +/* eslint-disable @typescript-eslint/ban-ts-comment */ +import { strict as assert } from 'assert' +import { Server } from 'http' +import { CustomMethod, feathers } from '@feathersjs/feathers' +import { io, Socket } from 'socket.io-client' +import { clientTests } from '@feathersjs/tests' -import { createServer } from './server'; -import socketio, { SocketService } from '../src'; +import { createServer } from './server' +import socketio, { SocketService } from '../src' type ServiceTypes = { - '/': SocketService, - 'todos': SocketService & CustomMethods<{customMethod: any}>, - [key: string]: any; + '/': SocketService + todos: SocketService & { + customMethod: CustomMethod<{ message: string }> + } + [key: string]: any } describe('@feathersjs/socketio-client', () => { - const app = feathers(); - - let socket: Socket; - let server: Server; - - before(done => { - createServer().listen(9988).then(srv => { - server = srv; - server.once('listening', () => { - socket = io('http://localhost:9988'); - app.configure(socketio(socket)); - done(); - }); - }); - }); - - after(done => { - socket.disconnect(); - server.close(done); - }); + const app = feathers() + + let socket: Socket + let server: Server + + before(async () => { + server = await createServer().listen(9988) + socket = io('http://localhost:9988') + + const connection = socketio(socket) + + app.configure(connection) + app.use('todos', connection.service('todos'), { + methods: ['find', 'get', 'create', 'patch', 'customMethod'] + }) + }) + + after((done) => { + socket.disconnect() + server.close(done) + }) it('throws an error with no connection', () => { try { // @ts-ignore - feathers().configure(socketio()); - assert.ok(false); + feathers().configure(socketio()) + assert.ok(false) } catch (e: any) { - assert.strictEqual(e.message, - 'Socket.io connection needs to be provided' - ); + assert.strictEqual(e.message, 'Socket.io connection needs to be provided') } - }); + }) it('app has the io attribute', () => { - assert.ok((app as any).io); - }); + assert.ok((app as any).io) + }) it('throws an error when configured twice', () => { try { - app.configure(socketio(socket)); - assert.ok(false, 'Should never get here'); + app.configure(socketio(socket)) + assert.ok(false, 'Should never get here') } catch (e: any) { - assert.strictEqual(e.message, 'Only one default client provider can be configured'); + assert.strictEqual(e.message, 'Only one default client provider can be configured') } - }); + }) it('can initialize a client instance', async () => { - const init = socketio(socket); - const totoService = init.service('todos'); + const init = socketio(socket) + const totoService = init.service('todos') - assert.ok(totoService instanceof init.Service, 'Returned service is a client'); + assert.ok(totoService instanceof init.Service, 'Returned service is a client') - const todos = await totoService.find(); + const todos = await totoService.find() - assert.deepEqual(todos, [{ - text: 'some todo', - complete: false, - id: 0 - }]); - }); + assert.deepEqual(todos, [ + { + text: 'some todo', + complete: false, + id: 0 + } + ]) + }) it('return 404 for non-existent service', async () => { try { - await app.service('not/me').create({}); - assert.fail('Should never get here'); + await app.service('not/me').create({}) + assert.fail('Should never get here') } catch (e: any) { - assert.strictEqual(e.message, 'Service \'not/me\' not found') + assert.strictEqual(e.message, "Service 'not/me' not found") } - }); + }) + + it('is event target compatible', async () => { + app.service('todo').addEventListener('created', (data: any) => assert.ok(data)) + }) it('calls .customMethod', async () => { - const service = app.service('todos').methods('customMethod'); - const result = await service.customMethod({ message: 'hi' }); + const service = app.service('todos') + const result = await service.customMethod({ message: 'hi' }) assert.deepStrictEqual(result, { data: { message: 'hi' }, provider: 'socketio', type: 'customMethod' - }); - }); + }) + }) - clientTests(app, 'todos'); - clientTests(app, '/'); -}); + clientTests(app, 'todos') + clientTests(app, '/') +}) diff --git a/packages/socketio-client/test/server.ts b/packages/socketio-client/test/server.ts index e9eac21138..8d579a7998 100644 --- a/packages/socketio-client/test/server.ts +++ b/packages/socketio-client/test/server.ts @@ -1,36 +1,36 @@ -import { feathers, Id, Params } from '@feathersjs/feathers'; -import socketio from '@feathersjs/socketio'; -import '@feathersjs/transport-commons'; -import { Service } from '@feathersjs/memory'; +import { feathers, Id, Params } from '@feathersjs/feathers' +import socketio from '@feathersjs/socketio' +import '@feathersjs/transport-commons' +import { MemoryService } from '@feathersjs/memory' // eslint-disable-next-line no-extend-native Object.defineProperty(Error.prototype, 'toJSON', { - value () { - const alt: any = {}; + value() { + const alt: any = {} Object.getOwnPropertyNames(this).forEach((key: string) => { - alt[key] = this[key]; - }, this); + alt[key] = this[key] + }, this) - return alt; + return alt }, configurable: true, writable: true -}); +}) // Create an in-memory CRUD service for our Todos -class TodoService extends Service { - async get (id: Id, params: Params) { +class TodoService extends MemoryService { + async get(id: Id, params: Params) { if (params.query.error) { - throw new Error('Something went wrong'); + throw new Error('Something went wrong') } - const data = await super.get(id); + const data = await super.get(id) return Object.assign({ query: params.query }, data) } - async customMethod (data: any, { provider }: Params) { + async customMethod(data: any, { provider }: Params) { return { data, provider, @@ -39,32 +39,28 @@ class TodoService extends Service { } } -export function createServer () { +export function createServer() { const app = feathers() .configure(socketio()) .use('/', new TodoService()) .use('/todos', new TodoService(), { - methods: [ - 'find', 'get', 'create', 'update', 'patch', 'remove', 'customMethod' - ] - }); - const service = app.service('todos'); - const rootService = app.service('/'); - const publisher = () => app.channel('general'); + methods: ['find', 'get', 'create', 'update', 'patch', 'remove', 'customMethod'] + }) + const service = app.service('todos') + const rootService = app.service('/') + const publisher = () => app.channel('general') const data = { text: 'some todo', complete: false - }; + } - app.on('connection', connection => - app.channel('general').join(connection) - ); + app.on('connection', (connection) => app.channel('general').join(connection)) - rootService.create(data); - rootService.publish(publisher); + rootService.create(data) + rootService.publish(publisher) - service.create(data); - service.publish(publisher); + service.create(data) + service.publish(publisher) - return app; + return app } diff --git a/packages/socketio/CHANGELOG.md b/packages/socketio/CHANGELOG.md index d11650a68c..f048ee4bfb 100644 --- a/packages/socketio/CHANGELOG.md +++ b/packages/socketio/CHANGELOG.md @@ -3,593 +3,414 @@ All notable changes to this project will be documented in this file. See [Conventional Commits](https://conventionalcommits.org) for commit guidelines. -# [5.0.0-pre.16](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.15...v5.0.0-pre.16) (2022-01-12) +# [5.0.0-pre.31](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.30...v5.0.0-pre.31) (2022-10-12) **Note:** Version bump only for package @feathersjs/socketio +# [5.0.0-pre.30](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.29...v5.0.0-pre.30) (2022-10-07) +### Bug Fixes +- **core:** Ensure setup and teardown can be overriden and maintain hook functionality ([#2779](https://github.com/feathersjs/feathers/issues/2779)) ([ab580cb](https://github.com/feathersjs/feathers/commit/ab580cbcaa68d19144d86798c13bf564f9d424a6)) +### Features -# [5.0.0-pre.15](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.14...v5.0.0-pre.15) (2021-11-27) +- **core:** Allow to unregister services at runtime ([#2756](https://github.com/feathersjs/feathers/issues/2756)) ([d16601f](https://github.com/feathersjs/feathers/commit/d16601f2277dca5357866ffdefba2a611f6dc7fa)) +# [5.0.0-pre.29](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.28...v5.0.0-pre.29) (2022-09-16) ### Bug Fixes -* **typescript:** Overall typing improvements ([#2478](https://github.com/feathersjs/feathers/issues/2478)) ([b8eb804](https://github.com/feathersjs/feathers/commit/b8eb804158556d9651a8607e3c3fda15e0bfd110)) - +- **socketio:** Reinitialize hooks on overriden setup method ([#2722](https://github.com/feathersjs/feathers/issues/2722)) ([5e8e7c4](https://github.com/feathersjs/feathers/commit/5e8e7c442238fdc929a0a36b8b8ca2b230ce761f)) +# [5.0.0-pre.28](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.27...v5.0.0-pre.28) (2022-08-03) +### Bug Fixes +- **cli:** Improve generated application and client ([#2701](https://github.com/feathersjs/feathers/issues/2701)) ([bd55ffb](https://github.com/feathersjs/feathers/commit/bd55ffb812e89bf215f4515e7f137656ea888c3f)) -# [5.0.0-pre.14](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.13...v5.0.0-pre.14) (2021-10-13) +# [5.0.0-pre.27](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.26...v5.0.0-pre.27) (2022-07-13) **Note:** Version bump only for package @feathersjs/socketio +# [5.0.0-pre.26](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.25...v5.0.0-pre.26) (2022-06-22) +**Note:** Version bump only for package @feathersjs/socketio +# [5.0.0-pre.25](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.24...v5.0.0-pre.25) (2022-06-22) +**Note:** Version bump only for package @feathersjs/socketio -# [5.0.0-pre.13](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.12...v5.0.0-pre.13) (2021-10-13) +# [5.0.0-pre.24](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.23...v5.0.0-pre.24) (2022-06-21) **Note:** Version bump only for package @feathersjs/socketio +# [5.0.0-pre.23](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.22...v5.0.0-pre.23) (2022-06-06) +**Note:** Version bump only for package @feathersjs/socketio +# [5.0.0-pre.22](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.21...v5.0.0-pre.22) (2022-05-24) +**Note:** Version bump only for package @feathersjs/socketio -# [5.0.0-pre.12](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.11...v5.0.0-pre.12) (2021-10-12) +# [5.0.0-pre.21](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.20...v5.0.0-pre.21) (2022-05-23) **Note:** Version bump only for package @feathersjs/socketio +# [5.0.0-pre.20](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.19...v5.0.0-pre.20) (2022-05-04) +### Bug Fixes +- **dependencies:** Lock monorepo package version numbers ([#2623](https://github.com/feathersjs/feathers/issues/2623)) ([5640c10](https://github.com/feathersjs/feathers/commit/5640c1020cc139994e695d658c08bad3494db507)) +# [5.0.0-pre.19](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.18...v5.0.0-pre.19) (2022-05-01) -# [5.0.0-pre.11](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.10...v5.0.0-pre.11) (2021-10-06) +### Features -**Note:** Version bump only for package @feathersjs/socketio +- **typescript:** Improve params and query typeability ([#2600](https://github.com/feathersjs/feathers/issues/2600)) ([df28b76](https://github.com/feathersjs/feathers/commit/df28b7619161f1df5e700326f52cca1a92dc5d28)) +# [5.0.0-pre.18](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.17...v5.0.0-pre.18) (2022-04-11) +**Note:** Version bump only for package @feathersjs/socketio +# [5.0.0-pre.17](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.16...v5.0.0-pre.17) (2022-02-15) +**Note:** Version bump only for package @feathersjs/socketio -# [5.0.0-pre.10](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.9...v5.0.0-pre.10) (2021-09-19) +# [5.0.0-pre.16](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.15...v5.0.0-pre.16) (2022-01-12) **Note:** Version bump only for package @feathersjs/socketio +# [5.0.0-pre.15](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.14...v5.0.0-pre.15) (2021-11-27) +### Bug Fixes +- **typescript:** Overall typing improvements ([#2478](https://github.com/feathersjs/feathers/issues/2478)) ([b8eb804](https://github.com/feathersjs/feathers/commit/b8eb804158556d9651a8607e3c3fda15e0bfd110)) - -# [5.0.0-pre.9](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.8...v5.0.0-pre.9) (2021-08-09) +# [5.0.0-pre.14](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.13...v5.0.0-pre.14) (2021-10-13) **Note:** Version bump only for package @feathersjs/socketio +# [5.0.0-pre.13](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.12...v5.0.0-pre.13) (2021-10-13) +**Note:** Version bump only for package @feathersjs/socketio - - -# [5.0.0-pre.8](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.7...v5.0.0-pre.8) (2021-08-09) +# [5.0.0-pre.12](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.11...v5.0.0-pre.12) (2021-10-12) **Note:** Version bump only for package @feathersjs/socketio +# [5.0.0-pre.11](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.10...v5.0.0-pre.11) (2021-10-06) +**Note:** Version bump only for package @feathersjs/socketio +# [5.0.0-pre.10](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.9...v5.0.0-pre.10) (2021-09-19) +**Note:** Version bump only for package @feathersjs/socketio -# [5.0.0-pre.7](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.6...v5.0.0-pre.7) (2021-08-09) +# [5.0.0-pre.9](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.8...v5.0.0-pre.9) (2021-08-09) **Note:** Version bump only for package @feathersjs/socketio +# [5.0.0-pre.8](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.7...v5.0.0-pre.8) (2021-08-09) +**Note:** Version bump only for package @feathersjs/socketio +# [5.0.0-pre.7](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.6...v5.0.0-pre.7) (2021-08-09) +**Note:** Version bump only for package @feathersjs/socketio # [5.0.0-pre.6](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.5...v5.0.0-pre.6) (2021-08-08) **Note:** Version bump only for package @feathersjs/socketio - - - - # [5.0.0-pre.5](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.4...v5.0.0-pre.5) (2021-06-23) - ### Features -* **adapter-commons:** Add support for params.adapter option and move memory adapter to @feathersjs/memory ([#2367](https://github.com/feathersjs/feathers/issues/2367)) ([a43e7da](https://github.com/feathersjs/feathers/commit/a43e7da22b6b981a96d1321736ea9a0cb924fb4f)) - - - - +- **adapter-commons:** Add support for params.adapter option and move memory adapter to @feathersjs/memory ([#2367](https://github.com/feathersjs/feathers/issues/2367)) ([a43e7da](https://github.com/feathersjs/feathers/commit/a43e7da22b6b981a96d1321736ea9a0cb924fb4f)) # [5.0.0-pre.4](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.3...v5.0.0-pre.4) (2021-05-13) **Note:** Version bump only for package @feathersjs/socketio - - - - # [5.0.0-pre.3](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.2...v5.0.0-pre.3) (2021-04-21) - ### Bug Fixes -* **typescript:** Improve TypeScript backwards compatibility ([#2310](https://github.com/feathersjs/feathers/issues/2310)) ([f33be73](https://github.com/feathersjs/feathers/commit/f33be73fc46a533efb15df9aab0658e3240d3897)) - +- **typescript:** Improve TypeScript backwards compatibility ([#2310](https://github.com/feathersjs/feathers/issues/2310)) ([f33be73](https://github.com/feathersjs/feathers/commit/f33be73fc46a533efb15df9aab0658e3240d3897)) ### Features -* **dependencies:** Remove direct debug dependency ([#2296](https://github.com/feathersjs/feathers/issues/2296)) ([501d416](https://github.com/feathersjs/feathers/commit/501d4164d30c6a126906dc640cdfdc82207ba34a)) - - - - +- **dependencies:** Remove direct debug dependency ([#2296](https://github.com/feathersjs/feathers/issues/2296)) ([501d416](https://github.com/feathersjs/feathers/commit/501d4164d30c6a126906dc640cdfdc82207ba34a)) # [5.0.0-pre.2](https://github.com/feathersjs/feathers/compare/v5.0.0-beta.1...v5.0.0-pre.2) (2021-04-06) **Note:** Version bump only for package @feathersjs/socketio - - - - # [5.0.0-beta.1](https://github.com/feathersjs/feathers/compare/v5.0.0-beta.0...v5.0.0-beta.1) (2021-04-03) - ### Bug Fixes -* **dependencies:** Fix transport-commons dependency and update other dependencies ([#2284](https://github.com/feathersjs/feathers/issues/2284)) ([05b03b2](https://github.com/feathersjs/feathers/commit/05b03b27b40604d956047e3021d8053c3a137616)) - - - - +- **dependencies:** Fix transport-commons dependency and update other dependencies ([#2284](https://github.com/feathersjs/feathers/issues/2284)) ([05b03b2](https://github.com/feathersjs/feathers/commit/05b03b27b40604d956047e3021d8053c3a137616)) # [5.0.0-beta.0](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.1...v5.0.0-beta.0) (2021-03-28) - ### Bug Fixes -* Update Grant usage and other dependencies ([#2264](https://github.com/feathersjs/feathers/issues/2264)) ([7b0f8fa](https://github.com/feathersjs/feathers/commit/7b0f8fad252419ed0ad0bf259cdf3104d322ab60)) - +- Update Grant usage and other dependencies ([#2264](https://github.com/feathersjs/feathers/issues/2264)) ([7b0f8fa](https://github.com/feathersjs/feathers/commit/7b0f8fad252419ed0ad0bf259cdf3104d322ab60)) ### Features -* **core:** Public custom service methods ([#2270](https://github.com/feathersjs/feathers/issues/2270)) ([e65abfb](https://github.com/feathersjs/feathers/commit/e65abfb5388df6c19a11c565cf1076a29f32668d)) -* Application service types default to any ([#1566](https://github.com/feathersjs/feathers/issues/1566)) ([d93ba9a](https://github.com/feathersjs/feathers/commit/d93ba9a17edd20d3397bb00f4f6e82e804e42ed6)) -* Feathers v5 core refactoring and features ([#2255](https://github.com/feathersjs/feathers/issues/2255)) ([2dafb7c](https://github.com/feathersjs/feathers/commit/2dafb7ce14ba57406aeec13d10ca45b1e709bee9)) -* **core:** Remove Uberproto ([#2178](https://github.com/feathersjs/feathers/issues/2178)) ([ddf8821](https://github.com/feathersjs/feathers/commit/ddf8821f53317e6a378657f7d66acb03a037ee47)) - +- **core:** Public custom service methods ([#2270](https://github.com/feathersjs/feathers/issues/2270)) ([e65abfb](https://github.com/feathersjs/feathers/commit/e65abfb5388df6c19a11c565cf1076a29f32668d)) +- Application service types default to any ([#1566](https://github.com/feathersjs/feathers/issues/1566)) ([d93ba9a](https://github.com/feathersjs/feathers/commit/d93ba9a17edd20d3397bb00f4f6e82e804e42ed6)) +- Feathers v5 core refactoring and features ([#2255](https://github.com/feathersjs/feathers/issues/2255)) ([2dafb7c](https://github.com/feathersjs/feathers/commit/2dafb7ce14ba57406aeec13d10ca45b1e709bee9)) +- **core:** Remove Uberproto ([#2178](https://github.com/feathersjs/feathers/issues/2178)) ([ddf8821](https://github.com/feathersjs/feathers/commit/ddf8821f53317e6a378657f7d66acb03a037ee47)) ### BREAKING CHANGES -* **core:** Services no longer extend Uberproto objects and -`service.mixin()` is no longer available. - - - - +- **core:** Services no longer extend Uberproto objects and + `service.mixin()` is no longer available. # [5.0.0-pre.1](https://github.com/feathersjs/feathers/compare/v4.5.11...v5.0.0-pre.1) (2020-12-17) - - # [5.0.0-pre.0](https://github.com/feathersjs/feathers/compare/v4.5.4...v5.0.0-pre.0) (2020-05-19) - ### Features -* **transport-commons:** Remove legacy message format and unnecessary client timeouts ([#1939](https://github.com/feathersjs/feathers/issues/1939)) ([5538881](https://github.com/feathersjs/feathers/commit/5538881a08bc130de42c5984055729d8336f8615)) - +- **transport-commons:** Remove legacy message format and unnecessary client timeouts ([#1939](https://github.com/feathersjs/feathers/issues/1939)) ([5538881](https://github.com/feathersjs/feathers/commit/5538881a08bc130de42c5984055729d8336f8615)) ### BREAKING CHANGES -* **transport-commons:** Removes the old message format and client service timeout - - - - +- **transport-commons:** Removes the old message format and client service timeout # [5.0.0-pre.0](https://github.com/feathersjs/feathers/compare/v4.5.4...v5.0.0-pre.0) (2020-05-19) - ### Features -* **transport-commons:** Remove legacy message format and unnecessary client timeouts ([#1939](https://github.com/feathersjs/feathers/issues/1939)) ([5538881](https://github.com/feathersjs/feathers/commit/5538881a08bc130de42c5984055729d8336f8615)) - +- **transport-commons:** Remove legacy message format and unnecessary client timeouts ([#1939](https://github.com/feathersjs/feathers/issues/1939)) ([5538881](https://github.com/feathersjs/feathers/commit/5538881a08bc130de42c5984055729d8336f8615)) ### BREAKING CHANGES -* **transport-commons:** Removes the old message format and client service timeout - - +- **transport-commons:** Removes the old message format and client service timeout ## [4.5.11](https://github.com/feathersjs/feathers/compare/v4.5.10...v4.5.11) (2020-12-05) **Note:** Version bump only for package @feathersjs/socketio - - - - ## [4.5.10](https://github.com/feathersjs/feathers/compare/v4.5.9...v4.5.10) (2020-11-08) **Note:** Version bump only for package @feathersjs/socketio - - - - ## [4.5.9](https://github.com/feathersjs/feathers/compare/v4.5.8...v4.5.9) (2020-10-09) **Note:** Version bump only for package @feathersjs/socketio - - - - ## [4.5.8](https://github.com/feathersjs/feathers/compare/v4.5.7...v4.5.8) (2020-08-12) **Note:** Version bump only for package @feathersjs/socketio - - - - ## [4.5.7](https://github.com/feathersjs/feathers/compare/v4.5.6...v4.5.7) (2020-07-24) **Note:** Version bump only for package @feathersjs/socketio - - - - ## [4.5.6](https://github.com/feathersjs/feathers/compare/v4.5.5...v4.5.6) (2020-07-12) **Note:** Version bump only for package @feathersjs/socketio - - - - ## [4.5.5](https://github.com/feathersjs/feathers/compare/v4.5.4...v4.5.5) (2020-07-11) **Note:** Version bump only for package @feathersjs/socketio - - - - ## [4.5.4](https://github.com/feathersjs/feathers/compare/v4.5.3...v4.5.4) (2020-04-29) **Note:** Version bump only for package @feathersjs/socketio - - - - ## [4.5.3](https://github.com/feathersjs/feathers/compare/v4.5.2...v4.5.3) (2020-04-17) **Note:** Version bump only for package @feathersjs/socketio - - - - ## [4.5.2](https://github.com/feathersjs/feathers/compare/v4.5.1...v4.5.2) (2020-03-04) **Note:** Version bump only for package @feathersjs/socketio - - - - ## [4.5.1](https://github.com/feathersjs/feathers/compare/v4.5.0...v4.5.1) (2020-01-24) **Note:** Version bump only for package @feathersjs/socketio - - - - # [4.5.0](https://github.com/feathersjs/feathers/compare/v4.4.3...v4.5.0) (2020-01-18) **Note:** Version bump only for package @feathersjs/socketio - - - - ## [4.4.3](https://github.com/feathersjs/feathers/compare/v4.4.1...v4.4.3) (2019-12-06) **Note:** Version bump only for package @feathersjs/socketio - - - - ## [4.4.1](https://github.com/feathersjs/feathers/compare/v4.4.0...v4.4.1) (2019-11-27) **Note:** Version bump only for package @feathersjs/socketio - - - - # [4.4.0](https://github.com/feathersjs/feathers/compare/v4.3.11...v4.4.0) (2019-11-27) - ### Features -* **authentication:** Add parseStrategies to allow separate strategies for creating JWTs and parsing headers ([#1708](https://github.com/feathersjs/feathers/issues/1708)) ([5e65629](https://github.com/feathersjs/feathers/commit/5e65629b924724c3e81d7c81df047e123d1c8bd7)) - - - - +- **authentication:** Add parseStrategies to allow separate strategies for creating JWTs and parsing headers ([#1708](https://github.com/feathersjs/feathers/issues/1708)) ([5e65629](https://github.com/feathersjs/feathers/commit/5e65629b924724c3e81d7c81df047e123d1c8bd7)) ## [4.3.11](https://github.com/feathersjs/feathers/compare/v4.3.10...v4.3.11) (2019-11-11) **Note:** Version bump only for package @feathersjs/socketio - - - - ## [4.3.10](https://github.com/feathersjs/feathers/compare/v4.3.9...v4.3.10) (2019-10-26) **Note:** Version bump only for package @feathersjs/socketio - - - - ## [4.3.9](https://github.com/feathersjs/feathers/compare/v4.3.8...v4.3.9) (2019-10-26) **Note:** Version bump only for package @feathersjs/socketio - - - - ## [4.3.7](https://github.com/feathersjs/feathers/compare/v4.3.6...v4.3.7) (2019-10-14) **Note:** Version bump only for package @feathersjs/socketio - - - - ## [4.3.5](https://github.com/feathersjs/feathers/compare/v4.3.4...v4.3.5) (2019-10-07) **Note:** Version bump only for package @feathersjs/socketio - - - - ## [4.3.4](https://github.com/feathersjs/feathers/compare/v4.3.3...v4.3.4) (2019-10-03) - ### Bug Fixes -* Typing improvements ([#1580](https://github.com/feathersjs/feathers/issues/1580)) ([7818aec](https://github.com/feathersjs/feathers/commit/7818aec)) - - - - +- Typing improvements ([#1580](https://github.com/feathersjs/feathers/issues/1580)) ([7818aec](https://github.com/feathersjs/feathers/commit/7818aec)) ## [4.3.3](https://github.com/feathersjs/feathers/compare/v4.3.2...v4.3.3) (2019-09-21) **Note:** Version bump only for package @feathersjs/socketio - - - - ## [4.3.2](https://github.com/feathersjs/feathers/compare/v4.3.1...v4.3.2) (2019-09-16) **Note:** Version bump only for package @feathersjs/socketio - - - - ## [4.3.1](https://github.com/feathersjs/feathers/compare/v4.3.0...v4.3.1) (2019-09-09) **Note:** Version bump only for package @feathersjs/socketio - - - - # [4.3.0](https://github.com/feathersjs/feathers/compare/v4.3.0-pre.4...v4.3.0) (2019-08-27) **Note:** Version bump only for package @feathersjs/socketio - - - - # [4.3.0-pre.4](https://github.com/feathersjs/feathers/compare/v4.3.0-pre.3...v4.3.0-pre.4) (2019-08-22) **Note:** Version bump only for package @feathersjs/socketio - - - - # [4.3.0-pre.3](https://github.com/feathersjs/feathers/compare/v4.3.0-pre.2...v4.3.0-pre.3) (2019-08-19) - ### Bug Fixes -* Expire and remove authenticated real-time connections ([#1512](https://github.com/feathersjs/feathers/issues/1512)) ([2707c33](https://github.com/feathersjs/feathers/commit/2707c33)) -* Use WeakMap to connect socket to connection ([#1509](https://github.com/feathersjs/feathers/issues/1509)) ([64807e3](https://github.com/feathersjs/feathers/commit/64807e3)) - - - - +- Expire and remove authenticated real-time connections ([#1512](https://github.com/feathersjs/feathers/issues/1512)) ([2707c33](https://github.com/feathersjs/feathers/commit/2707c33)) +- Use WeakMap to connect socket to connection ([#1509](https://github.com/feathersjs/feathers/issues/1509)) ([64807e3](https://github.com/feathersjs/feathers/commit/64807e3)) # [4.3.0-pre.2](https://github.com/feathersjs/feathers/compare/v4.3.0-pre.1...v4.3.0-pre.2) (2019-08-02) **Note:** Version bump only for package @feathersjs/socketio - - - - # [4.3.0-pre.1](https://github.com/feathersjs/feathers/compare/v4.0.0-pre.5...v4.3.0-pre.1) (2019-07-11) **Note:** Version bump only for package @feathersjs/socketio - - - - # [4.0.0-pre.5](https://github.com/feathersjs/feathers/compare/v4.0.0-pre.4...v4.0.0-pre.5) (2019-07-10) **Note:** Version bump only for package @feathersjs/socketio - - - - # [4.0.0-pre.4](https://github.com/feathersjs/feathers/compare/v4.0.0-pre.3...v4.0.0-pre.4) (2019-07-05) **Note:** Version bump only for package @feathersjs/socketio - - - - # [4.0.0-pre.3](https://github.com/feathersjs/feathers/compare/v4.0.0-pre.2...v4.0.0-pre.3) (2019-06-01) - ### Bug Fixes -* Update dependencies and fix tests ([#1373](https://github.com/feathersjs/feathers/issues/1373)) ([d743a7f](https://github.com/feathersjs/feathers/commit/d743a7f)) - - - - +- Update dependencies and fix tests ([#1373](https://github.com/feathersjs/feathers/issues/1373)) ([d743a7f](https://github.com/feathersjs/feathers/commit/d743a7f)) # [4.0.0-pre.2](https://github.com/feathersjs/feathers/compare/v4.0.0-pre.1...v4.0.0-pre.2) (2019-05-15) - ### Bug Fixes -* Use `export =` in TypeScript definitions ([#1285](https://github.com/feathersjs/feathers/issues/1285)) ([12d0f4b](https://github.com/feathersjs/feathers/commit/12d0f4b)) - +- Use `export =` in TypeScript definitions ([#1285](https://github.com/feathersjs/feathers/issues/1285)) ([12d0f4b](https://github.com/feathersjs/feathers/commit/12d0f4b)) ### Features -* Add global disconnect event ([#1355](https://github.com/feathersjs/feathers/issues/1355)) ([85afcca](https://github.com/feathersjs/feathers/commit/85afcca)) - - - - +- Add global disconnect event ([#1355](https://github.com/feathersjs/feathers/issues/1355)) ([85afcca](https://github.com/feathersjs/feathers/commit/85afcca)) # [4.0.0-pre.1](https://github.com/feathersjs/feathers/compare/v4.0.0-pre.0...v4.0.0-pre.1) (2019-05-08) - ### Features -* Add params.headers to all transports when available ([#1303](https://github.com/feathersjs/feathers/issues/1303)) ([ebce79b](https://github.com/feathersjs/feathers/commit/ebce79b)) - - - - +- Add params.headers to all transports when available ([#1303](https://github.com/feathersjs/feathers/issues/1303)) ([ebce79b](https://github.com/feathersjs/feathers/commit/ebce79b)) # [4.0.0-pre.0](https://github.com/feathersjs/feathers/compare/v3.2.0-pre.1...v4.0.0-pre.0) (2019-04-21) - ### Bug Fixes -* Make Mocha a proper devDependency for every repository ([#1053](https://github.com/feathersjs/feathers/issues/1053)) ([9974803](https://github.com/feathersjs/feathers/commit/9974803)) -* Update all dependencies to latest ([#1206](https://github.com/feathersjs/feathers/issues/1206)) ([e51e0f6](https://github.com/feathersjs/feathers/commit/e51e0f6)) -* **package:** update debug to version 3.0.0 ([#83](https://github.com/feathersjs/feathers/issues/83)) ([49f1de9](https://github.com/feathersjs/feathers/commit/49f1de9)) -* **package:** update socket.io to version 2.0.0 ([#75](https://github.com/feathersjs/feathers/issues/75)) ([d4a4b71](https://github.com/feathersjs/feathers/commit/d4a4b71)) - +- Make Mocha a proper devDependency for every repository ([#1053](https://github.com/feathersjs/feathers/issues/1053)) ([9974803](https://github.com/feathersjs/feathers/commit/9974803)) +- Update all dependencies to latest ([#1206](https://github.com/feathersjs/feathers/issues/1206)) ([e51e0f6](https://github.com/feathersjs/feathers/commit/e51e0f6)) +- **package:** update debug to version 3.0.0 ([#83](https://github.com/feathersjs/feathers/issues/83)) ([49f1de9](https://github.com/feathersjs/feathers/commit/49f1de9)) +- **package:** update socket.io to version 2.0.0 ([#75](https://github.com/feathersjs/feathers/issues/75)) ([d4a4b71](https://github.com/feathersjs/feathers/commit/d4a4b71)) ### chore -* drop support for Node.js 0.10 ([#48](https://github.com/feathersjs/feathers/issues/48)) ([3f7555a](https://github.com/feathersjs/feathers/commit/3f7555a)) - +- drop support for Node.js 0.10 ([#48](https://github.com/feathersjs/feathers/issues/48)) ([3f7555a](https://github.com/feathersjs/feathers/commit/3f7555a)) ### Features -* Add TypeScript definitions ([#1275](https://github.com/feathersjs/feathers/issues/1275)) ([9dd6713](https://github.com/feathersjs/feathers/commit/9dd6713)) - +- Add TypeScript definitions ([#1275](https://github.com/feathersjs/feathers/issues/1275)) ([9dd6713](https://github.com/feathersjs/feathers/commit/9dd6713)) ### BREAKING CHANGES -* This module no longer supports Node.js 0.10 - - - - +- This module no longer supports Node.js 0.10 ## [3.2.9](https://github.com/feathersjs/feathers/compare/@feathersjs/socketio@3.2.8...@feathersjs/socketio@3.2.9) (2019-01-02) **Note:** Version bump only for package @feathersjs/socketio - - - - + ## [3.2.8](https://github.com/feathersjs/feathers/compare/@feathersjs/socketio@3.2.7...@feathersjs/socketio@3.2.8) (2018-12-16) **Note:** Version bump only for package @feathersjs/socketio - - - - -## [3.2.7](https://github.com/feathersjs/feathers/compare/@feathersjs/socketio@3.2.6...@feathersjs/socketio@3.2.7) (2018-10-25) +## [3.2.7](https://github.com/feathersjs/feathers/compare/@feathersjs/socketio@3.2.6...@feathersjs/socketio@3.2.7) (2018-10-25) ### Bug Fixes -* Make Mocha a proper devDependency for every repository ([#1053](https://github.com/feathersjs/feathers/issues/1053)) ([9974803](https://github.com/feathersjs/feathers/commit/9974803)) - - - - +- Make Mocha a proper devDependency for every repository ([#1053](https://github.com/feathersjs/feathers/issues/1053)) ([9974803](https://github.com/feathersjs/feathers/commit/9974803)) + ## [3.2.6](https://github.com/feathersjs/feathers/compare/@feathersjs/socketio@3.2.5...@feathersjs/socketio@3.2.6) (2018-09-21) **Note:** Version bump only for package @feathersjs/socketio - - - - + ## [3.2.5](https://github.com/feathersjs/feathers/compare/@feathersjs/socketio@3.2.4...@feathersjs/socketio@3.2.5) (2018-09-17) **Note:** Version bump only for package @feathersjs/socketio - - - - + ## [3.2.4](https://github.com/feathersjs/feathers/compare/@feathersjs/socketio@3.2.3...@feathersjs/socketio@3.2.4) (2018-09-02) **Note:** Version bump only for package @feathersjs/socketio + ## 3.2.3 - Migrate to Monorepo ([feathers#462](https://github.com/feathersjs/feathers/issues/462)) ## [v3.2.2](https://github.com/feathersjs/socketio/tree/v3.2.2) (2018-06-03) + [Full Changelog](https://github.com/feathersjs/socketio/compare/v3.2.1...v3.2.2) **Merged pull requests:** @@ -597,6 +418,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Update uberproto to the latest version 🚀 [\#117](https://github.com/feathersjs/socketio/pull/117) ([greenkeeper[bot]](https://github.com/apps/greenkeeper)) ## [v3.2.1](https://github.com/feathersjs/socketio/tree/v3.2.1) (2018-04-04) + [Full Changelog](https://github.com/feathersjs/socketio/compare/v3.2.0...v3.2.1) **Closed issues:** @@ -609,6 +431,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Use latest version of Socket.io \(2.1.0\) [\#115](https://github.com/feathersjs/socketio/pull/115) ([daffl](https://github.com/daffl)) ## [v3.2.0](https://github.com/feathersjs/socketio/tree/v3.2.0) (2018-02-09) + [Full Changelog](https://github.com/feathersjs/socketio/compare/v3.1.0...v3.2.0) **Closed issues:** @@ -620,11 +443,12 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Update @feathersjs/transport-commons to the latest version 🚀 [\#111](https://github.com/feathersjs/socketio/pull/111) ([greenkeeper[bot]](https://github.com/apps/greenkeeper)) ## [v3.1.0](https://github.com/feathersjs/socketio/tree/v3.1.0) (2018-01-30) + [Full Changelog](https://github.com/feathersjs/socketio/compare/v3.0.2...v3.1.0) **Closed issues:** -- How to change 5000ms timeout? [\#107](https://github.com/feathersjs/socketio/issues/107) +- How to change 5000ms timeout? [\#107](https://github.com/feathersjs/socketio/issues/107) **Merged pull requests:** @@ -632,12 +456,13 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Update mocha to the latest version 🚀 [\#108](https://github.com/feathersjs/socketio/pull/108) ([greenkeeper[bot]](https://github.com/apps/greenkeeper)) ## [v3.0.2](https://github.com/feathersjs/socketio/tree/v3.0.2) (2018-01-03) + [Full Changelog](https://github.com/feathersjs/socketio/compare/v3.0.1...v3.0.2) **Closed issues:** - Updated from feathers-socketio to @feathersjs/socketio; error message [\#104](https://github.com/feathersjs/socketio/issues/104) -- How to stop listening to socket server from client service [\#103](https://github.com/feathersjs/socketio/issues/103) +- How to stop listening to socket server from client service [\#103](https://github.com/feathersjs/socketio/issues/103) - Options are not passed to socket-io [\#101](https://github.com/feathersjs/socketio/issues/101) - feathers / graphql using REST / Sockets [\#97](https://github.com/feathersjs/socketio/issues/97) @@ -648,6 +473,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Update feathers-memory to the latest version 🚀 [\#102](https://github.com/feathersjs/socketio/pull/102) ([greenkeeper[bot]](https://github.com/apps/greenkeeper)) ## [v3.0.1](https://github.com/feathersjs/socketio/tree/v3.0.1) (2017-11-16) + [Full Changelog](https://github.com/feathersjs/socketio/compare/v3.0.0...v3.0.1) **Closed issues:** @@ -660,6 +486,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Updating client use example to fix imports [\#99](https://github.com/feathersjs/socketio/pull/99) ([corymsmith](https://github.com/corymsmith)) ## [v3.0.0](https://github.com/feathersjs/socketio/tree/v3.0.0) (2017-11-01) + [Full Changelog](https://github.com/feathersjs/socketio/compare/v2.0.1...v3.0.0) **Merged pull requests:** @@ -668,6 +495,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Throw an error when using an incompatible version of Feathers [\#94](https://github.com/feathersjs/socketio/pull/94) ([daffl](https://github.com/daffl)) ## [v2.0.1](https://github.com/feathersjs/socketio/tree/v2.0.1) (2017-10-31) + [Full Changelog](https://github.com/feathersjs/socketio/compare/v3.0.0-pre.4...v2.0.1) **Merged pull requests:** @@ -675,9 +503,11 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Add an error when trying to use earlier versions with Feathers v3 [\#93](https://github.com/feathersjs/socketio/pull/93) ([daffl](https://github.com/daffl)) ## [v3.0.0-pre.4](https://github.com/feathersjs/socketio/tree/v3.0.0-pre.4) (2017-10-25) + [Full Changelog](https://github.com/feathersjs/socketio/compare/v3.0.0-pre.3...v3.0.0-pre.4) ## [v3.0.0-pre.3](https://github.com/feathersjs/socketio/tree/v3.0.0-pre.3) (2017-10-22) + [Full Changelog](https://github.com/feathersjs/socketio/compare/v3.0.0-pre.2...v3.0.0-pre.3) **Merged pull requests:** @@ -686,6 +516,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Updates for Feathers v3 \(Buzzard\) [\#91](https://github.com/feathersjs/socketio/pull/91) ([daffl](https://github.com/daffl)) ## [v3.0.0-pre.2](https://github.com/feathersjs/socketio/tree/v3.0.0-pre.2) (2017-10-18) + [Full Changelog](https://github.com/feathersjs/socketio/compare/v3.0.0-pre.1...v3.0.0-pre.2) **Merged pull requests:** @@ -693,6 +524,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Some finishing touches for v3 [\#90](https://github.com/feathersjs/socketio/pull/90) ([daffl](https://github.com/daffl)) ## [v3.0.0-pre.1](https://github.com/feathersjs/socketio/tree/v3.0.0-pre.1) (2017-10-17) + [Full Changelog](https://github.com/feathersjs/socketio/compare/v2.0.0...v3.0.0-pre.1) **Closed issues:** @@ -700,7 +532,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Filter service updates by ID [\#87](https://github.com/feathersjs/socketio/issues/87) - An in-range update of mocha is breaking the build 🚨 [\#86](https://github.com/feathersjs/socketio/issues/86) - An in-range update of babel-cli is breaking the build 🚨 [\#85](https://github.com/feathersjs/socketio/issues/85) -- Connection closed before receiving a handshake response [\#84](https://github.com/feathersjs/socketio/issues/84) +- Connection closed before receiving a handshake response [\#84](https://github.com/feathersjs/socketio/issues/84) - Maybe acting wrong please look into my test app [\#81](https://github.com/feathersjs/socketio/issues/81) - Connecting to sockets on a path [\#80](https://github.com/feathersjs/socketio/issues/80) - An in-range update of babel-core is breaking the build 🚨 [\#79](https://github.com/feathersjs/socketio/issues/79) @@ -716,6 +548,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Update to latest plugin infrastructure [\#82](https://github.com/feathersjs/socketio/pull/82) ([daffl](https://github.com/daffl)) ## [v2.0.0](https://github.com/feathersjs/socketio/tree/v2.0.0) (2017-05-10) + [Full Changelog](https://github.com/feathersjs/socketio/compare/v1.6.0...v2.0.0) **Closed issues:** @@ -731,6 +564,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Update semistandard to the latest version 🚀 [\#72](https://github.com/feathersjs/socketio/pull/72) ([greenkeeper[bot]](https://github.com/apps/greenkeeper)) ## [v1.6.0](https://github.com/feathersjs/socketio/tree/v1.6.0) (2017-04-18) + [Full Changelog](https://github.com/feathersjs/socketio/compare/v1.5.2...v1.6.0) **Closed issues:** @@ -744,6 +578,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Update dependencies to enable Greenkeeper 🌴 [\#68](https://github.com/feathersjs/socketio/pull/68) ([greenkeeper[bot]](https://github.com/apps/greenkeeper)) ## [v1.5.2](https://github.com/feathersjs/socketio/tree/v1.5.2) (2017-03-03) + [Full Changelog](https://github.com/feathersjs/socketio/compare/v1.5.1...v1.5.2) **Merged pull requests:** @@ -751,6 +586,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Server-side socketio typedef to allow `import \* as` syntax when importing [\#65](https://github.com/feathersjs/socketio/pull/65) ([myknbani](https://github.com/myknbani)) ## [v1.5.1](https://github.com/feathersjs/socketio/tree/v1.5.1) (2017-03-02) + [Full Changelog](https://github.com/feathersjs/socketio/compare/v1.5.0...v1.5.1) **Closed issues:** @@ -763,6 +599,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - feathers-hooks@1.8.0 breaks build 🚨 [\#62](https://github.com/feathersjs/socketio/pull/62) ([greenkeeperio-bot](https://github.com/greenkeeperio-bot)) ## [v1.5.0](https://github.com/feathersjs/socketio/tree/v1.5.0) (2017-03-01) + [Full Changelog](https://github.com/feathersjs/socketio/compare/v1.4.3...v1.5.0) **Merged pull requests:** @@ -770,6 +607,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Typescript Definitions [\#60](https://github.com/feathersjs/socketio/pull/60) ([AbraaoAlves](https://github.com/AbraaoAlves)) ## [v1.4.3](https://github.com/feathersjs/socketio/tree/v1.4.3) (2017-02-24) + [Full Changelog](https://github.com/feathersjs/socketio/compare/v1.4.2...v1.4.3) **Closed issues:** @@ -786,6 +624,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Update feathers-commons to version 0.8.0 🚀 [\#49](https://github.com/feathersjs/socketio/pull/49) ([greenkeeperio-bot](https://github.com/greenkeeperio-bot)) ## [v1.4.2](https://github.com/feathersjs/socketio/tree/v1.4.2) (2016-11-02) + [Full Changelog](https://github.com/feathersjs/socketio/compare/v1.4.1...v1.4.2) **Closed issues:** @@ -810,6 +649,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Update mocha to version 3.0.0 🚀 [\#33](https://github.com/feathersjs/socketio/pull/33) ([greenkeeperio-bot](https://github.com/greenkeeperio-bot)) ## [v1.4.1](https://github.com/feathersjs/socketio/tree/v1.4.1) (2016-05-23) + [Full Changelog](https://github.com/feathersjs/socketio/compare/v1.4.0...v1.4.1) **Closed issues:** @@ -825,6 +665,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - fix link in README.md to feathers-socketio API docs [\#24](https://github.com/feathersjs/socketio/pull/24) ([ElliotPsyIT](https://github.com/ElliotPsyIT)) ## [v1.4.0](https://github.com/feathersjs/socketio/tree/v1.4.0) (2016-04-28) + [Full Changelog](https://github.com/feathersjs/socketio/compare/v1.3.4...v1.4.0) **Merged pull requests:** @@ -835,6 +676,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - More tests for error cases [\#16](https://github.com/feathersjs/socketio/pull/16) ([daffl](https://github.com/daffl)) ## [v1.3.4](https://github.com/feathersjs/socketio/tree/v1.3.4) (2016-04-16) + [Full Changelog](https://github.com/feathersjs/socketio/compare/v1.3.3...v1.3.4) **Merged pull requests:** @@ -843,6 +685,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Update feathers-memory to version 0.7.0 🚀 [\#14](https://github.com/feathersjs/socketio/pull/14) ([greenkeeperio-bot](https://github.com/greenkeeperio-bot)) ## [v1.3.3](https://github.com/feathersjs/socketio/tree/v1.3.3) (2016-02-18) + [Full Changelog](https://github.com/feathersjs/socketio/compare/v1.3.2...v1.3.3) **Closed issues:** @@ -854,6 +697,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Allow to pass Socket.io options [\#13](https://github.com/feathersjs/socketio/pull/13) ([daffl](https://github.com/daffl)) ## [v1.3.2](https://github.com/feathersjs/socketio/tree/v1.3.2) (2016-02-11) + [Full Changelog](https://github.com/feathersjs/socketio/compare/v1.3.1...v1.3.2) **Merged pull requests:** @@ -861,9 +705,11 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Allow to instantiate a client instance [\#11](https://github.com/feathersjs/socketio/pull/11) ([daffl](https://github.com/daffl)) ## [v1.3.1](https://github.com/feathersjs/socketio/tree/v1.3.1) (2016-02-09) + [Full Changelog](https://github.com/feathersjs/socketio/compare/v1.3.0...v1.3.1) ## [v1.3.0](https://github.com/feathersjs/socketio/tree/v1.3.0) (2016-02-09) + [Full Changelog](https://github.com/feathersjs/socketio/compare/v1.2.0...v1.3.0) **Merged pull requests:** @@ -873,6 +719,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Adding nsp check [\#6](https://github.com/feathersjs/socketio/pull/6) ([marshallswain](https://github.com/marshallswain)) ## [v1.2.0](https://github.com/feathersjs/socketio/tree/v1.2.0) (2016-01-21) + [Full Changelog](https://github.com/feathersjs/socketio/compare/v1.1.0...v1.2.0) **Closed issues:** @@ -885,6 +732,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Fixing .npmignore entries [\#3](https://github.com/feathersjs/socketio/pull/3) ([corymsmith](https://github.com/corymsmith)) ## [v1.1.0](https://github.com/feathersjs/socketio/tree/v1.1.0) (2016-01-10) + [Full Changelog](https://github.com/feathersjs/socketio/compare/v1.0.0...v1.1.0) **Merged pull requests:** @@ -893,5 +741,4 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline ## [v1.0.0](https://github.com/feathersjs/socketio/tree/v1.0.0) (2016-01-03) - -\* *This Change Log was automatically generated by [github_changelog_generator](https://github.com/skywinder/Github-Changelog-Generator)* +\* _This Change Log was automatically generated by [github_changelog_generator](https://github.com/skywinder/Github-Changelog-Generator)_ diff --git a/packages/socketio/LICENSE b/packages/socketio/LICENSE index 3f395cc665..59604f46f3 100644 --- a/packages/socketio/LICENSE +++ b/packages/socketio/LICENSE @@ -1,6 +1,6 @@ The MIT License (MIT) -Copyright (c) 2021 Feathers +Copyright (c) 2022 Feathers Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated documentation files (the "Software"), to deal diff --git a/packages/socketio/README.md b/packages/socketio/README.md index 352762b089..68e41686f0 100644 --- a/packages/socketio/README.md +++ b/packages/socketio/README.md @@ -1,8 +1,8 @@ # @feathersjs/socketio [![CI](https://github.com/feathersjs/feathers/workflows/CI/badge.svg)](https://github.com/feathersjs/feathers/actions?query=workflow%3ACI) -[![Dependency Status](https://img.shields.io/david/feathersjs/feathers.svg?style=flat-square&path=packages/socketio)](https://david-dm.org/feathersjs/feathers?path=packages/socketio) [![Download Status](https://img.shields.io/npm/dm/@feathersjs/socketio.svg?style=flat-square)](https://www.npmjs.com/package/@feathersjs/socketio) +[![Discord](https://badgen.net/badge/icon/discord?icon=discord&label)](https://discord.gg/qa8kez8QBx) > The Feathers Socket.io real-time API provider @@ -18,6 +18,6 @@ Refer to the [Feathers SocketIO API documentation](https://docs.feathersjs.com/a ## License -Copyright (c) 2021 [Feathers contributors](https://github.com/feathersjs/feathers/graphs/contributors) +Copyright (c) 2022 [Feathers contributors](https://github.com/feathersjs/feathers/graphs/contributors) Licensed under the [MIT license](LICENSE). diff --git a/packages/socketio/package.json b/packages/socketio/package.json index bd6740084f..cff5703b3b 100644 --- a/packages/socketio/package.json +++ b/packages/socketio/package.json @@ -1,9 +1,10 @@ { "name": "@feathersjs/socketio", "description": "The Feathers Socket.io real-time API provider", - "version": "5.0.0-pre.16", + "version": "5.0.0-pre.31", "homepage": "https://feathersjs.com", "main": "lib/", + "types": "lib/", "keywords": [ "feathers", "feathers-plugin" @@ -15,7 +16,8 @@ }, "repository": { "type": "git", - "url": "git://github.com/feathersjs/feathers.git" + "url": "git://github.com/feathersjs/feathers.git", + "directory": "packages/socketio" }, "author": { "name": "Feathers contributors", @@ -40,7 +42,8 @@ ], "scripts": { "prepublish": "npm run compile", - "compile": "shx rm -rf lib/ && tsc", + "pack": "npm pack --pack-destination ../cli/test/build", + "compile": "shx rm -rf lib/ && tsc && npm run pack", "test": "mocha --config ../../.mocharc.json --recursive test/**.test.ts test/**/*.test.ts" }, "directories": { @@ -50,22 +53,22 @@ "access": "public" }, "dependencies": { - "@feathersjs/commons": "^5.0.0-pre.16", - "@feathersjs/feathers": "^5.0.0-pre.16", - "@feathersjs/transport-commons": "^5.0.0-pre.16", - "socket.io": "^4.4.0" + "@feathersjs/commons": "^5.0.0-pre.31", + "@feathersjs/feathers": "^5.0.0-pre.31", + "@feathersjs/transport-commons": "^5.0.0-pre.31", + "socket.io": "^4.5.2" }, "devDependencies": { - "@feathersjs/express": "^5.0.0-pre.16", - "@feathersjs/memory": "^5.0.0-pre.16", - "@feathersjs/tests": "^5.0.0-pre.16", - "@types/mocha": "^9.0.0", - "@types/node": "^17.0.5", + "@feathersjs/express": "^5.0.0-pre.31", + "@feathersjs/memory": "^5.0.0-pre.31", + "@feathersjs/tests": "^5.0.0-pre.31", + "@types/mocha": "^10.0.0", + "@types/node": "^18.8.2", "lodash": "^4.17.21", - "mocha": "^9.1.3", - "shx": "^0.3.3", - "socket.io-client": "^4.4.0", - "typescript": "^4.5.4" + "mocha": "^10.0.0", + "shx": "^0.3.4", + "socket.io-client": "^4.5.2", + "typescript": "^4.8.4" }, - "gitHead": "f0cd227a82d159b528193bd33747c97684a48773" + "gitHead": "4500dbeb8cea566678cf88b3313a88efd93a2ed9" } diff --git a/packages/socketio/src/index.ts b/packages/socketio/src/index.ts index 7a438e2e5c..e392206713 100644 --- a/packages/socketio/src/index.ts +++ b/packages/socketio/src/index.ts @@ -1,93 +1,104 @@ -import http from 'http'; -import { Server, ServerOptions } from 'socket.io'; -import { createDebug } from '@feathersjs/commons'; -import { Application } from '@feathersjs/feathers'; -import { socket } from '@feathersjs/transport-commons'; +import http from 'http' +import { Server, ServerOptions } from 'socket.io' +import { createDebug } from '@feathersjs/commons' +import { Application } from '@feathersjs/feathers' +import { socket } from '@feathersjs/transport-commons' -import { disconnect, params, authentication, FeathersSocket } from './middleware'; +import { disconnect, params, authentication, FeathersSocket } from './middleware' -const debug = createDebug('@feathersjs/socketio'); +const debug = createDebug('@feathersjs/socketio') declare module '@feathersjs/feathers/lib/declarations' { - interface Application { // eslint-disable-line - io: Server; - listen (options: any): Promise; + // eslint-disable-next-line @typescript-eslint/no-unused-vars + interface Application { + // eslint-disable-line + io: Server + listen(options: any): Promise } } -function configureSocketio (callback?: (io: Server) => void): (app: Application) => void; -function configureSocketio (options: number | Partial, callback?: (io: Server) => void): (app: Application) => void; -function configureSocketio (port: number, options?: Partial, callback?: (io: Server) => void): (app: Application) => void; -function configureSocketio (port?: any, options?: any, config?: any) { +function configureSocketio(callback?: (io: Server) => void): (app: Application) => void +function configureSocketio( + options: number | Partial, + callback?: (io: Server) => void +): (app: Application) => void +function configureSocketio( + port: number, + options?: Partial, + callback?: (io: Server) => void +): (app: Application) => void +function configureSocketio(port?: any, options?: any, config?: any) { if (typeof port !== 'number') { - config = options; - options = port; - port = null; + config = options + options = port + port = null } if (typeof options !== 'object') { - config = options; - options = {}; + config = options + options = {} } return (app: Application) => { // Function that gets the connection - const getParams = (socket: FeathersSocket) => socket.feathers; + const getParams = (socket: FeathersSocket) => socket.feathers // A mapping from connection to socket instance - const socketMap = new WeakMap(); + const socketMap = new WeakMap() // Promise that resolves with the Socket.io `io` instance // when `setup` has been called (with a server) - const done = new Promise(resolve => { - const { listen, setup } = app as any; + const done = new Promise((resolve) => { + const { listen, setup } = app as any Object.assign(app, { - async listen (this: any, ...args: any[]) { + async listen(this: any, ...args: any[]) { if (typeof listen === 'function') { // If `listen` already exists // usually the case when the app has been expressified - return listen.call(this, ...args); + return listen.call(this, ...args) } - const server = http.createServer(); + const server = http.createServer() - await this.setup(server); + await this.setup(server) - return server.listen(...args); + return server.listen(...args) }, - async setup (this: any, server: http.Server, ...rest: any[]) { + async setup(this: any, server: http.Server, ...rest: any[]) { if (!this.io) { - const io = this.io = new Server(port || server, options); + const io = (this.io = new Server(port || server, options)) - io.use(disconnect(app, getParams)); - io.use(params(app, socketMap)); - io.use(authentication(app, getParams)); + io.use(disconnect(app, getParams)) + io.use(params(app, socketMap)) + io.use(authentication(app, getParams)) // In Feathers it is easy to hit the standard Node warning limit // of event listeners (e.g. by registering 10 services). // So we set it to a higher number. 64 should be enough for everyone. - io.sockets.setMaxListeners(64); + io.sockets.setMaxListeners(64) } if (typeof config === 'function') { - debug('Calling SocketIO configuration function'); - config.call(this, this.io); + debug('Calling SocketIO configuration function') + config.call(this, this.io) } - resolve(this.io); + resolve(this.io) - return setup.call(this, server, ...rest); + return setup.call(this, server, ...rest) } - }); - }); - - app.configure(socket({ - done, - socketMap, - getParams, - emit: 'emit' - })); - }; + }) + }) + + app.configure( + socket({ + done, + socketMap, + getParams, + emit: 'emit' + }) + ) + } } -export = configureSocketio; +export = configureSocketio diff --git a/packages/socketio/src/middleware.ts b/packages/socketio/src/middleware.ts index c4e0d21c4c..ec6d63cd54 100644 --- a/packages/socketio/src/middleware.ts +++ b/packages/socketio/src/middleware.ts @@ -1,59 +1,64 @@ -import { Application, Params } from '@feathersjs/feathers'; -import { createDebug } from '@feathersjs/commons'; -import { Socket } from 'socket.io'; +import { Application, Params } from '@feathersjs/feathers' +import { createDebug } from '@feathersjs/commons' +import { Socket } from 'socket.io' -const debug = createDebug('@feathersjs/socketio/middleware'); +const debug = createDebug('@feathersjs/socketio/middleware') -export type ParamsGetter = (socket: Socket) => any; -export type NextFunction = (err?: any) => void; +export type ParamsGetter = (socket: Socket) => any +export type NextFunction = (err?: any) => void export interface FeathersSocket extends Socket { - feathers?: Params + feathers?: Params & { [key: string]: any } } -export const disconnect = (app: Application, getParams: ParamsGetter) => - (socket: FeathersSocket, next: NextFunction) => { - socket.once('disconnect', () => app.emit('disconnect', getParams(socket))); - next(); +export const disconnect = + (app: Application, getParams: ParamsGetter) => (socket: FeathersSocket, next: NextFunction) => { + socket.once('disconnect', () => app.emit('disconnect', getParams(socket))) + next() } -export const params = (_app: Application, socketMap: WeakMap) => - (socket: FeathersSocket, next: NextFunction) => { +export const params = + (_app: Application, socketMap: WeakMap) => (socket: FeathersSocket, next: NextFunction) => { socket.feathers = { provider: 'socketio', headers: socket.handshake.headers - }; + } - socketMap.set(socket.feathers, socket); + socketMap.set(socket.feathers, socket) - next(); + next() } -export const authentication = (app: Application, getParams: ParamsGetter, settings: any = {}) => +export const authentication = + (app: Application, getParams: ParamsGetter, settings: any = {}) => (socket: FeathersSocket, next: NextFunction) => { - const service = (app as any).defaultAuthentication ? (app as any).defaultAuthentication(settings.service) : null; + const service = (app as any).defaultAuthentication + ? (app as any).defaultAuthentication(settings.service) + : null if (service === null) { - return next(); + return next() } - const config = service.configuration; - const authStrategies = config.parseStrategies || config.authStrategies || []; + const config = service.configuration + const authStrategies = config.parseStrategies || config.authStrategies || [] if (authStrategies.length === 0) { - return next(); + return next() } - service.parse(socket.handshake, null, ...authStrategies) + service + .parse(socket.handshake, null, ...authStrategies) .then(async (authentication: any) => { if (authentication) { - debug('Parsed authentication from HTTP header', authentication); - socket.feathers.authentication = authentication; + debug('Parsed authentication from HTTP header', authentication) + socket.feathers.authentication = authentication await service.create(authentication, { provider: 'socketio', connection: getParams(socket) - }); + }) } - next(); - }).catch(next); + next() + }) + .catch(next) } diff --git a/packages/socketio/test/events.ts b/packages/socketio/test/events.ts index e9775f24f0..ff18008be6 100644 --- a/packages/socketio/test/events.ts +++ b/packages/socketio/test/events.ts @@ -1,139 +1,145 @@ -import { strict as assert } from 'assert'; -import { io, Socket } from 'socket.io-client'; -import { verify } from '@feathersjs/tests'; -import { RealTimeConnection } from '@feathersjs/transport-commons/src/channels/channel/base'; +import { strict as assert } from 'assert' +import { io, Socket } from 'socket.io-client' +import { verify } from '@feathersjs/tests' +import { RealTimeConnection } from '@feathersjs/transport-commons/src/channels/channel/base' export default (name: string, options: any) => { const call = (method: string, ...args: any[]) => { return new Promise((resolve, reject) => { - const { socket } = options; - const emitArgs = [ method, name ].concat(args); + const { socket } = options + const emitArgs = [method, name].concat(args) - socket.emit(...emitArgs, (error: any, result: any) => - error ? reject(error) : resolve(result) - ); - }); - }; + socket.emit(...emitArgs, (error: any, result: any) => (error ? reject(error) : resolve(result))) + }) + } const verifyEvent = (done: (err?: any) => void, callback: (data: any) => void) => { return function (data: any) { try { - callback(data); - done(); + callback(data) + done() } catch (error: any) { - done(error); + done(error) } - }; - }; + } + } describe('Basic service events', () => { - let socket: Socket; - let connection: RealTimeConnection; + let socket: Socket + let connection: RealTimeConnection - before(done => { + before((done) => { options.app.once('connection', (conn: RealTimeConnection) => { - connection = conn; + connection = conn - options.app.channel('default').join(connection); - options.app.publish(() => options.app.channel('default')); - done(); - }); - socket = io('http://localhost:7886'); - }); + options.app.channel('default').join(connection) + options.app.publish(() => options.app.channel('default')) + done() + }) + socket = io('http://localhost:7886') + }) - after(done => { - socket.once('disconnect', () => done()); - socket.disconnect(); - }); + after((done) => { + socket.once('disconnect', () => done()) + socket.disconnect() + }) - it(`${name} created`, done => { + it(`${name} created`, (done) => { const original = { name: 'created event' - }; + } - socket.once(`${name} created`, verifyEvent(done, data => - verify.create(original, data) - )); + socket.once( + `${name} created`, + verifyEvent(done, (data) => verify.create(original, data)) + ) - call('create', original); - }); + call('create', original) + }) - it(`${name} updated`, done => { + it(`${name} updated`, (done) => { const original = { name: 'updated event' - }; + } - socket.once(`${name} updated`, verifyEvent(done, (data: any) => - verify.update(10, original, data) - )); + socket.once( + `${name} updated`, + verifyEvent(done, (data: any) => verify.update(10, original, data)) + ) - call('update', 10, original); - }); + call('update', 10, original) + }) - it(`${name} patched`, done => { + it(`${name} patched`, (done) => { const original = { name: 'patched event' - }; + } - socket.once(`${name} patched`, verifyEvent(done, (data: any) => - verify.patch(12, original, data) - )); + socket.once( + `${name} patched`, + verifyEvent(done, (data: any) => verify.patch(12, original, data)) + ) - call('patch', 12, original); - }); + call('patch', 12, original) + }) - it(`${name} removed`, done => { - socket.once(`${name} removed`, verifyEvent(done, (data: any) => - verify.remove(333, data) - )); + it(`${name} removed`, (done) => { + socket.once( + `${name} removed`, + verifyEvent(done, (data: any) => verify.remove(333, data)) + ) - call('remove', 333); - }); + call('remove', 333) + }) - it(`${name} custom events`, done => { - const service = options.app.service(name); + it(`${name} custom events`, (done) => { + const service = options.app.service(name) const original = { name: 'created event' - }; + } - socket.once(`${name} log`, verifyEvent(done, (data: any) => { - assert.deepStrictEqual(data, { - message: 'Custom log event', data: original - }); - })); + socket.once( + `${name} log`, + verifyEvent(done, (data: any) => { + assert.deepStrictEqual(data, { + message: 'Custom log event', + data: original + }) + }) + ) service.emit('log', { data: original, message: 'Custom log event' - }); - }); - }); + }) + }) + }) describe('Event channels', () => { - const eventName = `${name} created`; + const eventName = `${name} created` - let connections: RealTimeConnection[]; - let sockets: any[]; + let connections: RealTimeConnection[] + let sockets: any[] - before(done => { - let counter = 0; + before((done) => { + let counter = 0 const handler = (connection: RealTimeConnection) => { - counter++; + counter++ - options.app.channel(connection.channel).join(connection); + options.app.channel(connection.channel).join(connection) - connections.push(connection); + connections.push(connection) if (counter === 3) { - done(); - options.app.removeListener('connection', handler); + done() + options.app.removeListener('connection', handler) } - }; + } - connections = []; - sockets = []; + connections = [] + sockets = [] - options.app.on('connection', handler); + options.app.on('connection', handler) sockets.push( io('http://localhost:7886', { @@ -147,68 +153,64 @@ export default (name: string, options: any) => { io('http://localhost:7886', { query: { channel: 'second' } }) - ); - }); + ) + }) after(() => { - sockets.forEach(socket => socket.disconnect()); - }); + sockets.forEach((socket) => socket.disconnect()) + }) - it(`filters '${eventName}' event for a single channel`, done => { - const service = options.app.service(name); - const [ socket, otherSocket ] = sockets; + it(`filters '${eventName}' event for a single channel`, (done) => { + const service = options.app.service(name) + const [socket, otherSocket] = sockets const onError = () => { - done(new Error('Should not get this event')); - }; + done(new Error('Should not get this event')) + } - service.publish('created', (data: any) => - options.app.channel(data.room) - ); + service.publish('created', (data: any) => options.app.channel(data.room)) socket.once(eventName, (data: any) => { - assert.strictEqual(data.room, 'first'); - otherSocket.removeEventListener(eventName, onError); - done(); - }); + assert.strictEqual(data.room, 'first') + otherSocket.removeEventListener(eventName, onError) + done() + }) - otherSocket.once(eventName, onError); + otherSocket.once(eventName, onError) service.create({ text: 'Event dispatching test', room: 'first' - }); - }); + }) + }) - it(`filters '${name} created' event for a channel with multiple connections`, done => { - let counter = 0; + it(`filters '${name} created' event for a channel with multiple connections`, (done) => { + let counter = 0 - const service = options.app.service(name); - const [ otherSocket, socketOne, socketTwo ] = sockets; + const service = options.app.service(name) + const [otherSocket, socketOne, socketTwo] = sockets const onError = () => { - done(new Error('Should not get this event')); - }; + done(new Error('Should not get this event')) + } const onEvent = (data: any) => { - counter++; - assert.strictEqual(data.room, 'second'); + counter++ + assert.strictEqual(data.room, 'second') if (++counter === 2) { - otherSocket.removeEventListener(eventName, onError); - done(); + otherSocket.removeEventListener(eventName, onError) + done() } - }; + } - service.publish('created', (data: any) => - options.app.channel(data.room) - ); + service.publish('created', (data: any) => options.app.channel(data.room)) - socketOne.once(eventName, onEvent); - socketTwo.once(eventName, onEvent); - otherSocket.once(eventName, onError); + socketOne.once(eventName, onEvent) + socketTwo.once(eventName, onEvent) + otherSocket.once(eventName, onError) service.create({ text: 'Event dispatching test', room: 'second' - }); - }); - }); -}; + }) + }) + }) +} diff --git a/packages/socketio/test/index.test.ts b/packages/socketio/test/index.test.ts index a4a06fa7ae..0e7a9e7b56 100644 --- a/packages/socketio/test/index.test.ts +++ b/packages/socketio/test/index.test.ts @@ -1,223 +1,267 @@ -import { strict as assert } from 'assert'; -import { feathers, Application, HookContext, NullableId, Params } from '@feathersjs/feathers'; -import express from '@feathersjs/express'; -import { Request, Response } from 'express'; -import { omit, extend } from 'lodash'; -import { io } from 'socket.io-client'; -import axios from 'axios'; -import { Server } from 'http'; -import { Service } from '@feathersjs/tests'; -import { Socket } from 'socket.io-client'; - -import methodTests from './methods'; -import eventTests from './events'; -import socketio from '../src'; -import { FeathersSocket, NextFunction } from '../src/middleware.js'; +import { strict as assert } from 'assert' +import { + feathers, + Application, + HookContext, + NullableId, + Params, + ApplicationHookContext +} from '@feathersjs/feathers' +import express from '@feathersjs/express' +import { Request, Response } from 'express' +import { omit, extend } from 'lodash' +import { io } from 'socket.io-client' +import axios from 'axios' +import { Server } from 'http' +import { Service } from '@feathersjs/tests' +import { Socket } from 'socket.io-client' + +import methodTests from './methods' +import eventTests from './events' +import socketio from '../src' +import { FeathersSocket, NextFunction } from '../src/middleware.js' class VerifierService { - async find (params: Params) { - return { params }; + async find(params: Params) { + return { params } } - async create (data: any, params: Params) { - return { data, params }; + async create(data: any, params: Params) { + return { data, params } } - async update (id: NullableId, data: any, params: Params) { - return { id, data, params }; + async update(id: NullableId, data: any, params: Params) { + return { id, data, params } } } describe('@feathersjs/socketio', () => { - let app: Application; - let server: Server; - let socket: Socket; + let app: Application + let server: Server + let socket: Socket const socketParams: any = { user: { name: 'David' }, provider: 'socketio' - }; + } const options = { - get app () { - return app; + get app() { + return app }, - get socket () { - return socket; + get socket() { + return socket } - }; + } - before(done => { + before((done) => { const errorHook = (hook: HookContext) => { if (hook.params.query.hookError) { - throw new Error(`Error from ${hook.method}, ${hook.type} hook`); + throw new Error(`Error from ${hook.method}, ${hook.type} hook`) } - }; + } app = feathers() - .configure(socketio(io => { - io.use(function (socket: FeathersSocket, next: NextFunction) { - socket.feathers.user = { name: 'David' }; - socketParams.headers = socket.feathers.headers; - - const { channel } = socket.handshake.query as any; - - if (channel) { - socket.feathers.channel = channel; - } - - next(); - }); - })) + .configure( + socketio((io) => { + io.use(function (socket: FeathersSocket, next: NextFunction) { + socket.feathers.user = { name: 'David' } + socketParams.headers = socket.feathers.headers + + const { channel } = socket.handshake.query as any + + if (channel) { + socket.feathers.channel = channel + } + + next() + }) + }) + ) .use('/todo', new Service()) - .use('/verify', new VerifierService()); + .use('/verify', new VerifierService()) app.service('todo').hooks({ before: { get: errorHook } - }); - - app.listen(7886).then(srv => { - server = srv; - server.once('listening', () => { - app.use('/tasks', new Service()); - app.service('tasks').hooks({ - before: { - get: errorHook - } - }); - }); - }); - - socket = io('http://localhost:7886'); - socket.on('connect', () => done()); - }); - - after(done => { - socket.disconnect(); - server.close(done); - }); - - it('runs io before setup (#131)', done => { - let counter = 0; - const app = feathers().configure(socketio(() => { - assert.strictEqual(counter, 0); - counter++; - })); - - app.listen(8887).then(srv => { - srv.on('listening', () => srv.close(done)); - }); - }); - - it('can set MaxListeners', done => { - const app = feathers().configure(socketio(io => - io.sockets.setMaxListeners(100) - )); - - app.listen(8987).then(srv => { + }) + + app.hooks({ + setup: [ + async (context: ApplicationHookContext, next: NextFunction) => { + assert.notStrictEqual(context.app, undefined) + await next() + } + ] + }) + + app + .listen(7886) + .then((srv) => { + server = srv + server.once('listening', () => { + app.use('/tasks', new Service()) + app.service('tasks').hooks({ + before: { + get: errorHook + } + }) + }) + }) + .catch(done) + + socket = io('http://localhost:7886') + socket.on('connect', () => done()) + }) + + after((done) => { + socket.disconnect() + server.close(done) + }) + + it('runs io before setup (#131)', (done) => { + let counter = 0 + const app = feathers().configure( + socketio(() => { + assert.strictEqual(counter, 0) + counter++ + }) + ) + + app.listen(8887).then((srv) => { + srv.on('listening', () => srv.close(done)) + }) + }) + + it('can set MaxListeners', (done) => { + const app = feathers().configure(socketio((io) => io.sockets.setMaxListeners(100))) + + app.listen(8987).then((srv) => { srv.on('listening', () => { - assert.strictEqual(app.io.sockets.getMaxListeners(), 100); - srv.close(done); - }); - }); - }); + assert.strictEqual(app.io.sockets.getMaxListeners(), 100) + srv.close(done) + }) + }) + }) it('expressified app works', async () => { - const data = { message: 'Hello world' }; + const data = { message: 'Hello world' } const app = express(feathers()) .configure(socketio()) - .use('/test', (_req: Request, res: Response) => res.json(data)); + .use('/test', (_req: Request, res: Response) => res.json(data)) - const srv = await app.listen(8992); + const srv = await app.listen(8992) const response = await axios({ url: 'http://localhost:8992/socket.io/socket.io.js' - }); + }) - assert.strictEqual(response.status, 200); + assert.strictEqual(response.status, 200) const res = await axios({ url: 'http://localhost:8992/test' - }); + }) + + assert.deepStrictEqual(res.data, data) - assert.deepStrictEqual(res.data, data); - - await new Promise(resolve => srv.close(() => resolve(srv))); - }); + await new Promise((resolve) => srv.close(() => resolve(srv))) + }) - it('can set options (#12)', done => { - const application = feathers().configure(socketio({ - path: '/test/' - }, ioInstance => assert.ok(ioInstance))); + it('can set options (#12)', (done) => { + const application = feathers().configure( + socketio( + { + path: '/test/' + }, + (ioInstance) => assert.ok(ioInstance) + ) + ) - application.listen(8987).then(srv => { + application.listen(8987).then((srv) => { srv.on('listening', async () => { - const { status } = await axios('http://localhost:8987/test/socket.io.js'); + const { status } = await axios('http://localhost:8987/test/socket.io.js') - assert.strictEqual(status, 200); - srv.close(done); - }); + assert.strictEqual(status, 200) + srv.close(done) + }) }) - }); + }) - it('passes handshake as service parameters', done => { + it('passes handshake as service parameters', (done) => { socket.emit('create', 'verify', {}, (error: any, data: any) => { - assert.ok(!error); - assert.deepStrictEqual(omit(data.params, 'query', 'route', 'connection'), socketParams, + assert.ok(!error) + assert.deepStrictEqual( + omit(data.params, 'query', 'route', 'connection'), + socketParams, 'Passed handshake parameters' - ); - - socket.emit('update', 'verify', 1, {}, { - test: 'param' - }, (error: any, data: any) => { - assert.ok(!error); - assert.deepStrictEqual(data.params, extend({ - route: {}, - connection: socketParams, - query: { - test: 'param' - } - }, socketParams), 'Passed handshake parameters as query'); - done(); - }); - }); - }); + ) + + socket.emit( + 'update', + 'verify', + 1, + {}, + { + test: 'param' + }, + (error: any, data: any) => { + assert.ok(!error) + assert.deepStrictEqual( + data.params, + extend( + { + route: {}, + connection: socketParams, + query: { + test: 'param' + } + }, + socketParams + ), + 'Passed handshake parameters as query' + ) + done() + } + ) + }) + }) it('connection and disconnect events (#1243, #1238)', (done) => { - const mySocket = io('http://localhost:7886?channel=dctest'); - - app.once('connection', connection => { - assert.strictEqual(connection.channel, 'dctest'); - app.once('disconnect', disconnection => { - assert.strictEqual(disconnection.channel, 'dctest'); - done(); - }); - setTimeout(() => mySocket.close(), 100); - }); + const mySocket = io('http://localhost:7886?channel=dctest') + + app.once('connection', (connection) => { + assert.strictEqual(connection.channel, 'dctest') + app.once('disconnect', (disconnection) => { + assert.strictEqual(disconnection.channel, 'dctest') + done() + }) + setTimeout(() => mySocket.close(), 100) + }) - assert.ok(mySocket); - }); + assert.ok(mySocket) + }) - it('missing parameters in socket call works (#88)', done => { + it('missing parameters in socket call works (#88)', (done) => { socket.emit('find', 'verify', (error: any, data: any) => { - assert.ok(!error); - assert.deepStrictEqual(omit(data.params, 'query', 'route', 'connection'), socketParams, + assert.ok(!error) + assert.deepStrictEqual( + omit(data.params, 'query', 'route', 'connection'), + socketParams, 'Handshake parameters passed on proper position' - ); - done(); - }); - }); + ) + done() + }) + }) describe('Service method calls', () => { - describe('(\'method\', \'service\') event format', () => { - describe('Service', () => methodTests('todo', options)); - describe('Dynamic Service', () => methodTests('todo', options)); - }); - }); + describe("('method', 'service') event format", () => { + describe('Service', () => methodTests('todo', options)) + describe('Dynamic Service', () => methodTests('todo', options)) + }) + }) describe('Service events', () => { - describe('Service', () => eventTests('todo', options)); - describe('Dynamic Service', () => eventTests('tasks', options)); - }); -}); + describe('Service', () => eventTests('todo', options)) + describe('Dynamic Service', () => eventTests('tasks', options)) + }) +}) diff --git a/packages/socketio/test/methods.ts b/packages/socketio/test/methods.ts index d573a42155..e376682256 100644 --- a/packages/socketio/test/methods.ts +++ b/packages/socketio/test/methods.ts @@ -1,130 +1,128 @@ -import { strict as assert } from 'assert'; -import { verify } from '@feathersjs/tests'; +import { strict as assert } from 'assert' +import { verify } from '@feathersjs/tests' export default (name: string, options: any) => { const call = (method: string, ...args: any[]) => new Promise((resolve, reject) => { - const { socket } = options; - const prefix = [method, name]; - const emitArgs = prefix.concat(args); + const { socket } = options + const prefix = [method, name] + const emitArgs = prefix.concat(args) - socket.emit(...emitArgs, (error: any, result: any) => - error ? reject(error) : resolve(result) - ); - }); + socket.emit(...emitArgs, (error: any, result: any) => (error ? reject(error) : resolve(result))) + }) it('invalid arguments cause an error', async () => { await assert.rejects(() => call('find', 1, {}), { - message: 'Too many arguments for \'find\' method' - }); - }); + message: "Too many arguments for 'find' method" + }) + }) it('.find', () => async () => { - await call('find', {}).then(data => verify.find(data)); - }); + await call('find', {}).then((data) => verify.find(data)) + }) it('.get', () => async () => { - await call('get', 'laundry').then(data => verify.get('laundry', data)); - }); + await call('get', 'laundry').then((data) => verify.get('laundry', data)) + }) it('.get with error', () => async () => { try { - await call('get', 'laundry', { error: true }); - assert.fail('Should never get here'); + await call('get', 'laundry', { error: true }) + assert.fail('Should never get here') } catch (error: any) { - assert.strictEqual(error.message, 'Something for laundry went wrong'); + assert.strictEqual(error.message, 'Something for laundry went wrong') } - }); + }) it('.get with runtime error', () => async () => { try { - await call('get', 'laundry', { runtimeError: true }); - assert.fail('Should never get here'); + await call('get', 'laundry', { runtimeError: true }) + assert.fail('Should never get here') } catch (error: any) { assert.strictEqual(error.message, 'thingThatDoesNotExist is not defined') } - }); + }) it('.get with error in hook', () => async () => { try { - await call('get', 'laundry', { hookError: true }); - assert.fail('Should never get here'); + await call('get', 'laundry', { hookError: true }) + assert.fail('Should never get here') } catch (error: any) { - assert.strictEqual(error.message, 'Error from get, before hook'); + assert.strictEqual(error.message, 'Error from get, before hook') } - }); + }) it('.create', async () => { const original = { name: 'creating' - }; + } - const data = await call('create', original, {}); + const data = await call('create', original, {}) - verify.create(original, data); - }); + verify.create(original, data) + }) it('.create without parameters', async () => { const original = { name: 'creating again' - }; + } - const data = await call('create', original); + const data = await call('create', original) - verify.create(original, data); - }); + verify.create(original, data) + }) it('.update', async () => { const original = { name: 'updating' - }; + } - const data = await call('update', 23, original, {}); + const data = await call('update', 23, original, {}) - verify.update(23, original, data); - }); + verify.update(23, original, data) + }) it('.update many', async () => { const original = { name: 'updating', many: true - }; + } - const data = await call('update', null, original); + const data = await call('update', null, original) - verify.update(null, original, data); - }); + verify.update(null, original, data) + }) it('.patch', async () => { const original = { name: 'patching' - }; + } - const data = await call('patch', 25, original); + const data = await call('patch', 25, original) - verify.patch(25, original, data); - }); + verify.patch(25, original, data) + }) it('.patch many', async () => { const original = { name: 'patching', many: true - }; + } - const data = await call('patch', null, original); + const data = await call('patch', null, original) - verify.patch(null, original, data); - }); + verify.patch(null, original, data) + }) it('.remove', () => async () => { - const data = await call('remove', 11); + const data = await call('remove', 11) - verify.remove(11, data); - }); + verify.remove(11, data) + }) it('.remove many', async () => { - const data = await call('remove', null); + const data = await call('remove', null) - verify.remove(null, data); - }); -}; + verify.remove(null, data) + }) +} diff --git a/packages/tests/CHANGELOG.md b/packages/tests/CHANGELOG.md index b0c3e4af5e..0f52aec55e 100644 --- a/packages/tests/CHANGELOG.md +++ b/packages/tests/CHANGELOG.md @@ -3,425 +3,287 @@ All notable changes to this project will be documented in this file. See [Conventional Commits](https://conventionalcommits.org) for commit guidelines. -# [5.0.0-pre.16](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.15...v5.0.0-pre.16) (2022-01-12) +# [5.0.0-pre.31](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.30...v5.0.0-pre.31) (2022-10-12) + +**Note:** Version bump only for package @feathersjs/tests +# [5.0.0-pre.30](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.29...v5.0.0-pre.30) (2022-10-07) ### Features -* **express, koa:** make transports similar ([#2486](https://github.com/feathersjs/feathers/issues/2486)) ([26aa937](https://github.com/feathersjs/feathers/commit/26aa937c114fb8596dfefc599b1f53cead69c159)) +- **core:** Allow to unregister services at runtime ([#2756](https://github.com/feathersjs/feathers/issues/2756)) ([d16601f](https://github.com/feathersjs/feathers/commit/d16601f2277dca5357866ffdefba2a611f6dc7fa)) +# [5.0.0-pre.29](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.28...v5.0.0-pre.29) (2022-09-16) +**Note:** Version bump only for package @feathersjs/tests +# [5.0.0-pre.28](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.27...v5.0.0-pre.28) (2022-08-03) +**Note:** Version bump only for package @feathersjs/tests -# [5.0.0-pre.15](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.14...v5.0.0-pre.15) (2021-11-27) +# [5.0.0-pre.27](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.26...v5.0.0-pre.27) (2022-07-13) **Note:** Version bump only for package @feathersjs/tests +# [5.0.0-pre.26](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.25...v5.0.0-pre.26) (2022-06-22) +**Note:** Version bump only for package @feathersjs/tests +# [5.0.0-pre.25](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.24...v5.0.0-pre.25) (2022-06-22) +**Note:** Version bump only for package @feathersjs/tests -# [5.0.0-pre.14](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.13...v5.0.0-pre.14) (2021-10-13) +# [5.0.0-pre.24](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.23...v5.0.0-pre.24) (2022-06-21) **Note:** Version bump only for package @feathersjs/tests +# [5.0.0-pre.23](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.22...v5.0.0-pre.23) (2022-06-06) +**Note:** Version bump only for package @feathersjs/tests +# [5.0.0-pre.22](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.21...v5.0.0-pre.22) (2022-05-24) +**Note:** Version bump only for package @feathersjs/tests -# [5.0.0-pre.13](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.12...v5.0.0-pre.13) (2021-10-13) +# [5.0.0-pre.21](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.20...v5.0.0-pre.21) (2022-05-23) **Note:** Version bump only for package @feathersjs/tests +# [5.0.0-pre.20](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.19...v5.0.0-pre.20) (2022-05-04) +### Bug Fixes +- **dependencies:** Lock monorepo package version numbers ([#2623](https://github.com/feathersjs/feathers/issues/2623)) ([5640c10](https://github.com/feathersjs/feathers/commit/5640c1020cc139994e695d658c08bad3494db507)) - -# [5.0.0-pre.12](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.11...v5.0.0-pre.12) (2021-10-12) +# [5.0.0-pre.19](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.18...v5.0.0-pre.19) (2022-05-01) **Note:** Version bump only for package @feathersjs/tests +# [5.0.0-pre.18](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.17...v5.0.0-pre.18) (2022-04-11) +**Note:** Version bump only for package @feathersjs/tests - - -# [5.0.0-pre.11](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.10...v5.0.0-pre.11) (2021-10-06) +# [5.0.0-pre.17](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.16...v5.0.0-pre.17) (2022-02-15) **Note:** Version bump only for package @feathersjs/tests +# [5.0.0-pre.16](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.15...v5.0.0-pre.16) (2022-01-12) +### Features +- **express, koa:** make transports similar ([#2486](https://github.com/feathersjs/feathers/issues/2486)) ([26aa937](https://github.com/feathersjs/feathers/commit/26aa937c114fb8596dfefc599b1f53cead69c159)) - -# [5.0.0-pre.10](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.9...v5.0.0-pre.10) (2021-09-19) +# [5.0.0-pre.15](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.14...v5.0.0-pre.15) (2021-11-27) **Note:** Version bump only for package @feathersjs/tests +# [5.0.0-pre.14](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.13...v5.0.0-pre.14) (2021-10-13) +**Note:** Version bump only for package @feathersjs/tests - - -# [5.0.0-pre.9](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.8...v5.0.0-pre.9) (2021-08-09) +# [5.0.0-pre.13](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.12...v5.0.0-pre.13) (2021-10-13) **Note:** Version bump only for package @feathersjs/tests +# [5.0.0-pre.12](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.11...v5.0.0-pre.12) (2021-10-12) +**Note:** Version bump only for package @feathersjs/tests +# [5.0.0-pre.11](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.10...v5.0.0-pre.11) (2021-10-06) +**Note:** Version bump only for package @feathersjs/tests -# [5.0.0-pre.8](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.7...v5.0.0-pre.8) (2021-08-09) +# [5.0.0-pre.10](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.9...v5.0.0-pre.10) (2021-09-19) **Note:** Version bump only for package @feathersjs/tests +# [5.0.0-pre.9](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.8...v5.0.0-pre.9) (2021-08-09) +**Note:** Version bump only for package @feathersjs/tests +# [5.0.0-pre.8](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.7...v5.0.0-pre.8) (2021-08-09) +**Note:** Version bump only for package @feathersjs/tests # [5.0.0-pre.7](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.6...v5.0.0-pre.7) (2021-08-09) **Note:** Version bump only for package @feathersjs/tests - - - - # [5.0.0-pre.6](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.5...v5.0.0-pre.6) (2021-08-08) **Note:** Version bump only for package @feathersjs/tests - - - - # [5.0.0-pre.5](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.4...v5.0.0-pre.5) (2021-06-23) - ### Bug Fixes -* **koa:** Use extended query parser for compatibility ([#2397](https://github.com/feathersjs/feathers/issues/2397)) ([b2944ba](https://github.com/feathersjs/feathers/commit/b2944bac3ec6d5ecc80dc518cd4e58093692db74)) - - - - +- **koa:** Use extended query parser for compatibility ([#2397](https://github.com/feathersjs/feathers/issues/2397)) ([b2944ba](https://github.com/feathersjs/feathers/commit/b2944bac3ec6d5ecc80dc518cd4e58093692db74)) # [5.0.0-pre.4](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.3...v5.0.0-pre.4) (2021-05-13) **Note:** Version bump only for package @feathersjs/tests - - - - # [5.0.0-pre.3](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.2...v5.0.0-pre.3) (2021-04-21) - ### Bug Fixes -* **typescript:** Improve TypeScript backwards compatibility ([#2310](https://github.com/feathersjs/feathers/issues/2310)) ([f33be73](https://github.com/feathersjs/feathers/commit/f33be73fc46a533efb15df9aab0658e3240d3897)) - - - - +- **typescript:** Improve TypeScript backwards compatibility ([#2310](https://github.com/feathersjs/feathers/issues/2310)) ([f33be73](https://github.com/feathersjs/feathers/commit/f33be73fc46a533efb15df9aab0658e3240d3897)) # [5.0.0-pre.2](https://github.com/feathersjs/feathers/compare/v5.0.0-beta.1...v5.0.0-pre.2) (2021-04-06) **Note:** Version bump only for package @feathersjs/tests - - - - # [5.0.0-beta.1](https://github.com/feathersjs/feathers/compare/v5.0.0-beta.0...v5.0.0-beta.1) (2021-04-03) **Note:** Version bump only for package @feathersjs/tests - - - - # [5.0.0-beta.0](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.1...v5.0.0-beta.0) (2021-03-28) - ### Bug Fixes -* Update Grant usage and other dependencies ([#2264](https://github.com/feathersjs/feathers/issues/2264)) ([7b0f8fa](https://github.com/feathersjs/feathers/commit/7b0f8fad252419ed0ad0bf259cdf3104d322ab60)) - +- Update Grant usage and other dependencies ([#2264](https://github.com/feathersjs/feathers/issues/2264)) ([7b0f8fa](https://github.com/feathersjs/feathers/commit/7b0f8fad252419ed0ad0bf259cdf3104d322ab60)) ### Features -* **core:** Public custom service methods ([#2270](https://github.com/feathersjs/feathers/issues/2270)) ([e65abfb](https://github.com/feathersjs/feathers/commit/e65abfb5388df6c19a11c565cf1076a29f32668d)) -* Feathers v5 core refactoring and features ([#2255](https://github.com/feathersjs/feathers/issues/2255)) ([2dafb7c](https://github.com/feathersjs/feathers/commit/2dafb7ce14ba57406aeec13d10ca45b1e709bee9)) - - - - +- **core:** Public custom service methods ([#2270](https://github.com/feathersjs/feathers/issues/2270)) ([e65abfb](https://github.com/feathersjs/feathers/commit/e65abfb5388df6c19a11c565cf1076a29f32668d)) +- Feathers v5 core refactoring and features ([#2255](https://github.com/feathersjs/feathers/issues/2255)) ([2dafb7c](https://github.com/feathersjs/feathers/commit/2dafb7ce14ba57406aeec13d10ca45b1e709bee9)) # [5.0.0-pre.1](https://github.com/feathersjs/feathers/compare/v4.5.11...v5.0.0-pre.1) (2020-12-17) - - # [5.0.0-pre.0](https://github.com/feathersjs/feathers/compare/v4.5.4...v5.0.0-pre.0) (2020-05-19) **Note:** Version bump only for package @feathersjs/tests - - - - # [5.0.0-pre.0](https://github.com/feathersjs/feathers/compare/v4.5.4...v5.0.0-pre.0) (2020-05-19) - - ## [4.5.11](https://github.com/feathersjs/feathers/compare/v4.5.10...v4.5.11) (2020-12-05) **Note:** Version bump only for package @feathersjs/tests - - - - ## [4.5.10](https://github.com/feathersjs/feathers/compare/v4.5.9...v4.5.10) (2020-11-08) **Note:** Version bump only for package @feathersjs/tests - - - - ## [4.5.9](https://github.com/feathersjs/feathers/compare/v4.5.8...v4.5.9) (2020-10-09) **Note:** Version bump only for package @feathersjs/tests - - - - ## [4.5.8](https://github.com/feathersjs/feathers/compare/v4.5.7...v4.5.8) (2020-08-12) **Note:** Version bump only for package @feathersjs/tests - ## [4.5.8](https://github.com/feathersjs/feathers/compare/v4.5.7...v4.5.8) (2020-08-12) - ## [4.5.7](https://github.com/feathersjs/feathers/compare/v4.5.6...v4.5.7) (2020-07-24) **Note:** Version bump only for package @feathersjs/tests - - - - ## [4.5.5](https://github.com/feathersjs/feathers/compare/v4.5.4...v4.5.5) (2020-07-11) **Note:** Version bump only for package @feathersjs/tests - - - - ## [4.5.3](https://github.com/feathersjs/feathers/compare/v4.5.2...v4.5.3) (2020-04-17) **Note:** Version bump only for package @feathersjs/tests - - - - ## [4.5.2](https://github.com/feathersjs/feathers/compare/v4.5.1...v4.5.2) (2020-03-04) **Note:** Version bump only for package @feathersjs/tests - - - - ## [4.5.1](https://github.com/feathersjs/feathers/compare/v4.5.0...v4.5.1) (2020-01-24) **Note:** Version bump only for package @feathersjs/tests - - - - # [4.5.0](https://github.com/feathersjs/feathers/compare/v4.4.3...v4.5.0) (2020-01-18) **Note:** Version bump only for package @feathersjs/tests - - - - ## [4.4.3](https://github.com/feathersjs/feathers/compare/v4.4.1...v4.4.3) (2019-12-06) **Note:** Version bump only for package @feathersjs/tests - - - - ## [4.4.1](https://github.com/feathersjs/feathers/compare/v4.4.0...v4.4.1) (2019-11-27) **Note:** Version bump only for package @feathersjs/tests - - - - # [4.4.0](https://github.com/feathersjs/feathers/compare/v4.3.11...v4.4.0) (2019-11-27) **Note:** Version bump only for package @feathersjs/tests - - - - ## [4.3.11](https://github.com/feathersjs/feathers/compare/v4.3.10...v4.3.11) (2019-11-11) **Note:** Version bump only for package @feathersjs/tests - - - - ## [4.3.10](https://github.com/feathersjs/feathers/compare/v4.3.9...v4.3.10) (2019-10-26) **Note:** Version bump only for package @feathersjs/tests - - - - ## [4.3.9](https://github.com/feathersjs/feathers/compare/v4.3.8...v4.3.9) (2019-10-26) **Note:** Version bump only for package @feathersjs/tests - - - - ## [4.3.7](https://github.com/feathersjs/feathers/compare/v4.3.6...v4.3.7) (2019-10-14) **Note:** Version bump only for package @feathersjs/tests - - - - ## [4.3.4](https://github.com/feathersjs/feathers/compare/v4.3.3...v4.3.4) (2019-10-03) **Note:** Version bump only for package @feathersjs/tests - - - - ## [4.3.3](https://github.com/feathersjs/feathers/compare/v4.3.2...v4.3.3) (2019-09-21) **Note:** Version bump only for package @feathersjs/tests - - - - ## [4.3.2](https://github.com/feathersjs/feathers/compare/v4.3.1...v4.3.2) (2019-09-16) **Note:** Version bump only for package @feathersjs/tests - - - - ## [4.3.1](https://github.com/feathersjs/feathers/compare/v4.3.0...v4.3.1) (2019-09-09) **Note:** Version bump only for package @feathersjs/tests - - - - # [4.3.0](https://github.com/feathersjs/feathers/compare/v4.3.0-pre.4...v4.3.0) (2019-08-27) **Note:** Version bump only for package @feathersjs/tests - - - - # [4.3.0-pre.4](https://github.com/feathersjs/feathers/compare/v4.3.0-pre.3...v4.3.0-pre.4) (2019-08-22) **Note:** Version bump only for package @feathersjs/tests - - - - # [4.3.0-pre.3](https://github.com/feathersjs/feathers/compare/v4.3.0-pre.2...v4.3.0-pre.3) (2019-08-19) - ### Bug Fixes -* Update all dependencies ([7d53a00](https://github.com/feathersjs/feathers/commit/7d53a00)) - - - - +- Update all dependencies ([7d53a00](https://github.com/feathersjs/feathers/commit/7d53a00)) # [4.3.0-pre.2](https://github.com/feathersjs/feathers/compare/v4.3.0-pre.1...v4.3.0-pre.2) (2019-08-02) **Note:** Version bump only for package @feathersjs/tests - - - - # [4.3.0-pre.1](https://github.com/feathersjs/feathers/compare/v4.0.0-pre.5...v4.3.0-pre.1) (2019-07-11) **Note:** Version bump only for package @feathersjs/tests - - - - # [4.0.0-pre.5](https://github.com/feathersjs/feathers/compare/v4.0.0-pre.4...v4.0.0-pre.5) (2019-07-10) **Note:** Version bump only for package @feathersjs/tests - - - - # [4.0.0-pre.4](https://github.com/feathersjs/feathers/compare/v4.0.0-pre.3...v4.0.0-pre.4) (2019-07-05) **Note:** Version bump only for package @feathersjs/tests - - - - # [4.0.0-pre.3](https://github.com/feathersjs/feathers/compare/v4.0.0-pre.2...v4.0.0-pre.3) (2019-06-01) - ### Bug Fixes -* Update dependencies and fix tests ([#1373](https://github.com/feathersjs/feathers/issues/1373)) ([d743a7f](https://github.com/feathersjs/feathers/commit/d743a7f)) - - - - +- Update dependencies and fix tests ([#1373](https://github.com/feathersjs/feathers/issues/1373)) ([d743a7f](https://github.com/feathersjs/feathers/commit/d743a7f)) # [4.0.0-pre.2](https://github.com/feathersjs/feathers/compare/v4.0.0-pre.1...v4.0.0-pre.2) (2019-05-15) **Note:** Version bump only for package @feathersjs/tests - - - - # [4.0.0-pre.1](https://github.com/feathersjs/feathers/compare/v4.0.0-pre.0...v4.0.0-pre.1) (2019-05-08) - ### Bug Fixes -* Improve authentication parameter handling ([#1333](https://github.com/feathersjs/feathers/issues/1333)) ([6e77204](https://github.com/feathersjs/feathers/commit/6e77204)) +- Improve authentication parameter handling ([#1333](https://github.com/feathersjs/feathers/issues/1333)) ([6e77204](https://github.com/feathersjs/feathers/commit/6e77204)) diff --git a/packages/tests/LICENSE b/packages/tests/LICENSE index 3f395cc665..59604f46f3 100644 --- a/packages/tests/LICENSE +++ b/packages/tests/LICENSE @@ -1,6 +1,6 @@ The MIT License (MIT) -Copyright (c) 2021 Feathers +Copyright (c) 2022 Feathers Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated documentation files (the "Software"), to deal diff --git a/packages/tests/README.md b/packages/tests/README.md index c959698005..f5018f2898 100644 --- a/packages/tests/README.md +++ b/packages/tests/README.md @@ -1,7 +1,6 @@ # @feathersjs/tests [![CI](https://github.com/feathersjs/feathers/workflows/CI/badge.svg)](https://github.com/feathersjs/feathers/actions?query=workflow%3ACI) -[![Dependency Status](https://img.shields.io/david/feathersjs/feathers.svg?style=flat-square&path=packages/express)](https://david-dm.org/feathersjs/feathers?path=packages/koa) [![Download Status](https://img.shields.io/npm/dm/@feathersjs/tests.svg?style=flat-square)](https://www.npmjs.com/package/@feathersjs/tests) > Common tests for Feathers core modules diff --git a/packages/tests/package.json b/packages/tests/package.json index d687415e79..d6cf34db66 100644 --- a/packages/tests/package.json +++ b/packages/tests/package.json @@ -2,9 +2,10 @@ "name": "@feathersjs/tests", "private": true, "description": "Feathers core module common tests", - "version": "5.0.0-pre.16", + "version": "5.0.0-pre.31", "homepage": "https://feathersjs.com", "main": "lib/", + "types": "lib/", "keywords": [ "feathers" ], @@ -15,7 +16,8 @@ }, "repository": { "type": "git", - "url": "git://github.com/feathersjs/feathers.git" + "url": "git://github.com/feathersjs/feathers.git", + "directory": "packages/tests" }, "author": { "name": "Feathers contributors", @@ -31,8 +33,9 @@ }, "scripts": { "prepublish": "npm run compile", - "compile": "shx rm -rf lib/ && tsc", - "test": "npm run compile" + "pack": "echo \"not necessary\"", + "test": "echo \"not necessary\"", + "compile": "shx rm -rf lib/ && tsc" }, "directories": { "lib": "lib" @@ -41,18 +44,17 @@ "access": "public" }, "dependencies": { - "@types/lodash": "^4.14.178", - "axios": "^0.24.0", + "@types/lodash": "^4.14.186", + "axios": "^0.27.2", "lodash": "^4.17.21" }, "devDependencies": { - "@feathersjs/feathers": "^5.0.0-pre.16", - "@types/axios": "^0.14.0", - "@types/mocha": "^9.0.0", - "@types/node": "^17.0.5", - "mocha": "^9.1.3", - "shx": "^0.3.3", - "ts-node": "^10.4.0", - "typescript": "^4.5.4" + "@feathersjs/feathers": "^5.0.0-pre.31", + "@types/mocha": "^10.0.0", + "@types/node": "^18.8.2", + "mocha": "^10.0.0", + "shx": "^0.3.4", + "ts-node": "^10.9.1", + "typescript": "^4.8.4" } } diff --git a/packages/tests/src/client.ts b/packages/tests/src/client.ts index b0cf028257..5d18a2243f 100644 --- a/packages/tests/src/client.ts +++ b/packages/tests/src/client.ts @@ -1,110 +1,121 @@ -import { strict as assert } from 'assert'; +import { strict as assert } from 'assert' export interface Todo { - text: string; - complete?: boolean; - id?: number; + text: string + complete?: boolean + id?: number } -export function clientTests (app: any, name: string) { - const getService = () => (name && typeof app.service === 'function') - ? app.service(name) : app; +export function clientTests(app: any, name: string) { + const getService = () => (name && typeof app.service === 'function' ? app.service(name) : app) describe('Service base tests', () => { it('.find', async () => { - const todos = await getService().find(); - - assert.deepEqual(todos, [{ // eslint-disable-line - text: 'some todo', - complete: false, - id: 0 - }]); - }); + const todos = await getService().find() + + assert.deepEqual(todos, [ + { + // eslint-disable-line + text: 'some todo', + complete: false, + id: 0 + } + ]) + }) it('.get and params passing', async () => { const query = { some: 'thing', other: ['one', 'two'], nested: { a: { b: 'object' } } - }; + } - const todo = await getService().get(0, { query }); + const todo = await getService().get(0, { query }) - assert.deepEqual(todo, { // eslint-disable-line + assert.deepEqual(todo, { + // eslint-disable-line id: 0, text: 'some todo', complete: false, query - }); - }); + }) + }) it('.create', async () => { - const todo = await getService().create({ text: 'created todo', complete: true }); + const todo = await getService().create({ + text: 'created todo', + complete: true + }) - assert.deepEqual(todo, { // eslint-disable-line + assert.deepEqual(todo, { + // eslint-disable-line id: 1, text: 'created todo', complete: true - }); - }); + }) + }) - it('.create and created event', done => { + it('.create and created event', (done) => { getService().once('created', (data: Todo) => { - assert.strictEqual(data.text, 'created todo'); - assert.ok(data.complete); - done(); - }); + assert.strictEqual(data.text, 'created todo') + assert.ok(data.complete) + done() + }) - getService().create({ text: 'created todo', complete: true }); - }); + getService().create({ text: 'created todo', complete: true }) + }) - it('.update and updated event', done => { + it('.update and updated event', (done) => { getService().once('updated', (data: Todo) => { - assert.strictEqual(data.text, 'updated todo'); - assert.ok(data.complete); - done(); - }); + assert.strictEqual(data.text, 'updated todo') + assert.ok(data.complete) + done() + }) - getService().create({ text: 'todo to update', complete: false }) + getService() + .create({ text: 'todo to update', complete: false }) .then((todo: Todo) => { getService().update(todo.id, { text: 'updated todo', complete: true - }); - }); - }); + }) + }) + }) - it('.patch and patched event', done => { + it('.patch and patched event', (done) => { getService().once('patched', (data: Todo) => { - assert.strictEqual(data.text, 'todo to patch'); - assert.ok(data.complete); - done(); - }); + assert.strictEqual(data.text, 'todo to patch') + assert.ok(data.complete) + done() + }) - getService().create({ text: 'todo to patch', complete: false }) - .then((todo: Todo) => getService().patch(todo.id, { complete: true })); - }); + getService() + .create({ text: 'todo to patch', complete: false }) + .then((todo: Todo) => getService().patch(todo.id, { complete: true })) + }) - it('.remove and removed event', done => { + it('.remove and removed event', (done) => { getService().once('removed', (data: Todo) => { - assert.strictEqual(data.text, 'todo to remove'); - assert.strictEqual(data.complete, false); - done(); - }); + assert.strictEqual(data.text, 'todo to remove') + assert.strictEqual(data.complete, false) + done() + }) - getService().create({ text: 'todo to remove', complete: false }) - .then((todo: Todo) => getService().remove(todo.id)).catch(done); - }); + getService() + .create({ text: 'todo to remove', complete: false }) + .then((todo: Todo) => getService().remove(todo.id)) + .catch(done) + }) it('.get with error', async () => { - const query = { error: true }; + const query = { error: true } try { - await getService().get(0, { query }); - assert.fail('Should never get here'); + await getService().get(0, { query }) + assert.fail('Should never get here') } catch (error: any) { - assert.strictEqual(error.message, 'Something went wrong'); + assert.strictEqual(error.message, 'Something went wrong') } - }); - }); + }) + }) } diff --git a/packages/tests/src/fixture.ts b/packages/tests/src/fixture.ts index a4d1c5d449..2e7bbb3fbf 100644 --- a/packages/tests/src/fixture.ts +++ b/packages/tests/src/fixture.ts @@ -1,127 +1,133 @@ -import assert from 'assert'; +import assert from 'assert' -const clone = (data: any) => JSON.parse(JSON.stringify(data)); +const clone = (data: any) => JSON.parse(JSON.stringify(data)) -const findAllData = [{ - id: 0, - description: 'You have to do something' -}, { - id: 1, - description: 'You have to do laundry' -}]; +const findAllData = [ + { + id: 0, + description: 'You have to do something' + }, + { + id: 1, + description: 'You have to do laundry' + } +] export class Service { - events = [ 'log' ]; + events = ['log'] - async find () { - return findAllData; + async find() { + return findAllData } - async get (name: string, params: any) { + async get(name: string, params: any) { if (params.query.error) { - throw new Error(`Something for ${name} went wrong`); + throw new Error(`Something for ${name} went wrong`) } if (params.query.runtimeError) { + // eslint-disable-next-line @typescript-eslint/ban-ts-comment // @ts-ignore - thingThatDoesNotExist(); // eslint-disable-line + thingThatDoesNotExist() // eslint-disable-line } return Promise.resolve({ id: name, description: `You have to do ${name}!` - }); + }) } - async create (data: any) { + async create(data: any) { const result = Object.assign({}, clone(data), { id: 42, status: 'created' - }); + }) if (Array.isArray(data)) { - result.many = true; + result.many = true } - return result; + return result } - async update (id: any, data: any) { + async update(id: any, data: any) { const result = Object.assign({}, clone(data), { - id, status: 'updated' - }); + id, + status: 'updated' + }) if (id === null) { - result.many = true; + result.many = true } - return result; + return result } - async patch (id: any, data: any) { + async patch(id: any, data: any) { const result = Object.assign({}, clone(data), { - id, status: 'patched' - }); + id, + status: 'patched' + }) if (id === null) { - result.many = true; + result.many = true } - return result; + return result } - async remove (id: any) { - return { id }; + async remove(id: any) { + return { id } } - async customMethod (data: any, params: any) { + async customMethod(data: any, params: any) { return { data, method: 'customMethod', provider: params.provider - }; + } } - async internalMethod () { - throw new Error('Should never get here'); + async internalMethod() { + throw new Error('Should never get here') } } export const verify = { - find (data: any) { - assert.deepStrictEqual(findAllData, clone(data), 'Data as expected'); + find(data: any) { + assert.deepStrictEqual(findAllData, clone(data), 'Data as expected') }, - get (id: any, data: any) { - assert.strictEqual(data.id, id, 'Got id in data'); - assert.strictEqual(data.description, `You have to do ${id}!`, 'Got description'); + get(id: any, data: any) { + assert.strictEqual(data.id, id, 'Got id in data') + assert.strictEqual(data.description, `You have to do ${id}!`, 'Got description') }, - create (original: any, current: any) { + create(original: any, current: any) { const expected = Object.assign({}, clone(original), { id: 42, status: 'created' - }); - assert.deepStrictEqual(expected, clone(current), 'Data ran through .create as expected'); + }) + assert.deepStrictEqual(expected, clone(current), 'Data ran through .create as expected') }, - update (id: any, original: any, current: any) { + update(id: any, original: any, current: any) { const expected = Object.assign({}, clone(original), { id, status: 'updated' - }); - assert.deepStrictEqual(expected, clone(current), 'Data ran through .update as expected'); + }) + assert.deepStrictEqual(expected, clone(current), 'Data ran through .update as expected') }, - patch (id: any, original: any, current: any) { + patch(id: any, original: any, current: any) { const expected = Object.assign({}, clone(original), { id, status: 'patched' - }); - assert.deepStrictEqual(expected, clone(current), 'Data ran through .patch as expected'); + }) + assert.deepStrictEqual(expected, clone(current), 'Data ran through .patch as expected') }, - remove (id: any, data: any) { - assert.deepStrictEqual({ id }, clone(data), '.remove called'); + remove(id: any, data: any) { + assert.deepStrictEqual({ id }, clone(data), '.remove called') } -}; +} diff --git a/packages/tests/src/index.ts b/packages/tests/src/index.ts index 9fccaeb726..214319e144 100644 --- a/packages/tests/src/index.ts +++ b/packages/tests/src/index.ts @@ -1,3 +1,3 @@ -export * from './client'; -export * from './rest'; -export * from './fixture'; +export * from './client' +export * from './rest' +export * from './fixture' diff --git a/packages/tests/src/rest.ts b/packages/tests/src/rest.ts index bcc975fc95..78149ba366 100644 --- a/packages/tests/src/rest.ts +++ b/packages/tests/src/rest.ts @@ -1,94 +1,94 @@ -import assert from 'assert'; -import axios from 'axios'; +import assert from 'assert' +import axios from 'axios' -import { verify } from './fixture'; +import { verify } from './fixture' -export function restTests (description: string, name: string, port: number) { +export function restTests(description: string, name: string, port: number) { describe(description, () => { it('GET .find', async () => { - const res = await axios.get(`http://localhost:${port}/${name}`); + const res = await axios.get(`http://localhost:${port}/${name}`) - assert.ok(res.status === 200, 'Got OK status code'); - verify.find(res.data); - }); + assert.ok(res.status === 200, 'Got OK status code') + verify.find(res.data) + }) it('GET .get', async () => { - const res = await axios.get(`http://localhost:${port}/${name}/dishes`); + const res = await axios.get(`http://localhost:${port}/${name}/dishes`) - assert.ok(res.status === 200, 'Got OK status code'); - verify.get('dishes', res.data); - }); + assert.ok(res.status === 200, 'Got OK status code') + verify.get('dishes', res.data) + }) it('POST .create', async () => { const original = { description: 'POST .create' - }; + } - const res = await axios.post(`http://localhost:${port}/${name}`, original); + const res = await axios.post(`http://localhost:${port}/${name}`, original) - assert.ok(res.status === 201, 'Got CREATED status code'); - verify.create(original, res.data); - }); + assert.ok(res.status === 201, 'Got CREATED status code') + verify.create(original, res.data) + }) it('PUT .update', async () => { const original = { description: 'PUT .update' - }; + } - const res = await axios.put(`http://localhost:${port}/${name}/544`, original); + const res = await axios.put(`http://localhost:${port}/${name}/544`, original) - assert.ok(res.status === 200, 'Got OK status code'); - verify.update('544', original, res.data); - }); + assert.ok(res.status === 200, 'Got OK status code') + verify.update('544', original, res.data) + }) it('PUT .update many', async () => { const original = { description: 'PUT .update', many: true - }; + } - const res = await axios.put(`http://localhost:${port}/${name}`, original); - const { data } = res; + const res = await axios.put(`http://localhost:${port}/${name}`, original) + const { data } = res - assert.ok(res.status === 200, 'Got OK status code'); - verify.update(null, original, data); - }); + assert.ok(res.status === 200, 'Got OK status code') + verify.update(null, original, data) + }) it('PATCH .patch', async () => { const original = { description: 'PATCH .patch' - }; + } - const res = await axios.patch(`http://localhost:${port}/${name}/544`, original); + const res = await axios.patch(`http://localhost:${port}/${name}/544`, original) - assert.ok(res.status === 200, 'Got OK status code'); - verify.patch('544', original, res.data); - }); + assert.ok(res.status === 200, 'Got OK status code') + verify.patch('544', original, res.data) + }) it('PATCH .patch many', async () => { const original = { description: 'PATCH .patch', many: true - }; + } - const res = await axios.patch(`http://localhost:${port}/${name}`, original); + const res = await axios.patch(`http://localhost:${port}/${name}`, original) - assert.ok(res.status === 200, 'Got OK status code'); - verify.patch(null, original, res.data); - }); + assert.ok(res.status === 200, 'Got OK status code') + verify.patch(null, original, res.data) + }) it('DELETE .remove', async () => { const res = await axios.delete(`http://localhost:${port}/${name}/233`) - assert.ok(res.status === 200, 'Got OK status code'); - verify.remove('233', res.data); - }); + assert.ok(res.status === 200, 'Got OK status code') + verify.remove('233', res.data) + }) it('DELETE .remove many', async () => { - const res = await axios.delete(`http://localhost:${port}/${name}`); + const res = await axios.delete(`http://localhost:${port}/${name}`) - assert.ok(res.status === 200, 'Got OK status code'); - verify.remove(null, res.data); - }); - }); + assert.ok(res.status === 200, 'Got OK status code') + verify.remove(null, res.data) + }) + }) } diff --git a/packages/transport-commons/CHANGELOG.md b/packages/transport-commons/CHANGELOG.md index 343ff398a0..8130f88533 100644 --- a/packages/transport-commons/CHANGELOG.md +++ b/packages/transport-commons/CHANGELOG.md @@ -3,597 +3,426 @@ All notable changes to this project will be documented in this file. See [Conventional Commits](https://conventionalcommits.org) for commit guidelines. -# [5.0.0-pre.16](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.15...v5.0.0-pre.16) (2022-01-12) - +# [5.0.0-pre.31](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.30...v5.0.0-pre.31) (2022-10-12) ### Features -* **express, koa:** make transports similar ([#2486](https://github.com/feathersjs/feathers/issues/2486)) ([26aa937](https://github.com/feathersjs/feathers/commit/26aa937c114fb8596dfefc599b1f53cead69c159)) +- **cli:** Generate full client test suite and improve typed client ([#2788](https://github.com/feathersjs/feathers/issues/2788)) ([57119b6](https://github.com/feathersjs/feathers/commit/57119b6bb2797f7297cf054268a248c093ecd538)) +# [5.0.0-pre.30](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.29...v5.0.0-pre.30) (2022-10-07) +### Features +- **core:** Allow to unregister services at runtime ([#2756](https://github.com/feathersjs/feathers/issues/2756)) ([d16601f](https://github.com/feathersjs/feathers/commit/d16601f2277dca5357866ffdefba2a611f6dc7fa)) +# [5.0.0-pre.29](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.28...v5.0.0-pre.29) (2022-09-16) -# [5.0.0-pre.15](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.14...v5.0.0-pre.15) (2021-11-27) +**Note:** Version bump only for package @feathersjs/transport-commons +# [5.0.0-pre.28](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.27...v5.0.0-pre.28) (2022-08-03) ### Bug Fixes -* **typescript:** Overall typing improvements ([#2478](https://github.com/feathersjs/feathers/issues/2478)) ([b8eb804](https://github.com/feathersjs/feathers/commit/b8eb804158556d9651a8607e3c3fda15e0bfd110)) +- **cli:** Improve generated application and client ([#2701](https://github.com/feathersjs/feathers/issues/2701)) ([bd55ffb](https://github.com/feathersjs/feathers/commit/bd55ffb812e89bf215f4515e7f137656ea888c3f)) +# [5.0.0-pre.27](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.26...v5.0.0-pre.27) (2022-07-13) -### Features +### Bug Fixes -* **core:** add `context.http` and move `statusCode` there ([#2496](https://github.com/feathersjs/feathers/issues/2496)) ([b701bf7](https://github.com/feathersjs/feathers/commit/b701bf77fb83048aa1dffa492b3d77dd53f7b72b)) -* **transport-commons:** Ability to register routes with custom params ([#2482](https://github.com/feathersjs/feathers/issues/2482)) ([497990a](https://github.com/feathersjs/feathers/commit/497990ae4a980e5a52a1f0f932db12cd0e6e254a)) +- **socketio-client:** Make Socket.io client event target compatible ([#2686](https://github.com/feathersjs/feathers/issues/2686)) ([716c49a](https://github.com/feathersjs/feathers/commit/716c49a270e4be5e5276192092c292f72ffcfa19)) +# [5.0.0-pre.26](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.25...v5.0.0-pre.26) (2022-06-22) +**Note:** Version bump only for package @feathersjs/transport-commons +# [5.0.0-pre.25](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.24...v5.0.0-pre.25) (2022-06-22) +**Note:** Version bump only for package @feathersjs/transport-commons -# [5.0.0-pre.14](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.13...v5.0.0-pre.14) (2021-10-13) +# [5.0.0-pre.24](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.23...v5.0.0-pre.24) (2022-06-21) **Note:** Version bump only for package @feathersjs/transport-commons +# [5.0.0-pre.23](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.22...v5.0.0-pre.23) (2022-06-06) +### Features +- **client:** Improve client side custom method support ([#2654](https://github.com/feathersjs/feathers/issues/2654)) ([c138acf](https://github.com/feathersjs/feathers/commit/c138acf50affbe6b66177d084d3c7a3e9220f09f)) - -# [5.0.0-pre.13](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.12...v5.0.0-pre.13) (2021-10-13) +# [5.0.0-pre.22](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.21...v5.0.0-pre.22) (2022-05-24) **Note:** Version bump only for package @feathersjs/transport-commons +# [5.0.0-pre.21](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.20...v5.0.0-pre.21) (2022-05-23) +**Note:** Version bump only for package @feathersjs/transport-commons +# [5.0.0-pre.20](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.19...v5.0.0-pre.20) (2022-05-04) +### Bug Fixes -# [5.0.0-pre.12](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.11...v5.0.0-pre.12) (2021-10-12) +- **dependencies:** Lock monorepo package version numbers ([#2623](https://github.com/feathersjs/feathers/issues/2623)) ([5640c10](https://github.com/feathersjs/feathers/commit/5640c1020cc139994e695d658c08bad3494db507)) -**Note:** Version bump only for package @feathersjs/transport-commons +# [5.0.0-pre.19](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.18...v5.0.0-pre.19) (2022-05-01) + +### Bug Fixes +- **transport-commons:** Ensure socket queries are always plain objects ([#2597](https://github.com/feathersjs/feathers/issues/2597)) ([97313e1](https://github.com/feathersjs/feathers/commit/97313e121cfee4199f10012e95b8507557aa507e)) +# [5.0.0-pre.18](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.17...v5.0.0-pre.18) (2022-04-11) +### Features +- **transport-commons:** add `context.http.response` ([#2524](https://github.com/feathersjs/feathers/issues/2524)) ([5bc9d44](https://github.com/feathersjs/feathers/commit/5bc9d447043c2e2b742c73ed28ecf3b3264dd9e5)) -# [5.0.0-pre.11](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.10...v5.0.0-pre.11) (2021-10-06) +# [5.0.0-pre.17](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.16...v5.0.0-pre.17) (2022-02-15) **Note:** Version bump only for package @feathersjs/transport-commons +# [5.0.0-pre.16](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.15...v5.0.0-pre.16) (2022-01-12) +### Features +- **express, koa:** make transports similar ([#2486](https://github.com/feathersjs/feathers/issues/2486)) ([26aa937](https://github.com/feathersjs/feathers/commit/26aa937c114fb8596dfefc599b1f53cead69c159)) +# [5.0.0-pre.15](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.14...v5.0.0-pre.15) (2021-11-27) -# [5.0.0-pre.10](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.9...v5.0.0-pre.10) (2021-09-19) +### Bug Fixes -**Note:** Version bump only for package @feathersjs/transport-commons +- **typescript:** Overall typing improvements ([#2478](https://github.com/feathersjs/feathers/issues/2478)) ([b8eb804](https://github.com/feathersjs/feathers/commit/b8eb804158556d9651a8607e3c3fda15e0bfd110)) +### Features +- **core:** add `context.http` and move `statusCode` there ([#2496](https://github.com/feathersjs/feathers/issues/2496)) ([b701bf7](https://github.com/feathersjs/feathers/commit/b701bf77fb83048aa1dffa492b3d77dd53f7b72b)) +- **transport-commons:** Ability to register routes with custom params ([#2482](https://github.com/feathersjs/feathers/issues/2482)) ([497990a](https://github.com/feathersjs/feathers/commit/497990ae4a980e5a52a1f0f932db12cd0e6e254a)) +# [5.0.0-pre.14](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.13...v5.0.0-pre.14) (2021-10-13) +**Note:** Version bump only for package @feathersjs/transport-commons -# [5.0.0-pre.9](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.8...v5.0.0-pre.9) (2021-08-09) +# [5.0.0-pre.13](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.12...v5.0.0-pre.13) (2021-10-13) **Note:** Version bump only for package @feathersjs/transport-commons +# [5.0.0-pre.12](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.11...v5.0.0-pre.12) (2021-10-12) +**Note:** Version bump only for package @feathersjs/transport-commons +# [5.0.0-pre.11](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.10...v5.0.0-pre.11) (2021-10-06) +**Note:** Version bump only for package @feathersjs/transport-commons -# [5.0.0-pre.8](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.7...v5.0.0-pre.8) (2021-08-09) +# [5.0.0-pre.10](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.9...v5.0.0-pre.10) (2021-09-19) **Note:** Version bump only for package @feathersjs/transport-commons +# [5.0.0-pre.9](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.8...v5.0.0-pre.9) (2021-08-09) +**Note:** Version bump only for package @feathersjs/transport-commons +# [5.0.0-pre.8](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.7...v5.0.0-pre.8) (2021-08-09) +**Note:** Version bump only for package @feathersjs/transport-commons # [5.0.0-pre.7](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.6...v5.0.0-pre.7) (2021-08-09) **Note:** Version bump only for package @feathersjs/transport-commons - - - - # [5.0.0-pre.6](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.5...v5.0.0-pre.6) (2021-08-08) **Note:** Version bump only for package @feathersjs/transport-commons - - - - # [5.0.0-pre.5](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.4...v5.0.0-pre.5) (2021-06-23) - ### Bug Fixes -* **koa:** Use extended query parser for compatibility ([#2397](https://github.com/feathersjs/feathers/issues/2397)) ([b2944ba](https://github.com/feathersjs/feathers/commit/b2944bac3ec6d5ecc80dc518cd4e58093692db74)) - - - - +- **koa:** Use extended query parser for compatibility ([#2397](https://github.com/feathersjs/feathers/issues/2397)) ([b2944ba](https://github.com/feathersjs/feathers/commit/b2944bac3ec6d5ecc80dc518cd4e58093692db74)) # [5.0.0-pre.4](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.3...v5.0.0-pre.4) (2021-05-13) - ### Bug Fixes -* **transport-commons:** Fix route placeholder registration and improve radix router performance ([#2336](https://github.com/feathersjs/feathers/issues/2336)) ([4d84dfd](https://github.com/feathersjs/feathers/commit/4d84dfd092ce0510312e975d5cd57e04973fb311)) - +- **transport-commons:** Fix route placeholder registration and improve radix router performance ([#2336](https://github.com/feathersjs/feathers/issues/2336)) ([4d84dfd](https://github.com/feathersjs/feathers/commit/4d84dfd092ce0510312e975d5cd57e04973fb311)) ### Features -* **koa:** KoaJS transport adapter ([#2315](https://github.com/feathersjs/feathers/issues/2315)) ([2554b57](https://github.com/feathersjs/feathers/commit/2554b57cf05731df58feeba9c12faab18e442107)) - - - - +- **koa:** KoaJS transport adapter ([#2315](https://github.com/feathersjs/feathers/issues/2315)) ([2554b57](https://github.com/feathersjs/feathers/commit/2554b57cf05731df58feeba9c12faab18e442107)) # [5.0.0-pre.3](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.2...v5.0.0-pre.3) (2021-04-21) - ### Bug Fixes -* **typescript:** Improve TypeScript backwards compatibility ([#2310](https://github.com/feathersjs/feathers/issues/2310)) ([f33be73](https://github.com/feathersjs/feathers/commit/f33be73fc46a533efb15df9aab0658e3240d3897)) - +- **typescript:** Improve TypeScript backwards compatibility ([#2310](https://github.com/feathersjs/feathers/issues/2310)) ([f33be73](https://github.com/feathersjs/feathers/commit/f33be73fc46a533efb15df9aab0658e3240d3897)) ### Features -* **dependencies:** Remove direct debug dependency ([#2296](https://github.com/feathersjs/feathers/issues/2296)) ([501d416](https://github.com/feathersjs/feathers/commit/501d4164d30c6a126906dc640cdfdc82207ba34a)) - - - - +- **dependencies:** Remove direct debug dependency ([#2296](https://github.com/feathersjs/feathers/issues/2296)) ([501d416](https://github.com/feathersjs/feathers/commit/501d4164d30c6a126906dc640cdfdc82207ba34a)) # [5.0.0-pre.2](https://github.com/feathersjs/feathers/compare/v5.0.0-beta.1...v5.0.0-pre.2) (2021-04-06) **Note:** Version bump only for package @feathersjs/transport-commons - - - - # [5.0.0-beta.1](https://github.com/feathersjs/feathers/compare/v5.0.0-beta.0...v5.0.0-beta.1) (2021-04-03) **Note:** Version bump only for package @feathersjs/transport-commons - - - - # [5.0.0-beta.0](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.1...v5.0.0-beta.0) (2021-03-28) - ### Bug Fixes -* **transport-commons:** Do not error when adding an undefined connection to a channel ([#2268](https://github.com/feathersjs/feathers/issues/2268)) ([28114c4](https://github.com/feathersjs/feathers/commit/28114c495d6564868bb3ffbf619bf80b774dce4b)) -* Update Grant usage and other dependencies ([#2264](https://github.com/feathersjs/feathers/issues/2264)) ([7b0f8fa](https://github.com/feathersjs/feathers/commit/7b0f8fad252419ed0ad0bf259cdf3104d322ab60)) -* **socketio-client:** Fix client transport-commons reference ([#2164](https://github.com/feathersjs/feathers/issues/2164)) ([3a42c54](https://github.com/feathersjs/feathers/commit/3a42c544058456b19c7e21827226541bfa6ad621)) - +- **transport-commons:** Do not error when adding an undefined connection to a channel ([#2268](https://github.com/feathersjs/feathers/issues/2268)) ([28114c4](https://github.com/feathersjs/feathers/commit/28114c495d6564868bb3ffbf619bf80b774dce4b)) +- Update Grant usage and other dependencies ([#2264](https://github.com/feathersjs/feathers/issues/2264)) ([7b0f8fa](https://github.com/feathersjs/feathers/commit/7b0f8fad252419ed0ad0bf259cdf3104d322ab60)) +- **socketio-client:** Fix client transport-commons reference ([#2164](https://github.com/feathersjs/feathers/issues/2164)) ([3a42c54](https://github.com/feathersjs/feathers/commit/3a42c544058456b19c7e21827226541bfa6ad621)) ### Features -* **core:** Public custom service methods ([#2270](https://github.com/feathersjs/feathers/issues/2270)) ([e65abfb](https://github.com/feathersjs/feathers/commit/e65abfb5388df6c19a11c565cf1076a29f32668d)) -* Application service types default to any ([#1566](https://github.com/feathersjs/feathers/issues/1566)) ([d93ba9a](https://github.com/feathersjs/feathers/commit/d93ba9a17edd20d3397bb00f4f6e82e804e42ed6)) -* Feathers v5 core refactoring and features ([#2255](https://github.com/feathersjs/feathers/issues/2255)) ([2dafb7c](https://github.com/feathersjs/feathers/commit/2dafb7ce14ba57406aeec13d10ca45b1e709bee9)) -* **transport-commons:** New built-in high performance radix router ([#2177](https://github.com/feathersjs/feathers/issues/2177)) ([6d18065](https://github.com/feathersjs/feathers/commit/6d180651b4eb40289ecea3df3575f207aa6c5d1f)) - - - - +- **core:** Public custom service methods ([#2270](https://github.com/feathersjs/feathers/issues/2270)) ([e65abfb](https://github.com/feathersjs/feathers/commit/e65abfb5388df6c19a11c565cf1076a29f32668d)) +- Application service types default to any ([#1566](https://github.com/feathersjs/feathers/issues/1566)) ([d93ba9a](https://github.com/feathersjs/feathers/commit/d93ba9a17edd20d3397bb00f4f6e82e804e42ed6)) +- Feathers v5 core refactoring and features ([#2255](https://github.com/feathersjs/feathers/issues/2255)) ([2dafb7c](https://github.com/feathersjs/feathers/commit/2dafb7ce14ba57406aeec13d10ca45b1e709bee9)) +- **transport-commons:** New built-in high performance radix router ([#2177](https://github.com/feathersjs/feathers/issues/2177)) ([6d18065](https://github.com/feathersjs/feathers/commit/6d180651b4eb40289ecea3df3575f207aa6c5d1f)) # [5.0.0-pre.1](https://github.com/feathersjs/feathers/compare/v4.5.11...v5.0.0-pre.1) (2020-12-17) - - # [5.0.0-pre.0](https://github.com/feathersjs/feathers/compare/v4.5.4...v5.0.0-pre.0) (2020-05-19) - ### Features -* **core:** use @feathers/hooks and add async type ([#1929](https://github.com/feathersjs/feathers/issues/1929)) ([a5c4756](https://github.com/feathersjs/feathers/commit/a5c47562eae8410c82fe2f6308f26f8e78b6a3e8)) -* **transport-commons:** Remove legacy message format and unnecessary client timeouts ([#1939](https://github.com/feathersjs/feathers/issues/1939)) ([5538881](https://github.com/feathersjs/feathers/commit/5538881a08bc130de42c5984055729d8336f8615)) - +- **core:** use @feathers/hooks and add async type ([#1929](https://github.com/feathersjs/feathers/issues/1929)) ([a5c4756](https://github.com/feathersjs/feathers/commit/a5c47562eae8410c82fe2f6308f26f8e78b6a3e8)) +- **transport-commons:** Remove legacy message format and unnecessary client timeouts ([#1939](https://github.com/feathersjs/feathers/issues/1939)) ([5538881](https://github.com/feathersjs/feathers/commit/5538881a08bc130de42c5984055729d8336f8615)) ### BREAKING CHANGES -* **transport-commons:** Removes the old message format and client service timeout - - - - +- **transport-commons:** Removes the old message format and client service timeout # [5.0.0-pre.0](https://github.com/feathersjs/feathers/compare/v4.5.4...v5.0.0-pre.0) (2020-05-19) - ### Features -* **core:** use @feathers/hooks and add async type ([#1929](https://github.com/feathersjs/feathers/issues/1929)) ([a5c4756](https://github.com/feathersjs/feathers/commit/a5c47562eae8410c82fe2f6308f26f8e78b6a3e8)) -* **transport-commons:** Remove legacy message format and unnecessary client timeouts ([#1939](https://github.com/feathersjs/feathers/issues/1939)) ([5538881](https://github.com/feathersjs/feathers/commit/5538881a08bc130de42c5984055729d8336f8615)) - +- **core:** use @feathers/hooks and add async type ([#1929](https://github.com/feathersjs/feathers/issues/1929)) ([a5c4756](https://github.com/feathersjs/feathers/commit/a5c47562eae8410c82fe2f6308f26f8e78b6a3e8)) +- **transport-commons:** Remove legacy message format and unnecessary client timeouts ([#1939](https://github.com/feathersjs/feathers/issues/1939)) ([5538881](https://github.com/feathersjs/feathers/commit/5538881a08bc130de42c5984055729d8336f8615)) ### BREAKING CHANGES -* **transport-commons:** Removes the old message format and client service timeout - - +- **transport-commons:** Removes the old message format and client service timeout ## [4.5.11](https://github.com/feathersjs/feathers/compare/v4.5.10...v4.5.11) (2020-12-05) - ### Bug Fixes -* **socketio-client:** Throw an error and show a warning if someone tries to use socket.io-client v3 ([#2135](https://github.com/feathersjs/feathers/issues/2135)) ([cc3521c](https://github.com/feathersjs/feathers/commit/cc3521c935a1cbd690e29b7057998e3898f282db)) - - - - +- **socketio-client:** Throw an error and show a warning if someone tries to use socket.io-client v3 ([#2135](https://github.com/feathersjs/feathers/issues/2135)) ([cc3521c](https://github.com/feathersjs/feathers/commit/cc3521c935a1cbd690e29b7057998e3898f282db)) ## [4.5.10](https://github.com/feathersjs/feathers/compare/v4.5.9...v4.5.10) (2020-11-08) **Note:** Version bump only for package @feathersjs/transport-commons - - - - ## [4.5.9](https://github.com/feathersjs/feathers/compare/v4.5.8...v4.5.9) (2020-10-09) **Note:** Version bump only for package @feathersjs/transport-commons - - - - ## [4.5.8](https://github.com/feathersjs/feathers/compare/v4.5.7...v4.5.8) (2020-08-12) **Note:** Version bump only for package @feathersjs/transport-commons - - - - ## [4.5.7](https://github.com/feathersjs/feathers/compare/v4.5.6...v4.5.7) (2020-07-24) **Note:** Version bump only for package @feathersjs/transport-commons - - - - ## [4.5.5](https://github.com/feathersjs/feathers/compare/v4.5.4...v4.5.5) (2020-07-11) **Note:** Version bump only for package @feathersjs/transport-commons - - - - ## [4.5.3](https://github.com/feathersjs/feathers/compare/v4.5.2...v4.5.3) (2020-04-17) **Note:** Version bump only for package @feathersjs/transport-commons - - - - ## [4.5.2](https://github.com/feathersjs/feathers/compare/v4.5.1...v4.5.2) (2020-03-04) **Note:** Version bump only for package @feathersjs/transport-commons - - - - ## [4.5.1](https://github.com/feathersjs/feathers/compare/v4.5.0...v4.5.1) (2020-01-24) **Note:** Version bump only for package @feathersjs/transport-commons - - - - # [4.5.0](https://github.com/feathersjs/feathers/compare/v4.4.3...v4.5.0) (2020-01-18) **Note:** Version bump only for package @feathersjs/transport-commons - - - - ## [4.4.3](https://github.com/feathersjs/feathers/compare/v4.4.1...v4.4.3) (2019-12-06) **Note:** Version bump only for package @feathersjs/transport-commons - - - - ## [4.4.1](https://github.com/feathersjs/feathers/compare/v4.4.0...v4.4.1) (2019-11-27) - ### Bug Fixes -* Gracefully handle errors in publishers ([#1710](https://github.com/feathersjs/feathers/issues/1710)) ([0616306](https://github.com/feathersjs/feathers/commit/061630696762e9dbf1dc4e738094992ba16989fc)) - - - - +- Gracefully handle errors in publishers ([#1710](https://github.com/feathersjs/feathers/issues/1710)) ([0616306](https://github.com/feathersjs/feathers/commit/061630696762e9dbf1dc4e738094992ba16989fc)) # [4.4.0](https://github.com/feathersjs/feathers/compare/v4.3.11...v4.4.0) (2019-11-27) - ### Bug Fixes -* **transport-commons:** Allow to properly chain SocketIo client.off ([#1706](https://github.com/feathersjs/feathers/issues/1706)) ([a4aecbc](https://github.com/feathersjs/feathers/commit/a4aecbcd3578c1cf4ecffb3a58fb6d26e15ee513)) - - - - +- **transport-commons:** Allow to properly chain SocketIo client.off ([#1706](https://github.com/feathersjs/feathers/issues/1706)) ([a4aecbc](https://github.com/feathersjs/feathers/commit/a4aecbcd3578c1cf4ecffb3a58fb6d26e15ee513)) ## [4.3.11](https://github.com/feathersjs/feathers/compare/v4.3.10...v4.3.11) (2019-11-11) **Note:** Version bump only for package @feathersjs/transport-commons - - - - ## [4.3.10](https://github.com/feathersjs/feathers/compare/v4.3.9...v4.3.10) (2019-10-26) **Note:** Version bump only for package @feathersjs/transport-commons - - - - ## [4.3.9](https://github.com/feathersjs/feathers/compare/v4.3.8...v4.3.9) (2019-10-26) **Note:** Version bump only for package @feathersjs/transport-commons - - - - ## [4.3.7](https://github.com/feathersjs/feathers/compare/v4.3.6...v4.3.7) (2019-10-14) **Note:** Version bump only for package @feathersjs/transport-commons - - - - ## [4.3.4](https://github.com/feathersjs/feathers/compare/v4.3.3...v4.3.4) (2019-10-03) **Note:** Version bump only for package @feathersjs/transport-commons - - - - ## [4.3.3](https://github.com/feathersjs/feathers/compare/v4.3.2...v4.3.3) (2019-09-21) **Note:** Version bump only for package @feathersjs/transport-commons - - - - ## [4.3.2](https://github.com/feathersjs/feathers/compare/v4.3.1...v4.3.2) (2019-09-16) **Note:** Version bump only for package @feathersjs/transport-commons - - - - ## [4.3.1](https://github.com/feathersjs/feathers/compare/v4.3.0...v4.3.1) (2019-09-09) - ### Bug Fixes -* Fix regression in transport commons ([#1551](https://github.com/feathersjs/feathers/issues/1551)) ([ed9e934](https://github.com/feathersjs/feathers/commit/ed9e934)) - - - - +- Fix regression in transport commons ([#1551](https://github.com/feathersjs/feathers/issues/1551)) ([ed9e934](https://github.com/feathersjs/feathers/commit/ed9e934)) # [4.3.0](https://github.com/feathersjs/feathers/compare/v4.3.0-pre.4...v4.3.0) (2019-08-27) **Note:** Version bump only for package @feathersjs/transport-commons - - - - # [4.3.0-pre.4](https://github.com/feathersjs/feathers/compare/v4.3.0-pre.3...v4.3.0-pre.4) (2019-08-22) **Note:** Version bump only for package @feathersjs/transport-commons - - - - # [4.3.0-pre.3](https://github.com/feathersjs/feathers/compare/v4.3.0-pre.2...v4.3.0-pre.3) (2019-08-19) - ### Bug Fixes -* Expire and remove authenticated real-time connections ([#1512](https://github.com/feathersjs/feathers/issues/1512)) ([2707c33](https://github.com/feathersjs/feathers/commit/2707c33)) -* Update all dependencies ([7d53a00](https://github.com/feathersjs/feathers/commit/7d53a00)) -* Use WeakMap to connect socket to connection ([#1509](https://github.com/feathersjs/feathers/issues/1509)) ([64807e3](https://github.com/feathersjs/feathers/commit/64807e3)) - - - - +- Expire and remove authenticated real-time connections ([#1512](https://github.com/feathersjs/feathers/issues/1512)) ([2707c33](https://github.com/feathersjs/feathers/commit/2707c33)) +- Update all dependencies ([7d53a00](https://github.com/feathersjs/feathers/commit/7d53a00)) +- Use WeakMap to connect socket to connection ([#1509](https://github.com/feathersjs/feathers/issues/1509)) ([64807e3](https://github.com/feathersjs/feathers/commit/64807e3)) # [4.3.0-pre.2](https://github.com/feathersjs/feathers/compare/v4.3.0-pre.1...v4.3.0-pre.2) (2019-08-02) - ### Bug Fixes -* Add getEntityId to JWT strategy and fix legacy Socket authentication ([#1488](https://github.com/feathersjs/feathers/issues/1488)) ([9a3b324](https://github.com/feathersjs/feathers/commit/9a3b324)) -* Improve Params typing ([#1474](https://github.com/feathersjs/feathers/issues/1474)) ([54a3aa7](https://github.com/feathersjs/feathers/commit/54a3aa7)) - - - - +- Add getEntityId to JWT strategy and fix legacy Socket authentication ([#1488](https://github.com/feathersjs/feathers/issues/1488)) ([9a3b324](https://github.com/feathersjs/feathers/commit/9a3b324)) +- Improve Params typing ([#1474](https://github.com/feathersjs/feathers/issues/1474)) ([54a3aa7](https://github.com/feathersjs/feathers/commit/54a3aa7)) # [4.3.0-pre.1](https://github.com/feathersjs/feathers/compare/v4.0.0-pre.5...v4.3.0-pre.1) (2019-07-11) **Note:** Version bump only for package @feathersjs/transport-commons - - - - # [4.0.0-pre.5](https://github.com/feathersjs/feathers/compare/v4.0.0-pre.4...v4.0.0-pre.5) (2019-07-10) **Note:** Version bump only for package @feathersjs/transport-commons - - - - # [4.0.0-pre.4](https://github.com/feathersjs/feathers/compare/v4.0.0-pre.3...v4.0.0-pre.4) (2019-07-05) - ### Bug Fixes -* Clean up hooks code ([#1407](https://github.com/feathersjs/feathers/issues/1407)) ([f25c88b](https://github.com/feathersjs/feathers/commit/f25c88b)) -* Improve transport-commons types ([#1396](https://github.com/feathersjs/feathers/issues/1396)) ([f9d8536](https://github.com/feathersjs/feathers/commit/f9d8536)) - - - - +- Clean up hooks code ([#1407](https://github.com/feathersjs/feathers/issues/1407)) ([f25c88b](https://github.com/feathersjs/feathers/commit/f25c88b)) +- Improve transport-commons types ([#1396](https://github.com/feathersjs/feathers/issues/1396)) ([f9d8536](https://github.com/feathersjs/feathers/commit/f9d8536)) # [4.0.0-pre.3](https://github.com/feathersjs/feathers/compare/v4.0.0-pre.2...v4.0.0-pre.3) (2019-06-01) - ### Bug Fixes -* Make oAuth paths more consistent and improve authentication client ([#1377](https://github.com/feathersjs/feathers/issues/1377)) ([adb2543](https://github.com/feathersjs/feathers/commit/adb2543)) -* Update dependencies and fix tests ([#1373](https://github.com/feathersjs/feathers/issues/1373)) ([d743a7f](https://github.com/feathersjs/feathers/commit/d743a7f)) - - - - +- Make oAuth paths more consistent and improve authentication client ([#1377](https://github.com/feathersjs/feathers/issues/1377)) ([adb2543](https://github.com/feathersjs/feathers/commit/adb2543)) +- Update dependencies and fix tests ([#1373](https://github.com/feathersjs/feathers/issues/1373)) ([d743a7f](https://github.com/feathersjs/feathers/commit/d743a7f)) # [4.0.0-pre.2](https://github.com/feathersjs/feathers/compare/v4.0.0-pre.1...v4.0.0-pre.2) (2019-05-15) - ### Bug Fixes -* Add fallback for legacy socket authenticate event ([#1356](https://github.com/feathersjs/feathers/issues/1356)) ([61b1056](https://github.com/feathersjs/feathers/commit/61b1056)) -* Throw NotAuthenticated on token verification errors ([#1357](https://github.com/feathersjs/feathers/issues/1357)) ([e0120df](https://github.com/feathersjs/feathers/commit/e0120df)) - +- Add fallback for legacy socket authenticate event ([#1356](https://github.com/feathersjs/feathers/issues/1356)) ([61b1056](https://github.com/feathersjs/feathers/commit/61b1056)) +- Throw NotAuthenticated on token verification errors ([#1357](https://github.com/feathersjs/feathers/issues/1357)) ([e0120df](https://github.com/feathersjs/feathers/commit/e0120df)) ### Features -* Add global disconnect event ([#1355](https://github.com/feathersjs/feathers/issues/1355)) ([85afcca](https://github.com/feathersjs/feathers/commit/85afcca)) - - - - +- Add global disconnect event ([#1355](https://github.com/feathersjs/feathers/issues/1355)) ([85afcca](https://github.com/feathersjs/feathers/commit/85afcca)) # [4.0.0-pre.1](https://github.com/feathersjs/feathers/compare/v4.0.0-pre.0...v4.0.0-pre.1) (2019-05-08) - ### Bug Fixes -* Add registerPublisher alias for .publish ([#1302](https://github.com/feathersjs/feathers/issues/1302)) ([98fe8f8](https://github.com/feathersjs/feathers/commit/98fe8f8)) - - - - +- Add registerPublisher alias for .publish ([#1302](https://github.com/feathersjs/feathers/issues/1302)) ([98fe8f8](https://github.com/feathersjs/feathers/commit/98fe8f8)) # [4.0.0-pre.0](https://github.com/feathersjs/feathers/compare/v3.2.0-pre.1...v4.0.0-pre.0) (2019-04-21) - ### Bug Fixes -* Compare socket event data using lodash's isEqual instead of indexOf ([#1061](https://github.com/feathersjs/feathers/issues/1061)) ([f706db3](https://github.com/feathersjs/feathers/commit/f706db3)) -* Make Mocha a proper devDependency for every repository ([#1053](https://github.com/feathersjs/feathers/issues/1053)) ([9974803](https://github.com/feathersjs/feathers/commit/9974803)) -* Update adapter common tests ([#1135](https://github.com/feathersjs/feathers/issues/1135)) ([8166dda](https://github.com/feathersjs/feathers/commit/8166dda)) -* Update all dependencies to latest ([#1206](https://github.com/feathersjs/feathers/issues/1206)) ([e51e0f6](https://github.com/feathersjs/feathers/commit/e51e0f6)) -* **package:** update debug to version 3.0.0 ([#45](https://github.com/feathersjs/feathers/issues/45)) ([9b9bde5](https://github.com/feathersjs/feathers/commit/9b9bde5)) - +- Compare socket event data using lodash's isEqual instead of indexOf ([#1061](https://github.com/feathersjs/feathers/issues/1061)) ([f706db3](https://github.com/feathersjs/feathers/commit/f706db3)) +- Make Mocha a proper devDependency for every repository ([#1053](https://github.com/feathersjs/feathers/issues/1053)) ([9974803](https://github.com/feathersjs/feathers/commit/9974803)) +- Update adapter common tests ([#1135](https://github.com/feathersjs/feathers/issues/1135)) ([8166dda](https://github.com/feathersjs/feathers/commit/8166dda)) +- Update all dependencies to latest ([#1206](https://github.com/feathersjs/feathers/issues/1206)) ([e51e0f6](https://github.com/feathersjs/feathers/commit/e51e0f6)) +- **package:** update debug to version 3.0.0 ([#45](https://github.com/feathersjs/feathers/issues/45)) ([9b9bde5](https://github.com/feathersjs/feathers/commit/9b9bde5)) ### Features -* Add TypeScript definitions ([#1275](https://github.com/feathersjs/feathers/issues/1275)) ([9dd6713](https://github.com/feathersjs/feathers/commit/9dd6713)) -* Allow registering a service at the root level ([#1115](https://github.com/feathersjs/feathers/issues/1115)) ([c73d322](https://github.com/feathersjs/feathers/commit/c73d322)) - - - - +- Add TypeScript definitions ([#1275](https://github.com/feathersjs/feathers/issues/1275)) ([9dd6713](https://github.com/feathersjs/feathers/commit/9dd6713)) +- Allow registering a service at the root level ([#1115](https://github.com/feathersjs/feathers/issues/1115)) ([c73d322](https://github.com/feathersjs/feathers/commit/c73d322)) ## [4.2.1](https://github.com/feathersjs/feathers/compare/@feathersjs/transport-commons@4.2.0...@feathersjs/transport-commons@4.2.1) (2019-01-02) - ### Bug Fixes -* Update adapter common tests ([#1135](https://github.com/feathersjs/feathers/issues/1135)) ([8166dda](https://github.com/feathersjs/feathers/commit/8166dda)) - - - - +- Update adapter common tests ([#1135](https://github.com/feathersjs/feathers/issues/1135)) ([8166dda](https://github.com/feathersjs/feathers/commit/8166dda)) -# [4.2.0](https://github.com/feathersjs/feathers/compare/@feathersjs/transport-commons@4.1.6...@feathersjs/transport-commons@4.2.0) (2018-12-16) +# [4.2.0](https://github.com/feathersjs/feathers/compare/@feathersjs/transport-commons@4.1.6...@feathersjs/transport-commons@4.2.0) (2018-12-16) ### Features -* Allow registering a service at the root level ([#1115](https://github.com/feathersjs/feathers/issues/1115)) ([c73d322](https://github.com/feathersjs/feathers/commit/c73d322)) - - - - +- Allow registering a service at the root level ([#1115](https://github.com/feathersjs/feathers/issues/1115)) ([c73d322](https://github.com/feathersjs/feathers/commit/c73d322)) -## [4.1.6](https://github.com/feathersjs/feathers/compare/@feathersjs/transport-commons@4.1.5...@feathersjs/transport-commons@4.1.6) (2018-10-25) +## [4.1.6](https://github.com/feathersjs/feathers/compare/@feathersjs/transport-commons@4.1.5...@feathersjs/transport-commons@4.1.6) (2018-10-25) ### Bug Fixes -* Compare socket event data using lodash's isEqual instead of indexOf ([#1061](https://github.com/feathersjs/feathers/issues/1061)) ([f706db3](https://github.com/feathersjs/feathers/commit/f706db3)) -* Make Mocha a proper devDependency for every repository ([#1053](https://github.com/feathersjs/feathers/issues/1053)) ([9974803](https://github.com/feathersjs/feathers/commit/9974803)) - - - - +- Compare socket event data using lodash's isEqual instead of indexOf ([#1061](https://github.com/feathersjs/feathers/issues/1061)) ([f706db3](https://github.com/feathersjs/feathers/commit/f706db3)) +- Make Mocha a proper devDependency for every repository ([#1053](https://github.com/feathersjs/feathers/issues/1053)) ([9974803](https://github.com/feathersjs/feathers/commit/9974803)) + ## [4.1.5](https://github.com/feathersjs/feathers/compare/@feathersjs/transport-commons@4.1.4...@feathersjs/transport-commons@4.1.5) (2018-09-21) **Note:** Version bump only for package @feathersjs/transport-commons - - - - + ## [4.1.4](https://github.com/feathersjs/feathers/compare/@feathersjs/transport-commons@4.1.3...@feathersjs/transport-commons@4.1.4) (2018-09-17) **Note:** Version bump only for package @feathersjs/transport-commons - - - - + ## [4.1.3](https://github.com/feathersjs/feathers/compare/@feathersjs/transport-commons@4.1.2...@feathersjs/transport-commons@4.1.3) (2018-09-02) **Note:** Version bump only for package @feathersjs/transport-commons + ## 4.1.2 - Migrate to Monorepo ([feathers#462](https://github.com/feathersjs/feathers/issues/462)) ## [v4.1.1](https://github.com/feathersjs/transport-commons/tree/v4.1.1) (2018-07-03) + [Full Changelog](https://github.com/feathersjs/transport-commons/compare/v4.1.0...v4.1.1) **Merged pull requests:** @@ -601,6 +430,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Properly dispatch arrays that do not come from Feathers hook events [\#77](https://github.com/feathersjs/transport-commons/pull/77) ([daffl](https://github.com/daffl)) ## [v4.1.0](https://github.com/feathersjs/transport-commons/tree/v4.1.0) (2018-06-28) + [Full Changelog](https://github.com/feathersjs/transport-commons/compare/v4.0.2...v4.1.0) **Merged pull requests:** @@ -608,6 +438,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Remove empty channels [\#75](https://github.com/feathersjs/transport-commons/pull/75) ([daffl](https://github.com/daffl)) ## [v4.0.2](https://github.com/feathersjs/transport-commons/tree/v4.0.2) (2018-06-12) + [Full Changelog](https://github.com/feathersjs/transport-commons/compare/v4.0.1...v4.0.2) **Merged pull requests:** @@ -615,6 +446,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Fix looking up invalid path names through sockets [\#76](https://github.com/feathersjs/transport-commons/pull/76) ([daffl](https://github.com/daffl)) ## [v4.0.1](https://github.com/feathersjs/transport-commons/tree/v4.0.1) (2018-05-30) + [Full Changelog](https://github.com/feathersjs/transport-commons/compare/v4.0.0...v4.0.1) **Merged pull requests:** @@ -622,6 +454,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Update Codeclimate settings [\#74](https://github.com/feathersjs/transport-commons/pull/74) ([daffl](https://github.com/daffl)) ## [v4.0.0](https://github.com/feathersjs/transport-commons/tree/v4.0.0) (2018-02-09) + [Full Changelog](https://github.com/feathersjs/transport-commons/compare/v3.2.0...v4.0.0) **Closed issues:** @@ -635,6 +468,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Move socket handling into its own file [\#70](https://github.com/feathersjs/transport-commons/pull/70) ([daffl](https://github.com/daffl)) ## [v3.2.0](https://github.com/feathersjs/transport-commons/tree/v3.2.0) (2018-01-30) + [Full Changelog](https://github.com/feathersjs/transport-commons/compare/v3.1.5...v3.2.0) **Closed issues:** @@ -650,9 +484,11 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Update semistandard to the latest version 🚀 [\#63](https://github.com/feathersjs/transport-commons/pull/63) ([greenkeeper[bot]](https://github.com/apps/greenkeeper)) ## [v3.1.5](https://github.com/feathersjs/transport-commons/tree/v3.1.5) (2017-12-12) + [Full Changelog](https://github.com/feathersjs/transport-commons/compare/v3.1.4...v3.1.5) ## [v3.1.4](https://github.com/feathersjs/transport-commons/tree/v3.1.4) (2017-12-12) + [Full Changelog](https://github.com/feathersjs/transport-commons/compare/v3.1.3...v3.1.4) **Merged pull requests:** @@ -660,6 +496,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Fix dispatching of arrays [\#62](https://github.com/feathersjs/transport-commons/pull/62) ([daffl](https://github.com/daffl)) ## [v3.1.3](https://github.com/feathersjs/transport-commons/tree/v3.1.3) (2017-12-12) + [Full Changelog](https://github.com/feathersjs/transport-commons/compare/v3.1.2...v3.1.3) **Merged pull requests:** @@ -667,6 +504,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Make sure that each entry in an array is dispatched as its own even [\#61](https://github.com/feathersjs/transport-commons/pull/61) ([daffl](https://github.com/daffl)) ## [v3.1.2](https://github.com/feathersjs/transport-commons/tree/v3.1.2) (2017-12-06) + [Full Changelog](https://github.com/feathersjs/transport-commons/compare/v3.1.1...v3.1.2) **Merged pull requests:** @@ -674,6 +512,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Fix another error when there are no results [\#60](https://github.com/feathersjs/transport-commons/pull/60) ([daffl](https://github.com/daffl)) ## [v3.1.1](https://github.com/feathersjs/transport-commons/tree/v3.1.1) (2017-12-06) + [Full Changelog](https://github.com/feathersjs/transport-commons/compare/v3.1.0...v3.1.1) **Merged pull requests:** @@ -681,6 +520,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Always use a combined channel [\#59](https://github.com/feathersjs/transport-commons/pull/59) ([daffl](https://github.com/daffl)) ## [v3.1.0](https://github.com/feathersjs/transport-commons/tree/v3.1.0) (2017-12-06) + [Full Changelog](https://github.com/feathersjs/transport-commons/compare/v3.0.1...v3.1.0) **Merged pull requests:** @@ -688,6 +528,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Give channel dispatchers a precedence [\#58](https://github.com/feathersjs/transport-commons/pull/58) ([daffl](https://github.com/daffl)) ## [v3.0.1](https://github.com/feathersjs/transport-commons/tree/v3.0.1) (2017-11-03) + [Full Changelog](https://github.com/feathersjs/transport-commons/compare/v3.0.0...v3.0.1) **Closed issues:** @@ -699,9 +540,11 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Allow socket calls without query and callback [\#55](https://github.com/feathersjs/transport-commons/pull/55) ([daffl](https://github.com/daffl)) ## [v3.0.0](https://github.com/feathersjs/transport-commons/tree/v3.0.0) (2017-11-01) + [Full Changelog](https://github.com/feathersjs/transport-commons/compare/v3.0.0-pre.7...v3.0.0) ## [v3.0.0-pre.7](https://github.com/feathersjs/transport-commons/tree/v3.0.0-pre.7) (2017-10-25) + [Full Changelog](https://github.com/feathersjs/transport-commons/compare/v3.0.0-pre.6...v3.0.0-pre.7) **Merged pull requests:** @@ -709,6 +552,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Update to better returnHook handling [\#53](https://github.com/feathersjs/transport-commons/pull/53) ([daffl](https://github.com/daffl)) ## [v3.0.0-pre.6](https://github.com/feathersjs/transport-commons/tree/v3.0.0-pre.6) (2017-10-21) + [Full Changelog](https://github.com/feathersjs/transport-commons/compare/v3.0.0-pre.5...v3.0.0-pre.6) **Closed issues:** @@ -722,6 +566,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Rename repository and use npm scope [\#51](https://github.com/feathersjs/transport-commons/pull/51) ([daffl](https://github.com/daffl)) ## [v3.0.0-pre.5](https://github.com/feathersjs/transport-commons/tree/v3.0.0-pre.5) (2017-10-18) + [Full Changelog](https://github.com/feathersjs/transport-commons/compare/v3.0.0-pre.4...v3.0.0-pre.5) **Merged pull requests:** @@ -729,6 +574,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Pass events property to the client [\#50](https://github.com/feathersjs/transport-commons/pull/50) ([daffl](https://github.com/daffl)) ## [v3.0.0-pre.4](https://github.com/feathersjs/transport-commons/tree/v3.0.0-pre.4) (2017-10-17) + [Full Changelog](https://github.com/feathersjs/transport-commons/compare/v3.0.0-pre.3...v3.0.0-pre.4) **Merged pull requests:** @@ -736,6 +582,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Fix the event name and add some channel debug statements [\#49](https://github.com/feathersjs/transport-commons/pull/49) ([daffl](https://github.com/daffl)) ## [v3.0.0-pre.3](https://github.com/feathersjs/transport-commons/tree/v3.0.0-pre.3) (2017-10-16) + [Full Changelog](https://github.com/feathersjs/transport-commons/compare/v3.0.0-pre.2...v3.0.0-pre.3) **Merged pull requests:** @@ -743,6 +590,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Update mocha to the latest version 🚀 [\#48](https://github.com/feathersjs/transport-commons/pull/48) ([greenkeeper[bot]](https://github.com/apps/greenkeeper)) ## [v3.0.0-pre.2](https://github.com/feathersjs/transport-commons/tree/v3.0.0-pre.2) (2017-09-28) + [Full Changelog](https://github.com/feathersjs/transport-commons/compare/v3.0.0-pre.1...v3.0.0-pre.2) **Merged pull requests:** @@ -750,6 +598,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Add feathers-channels [\#47](https://github.com/feathersjs/transport-commons/pull/47) ([daffl](https://github.com/daffl)) ## [v3.0.0-pre.1](https://github.com/feathersjs/transport-commons/tree/v3.0.0-pre.1) (2017-09-08) + [Full Changelog](https://github.com/feathersjs/transport-commons/compare/v2.4.0...v3.0.0-pre.1) **Fixed bugs:** @@ -769,6 +618,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Update dependencies to enable Greenkeeper 🌴 [\#41](https://github.com/feathersjs/transport-commons/pull/41) ([greenkeeper[bot]](https://github.com/apps/greenkeeper)) ## [v2.4.0](https://github.com/feathersjs/transport-commons/tree/v2.4.0) (2017-01-07) + [Full Changelog](https://github.com/feathersjs/transport-commons/compare/v2.3.1...v2.4.0) **Implemented enhancements:** @@ -790,6 +640,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Code coverage [\#29](https://github.com/feathersjs/transport-commons/pull/29) ([ekryski](https://github.com/ekryski)) ## [v2.3.1](https://github.com/feathersjs/transport-commons/tree/v2.3.1) (2016-09-02) + [Full Changelog](https://github.com/feathersjs/transport-commons/compare/v2.3.0...v2.3.1) **Merged pull requests:** @@ -798,6 +649,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Update mocha to version 3.0.0 🚀 [\#25](https://github.com/feathersjs/transport-commons/pull/25) ([greenkeeperio-bot](https://github.com/greenkeeperio-bot)) ## [v2.3.0](https://github.com/feathersjs/transport-commons/tree/v2.3.0) (2016-07-24) + [Full Changelog](https://github.com/feathersjs/transport-commons/compare/v2.2.1...v2.3.0) **Fixed bugs:** @@ -809,9 +661,11 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Skip subsequent filters instead of rejecting the promise [\#24](https://github.com/feathersjs/transport-commons/pull/24) ([daffl](https://github.com/daffl)) ## [v2.2.1](https://github.com/feathersjs/transport-commons/tree/v2.2.1) (2016-07-05) + [Full Changelog](https://github.com/feathersjs/transport-commons/compare/v2.2.0...v2.2.1) ## [v2.2.0](https://github.com/feathersjs/transport-commons/tree/v2.2.0) (2016-07-05) + [Full Changelog](https://github.com/feathersjs/transport-commons/compare/v2.1.0...v2.2.0) **Implemented enhancements:** @@ -832,6 +686,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Pass all EventEmitter methods to the client connection [\#23](https://github.com/feathersjs/transport-commons/pull/23) ([daffl](https://github.com/daffl)) ## [v2.1.0](https://github.com/feathersjs/transport-commons/tree/v2.1.0) (2016-05-29) + [Full Changelog](https://github.com/feathersjs/transport-commons/compare/v2.0.0...v2.1.0) **Closed issues:** @@ -843,6 +698,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Make client convert to feathers-errors [\#20](https://github.com/feathersjs/transport-commons/pull/20) ([daffl](https://github.com/daffl)) ## [v2.0.0](https://github.com/feathersjs/transport-commons/tree/v2.0.0) (2016-05-23) + [Full Changelog](https://github.com/feathersjs/transport-commons/compare/v1.0.0...v2.0.0) **Merged pull requests:** @@ -852,6 +708,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - babel-polyfill@6.7.4 breaks build 🚨 [\#16](https://github.com/feathersjs/transport-commons/pull/16) ([greenkeeperio-bot](https://github.com/greenkeeperio-bot)) ## [v1.0.0](https://github.com/feathersjs/transport-commons/tree/v1.0.0) (2016-04-28) + [Full Changelog](https://github.com/feathersjs/transport-commons/compare/v0.2.3...v1.0.0) **Implemented enhancements:** @@ -869,6 +726,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Convert errors in socket callbacks [\#14](https://github.com/feathersjs/transport-commons/pull/14) ([daffl](https://github.com/daffl)) ## [v0.2.3](https://github.com/feathersjs/transport-commons/tree/v0.2.3) (2016-04-16) + [Full Changelog](https://github.com/feathersjs/transport-commons/compare/v0.2.2...v0.2.3) **Merged pull requests:** @@ -876,6 +734,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Remove connection setMaxListeners [\#11](https://github.com/feathersjs/transport-commons/pull/11) ([daffl](https://github.com/daffl)) ## [v0.2.2](https://github.com/feathersjs/transport-commons/tree/v0.2.2) (2016-03-22) + [Full Changelog](https://github.com/feathersjs/transport-commons/compare/v0.2.1...v0.2.2) **Merged pull requests:** @@ -883,6 +742,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Allow chaining event listeners. [\#6](https://github.com/feathersjs/transport-commons/pull/6) ([joshuajabbour](https://github.com/joshuajabbour)) ## [v0.2.1](https://github.com/feathersjs/transport-commons/tree/v0.2.1) (2016-03-08) + [Full Changelog](https://github.com/feathersjs/transport-commons/compare/v0.2.0...v0.2.1) **Merged pull requests:** @@ -890,6 +750,7 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline - Set connection max listeners and better debug messages [\#3](https://github.com/feathersjs/transport-commons/pull/3) ([daffl](https://github.com/daffl)) ## [v0.2.0](https://github.com/feathersjs/transport-commons/tree/v0.2.0) (2016-02-08) + [Full Changelog](https://github.com/feathersjs/transport-commons/compare/v0.1.0...v0.2.0) **Merged pull requests:** @@ -899,5 +760,4 @@ See [Conventional Commits](https://conventionalcommits.org) for commit guideline ## [v0.1.0](https://github.com/feathersjs/transport-commons/tree/v0.1.0) (2016-01-21) - -\* *This Change Log was automatically generated by [github_changelog_generator](https://github.com/skywinder/Github-Changelog-Generator)* +\* _This Change Log was automatically generated by [github_changelog_generator](https://github.com/skywinder/Github-Changelog-Generator)_ diff --git a/packages/transport-commons/LICENSE b/packages/transport-commons/LICENSE index 3f395cc665..59604f46f3 100644 --- a/packages/transport-commons/LICENSE +++ b/packages/transport-commons/LICENSE @@ -1,6 +1,6 @@ The MIT License (MIT) -Copyright (c) 2021 Feathers +Copyright (c) 2022 Feathers Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated documentation files (the "Software"), to deal diff --git a/packages/transport-commons/README.md b/packages/transport-commons/README.md index e59f88e3b5..32136c6f8a 100644 --- a/packages/transport-commons/README.md +++ b/packages/transport-commons/README.md @@ -1,13 +1,13 @@ # @feathersjs/transport-commons [![CI](https://github.com/feathersjs/feathers/workflows/CI/badge.svg)](https://github.com/feathersjs/feathers/actions?query=workflow%3ACI) -[![Dependency Status](https://img.shields.io/david/feathersjs/feathers.svg?style=flat-square&path=packages/transport-commons)](https://david-dm.org/feathersjs/feathers?path=packages/transport-commons) [![Download Status](https://img.shields.io/npm/dm/@feathersjs/transport-commons.svg?style=flat-square)](https://www.npmjs.com/package/@feathersjs/transport-commons) +[![Discord](https://badgen.net/badge/icon/discord?icon=discord&label)](https://discord.gg/qa8kez8QBx) > Shared functionality for Feathers API transports like `@feathers/socketio` and `@feathersjs/primus`. Only intended to be used internally. ## License -Copyright (c) 2021 [Feathers contributors](https://github.com/feathersjs/feathers/graphs/contributors) +Copyright (c) 2022 [Feathers contributors](https://github.com/feathersjs/feathers/graphs/contributors) Licensed under the [MIT license](LICENSE). diff --git a/packages/transport-commons/client.d.ts b/packages/transport-commons/client.d.ts index 681bd0a98b..ee328040cf 100644 --- a/packages/transport-commons/client.d.ts +++ b/packages/transport-commons/client.d.ts @@ -1 +1 @@ -export * from './lib/client'; \ No newline at end of file +export * from './lib/client' diff --git a/packages/transport-commons/package.json b/packages/transport-commons/package.json index c6ca4bd913..9580e0bf58 100644 --- a/packages/transport-commons/package.json +++ b/packages/transport-commons/package.json @@ -1,7 +1,7 @@ { "name": "@feathersjs/transport-commons", "description": "Shared functionality for websocket providers", - "version": "5.0.0-pre.16", + "version": "5.0.0-pre.31", "homepage": "https://feathersjs.com", "main": "lib/", "types": "lib/", @@ -16,7 +16,8 @@ }, "repository": { "type": "git", - "url": "git://github.com/feathersjs/feathers.git" + "url": "git://github.com/feathersjs/feathers.git", + "directory": "packages/transport-commons" }, "author": { "name": "Feathers contributors", @@ -32,8 +33,9 @@ }, "scripts": { "prepublish": "npm run compile", - "compile": "shx rm -rf lib/ && tsc", - "test": "npm run compile && npm run mocha", + "pack": "npm pack --pack-destination ../cli/test/build", + "compile": "shx rm -rf lib/ && tsc && npm run pack", + "test": "npm run mocha", "mocha": "mocha --config ../../.mocharc.json --recursive test/**.test.ts test/**/*.test.ts" }, "directories": { @@ -52,19 +54,21 @@ "*.js" ], "dependencies": { - "@feathersjs/commons": "^5.0.0-pre.16", - "@feathersjs/errors": "^5.0.0-pre.16", - "@feathersjs/feathers": "^5.0.0-pre.16", + "@feathersjs/commons": "^5.0.0-pre.31", + "@feathersjs/errors": "^5.0.0-pre.31", + "@feathersjs/feathers": "^5.0.0-pre.31", + "encodeurl": "^1.0.2", "lodash": "^4.17.21" }, "devDependencies": { - "@types/lodash": "^4.14.178", - "@types/mocha": "^9.0.0", - "@types/node": "^17.0.5", - "mocha": "^9.1.3", - "shx": "^0.3.3", - "ts-node": "^10.4.0", - "typescript": "^4.5.4" + "@types/encodeurl": "^1.0.0", + "@types/lodash": "^4.14.186", + "@types/mocha": "^10.0.0", + "@types/node": "^18.8.2", + "mocha": "^10.0.0", + "shx": "^0.3.4", + "ts-node": "^10.9.1", + "typescript": "^4.8.4" }, - "gitHead": "f0cd227a82d159b528193bd33747c97684a48773" + "gitHead": "4500dbeb8cea566678cf88b3313a88efd93a2ed9" } diff --git a/packages/transport-commons/src/channels/channel/base.ts b/packages/transport-commons/src/channels/channel/base.ts index 464eae9caa..b64e50ffa2 100644 --- a/packages/transport-commons/src/channels/channel/base.ts +++ b/packages/transport-commons/src/channels/channel/base.ts @@ -1,61 +1,61 @@ -import { EventEmitter } from 'events'; +import { EventEmitter } from 'events' export interface RealTimeConnection { - [key: string]: any; + [key: string]: any } export class Channel extends EventEmitter { - connections: RealTimeConnection[]; - data: any; + connections: RealTimeConnection[] + data: any - constructor (connections: RealTimeConnection[] = [], data: any = null) { - super(); + constructor(connections: RealTimeConnection[] = [], data: any = null) { + super() - this.connections = connections; - this.data = data; + this.connections = connections + this.data = data } - get length () { - return this.connections.length; + get length() { + return this.connections.length } - leave (...connections: RealTimeConnection[]) { - connections.forEach(current => { + leave(...connections: RealTimeConnection[]) { + connections.forEach((current) => { if (typeof current === 'function') { - const callback = current as (connection: RealTimeConnection) => boolean; + const callback = current as (connection: RealTimeConnection) => boolean - this.leave(...this.connections.filter(callback)); + this.leave(...this.connections.filter(callback)) } else { - const index = this.connections.indexOf(current); + const index = this.connections.indexOf(current) if (index !== -1) { - this.connections.splice(index, 1); + this.connections.splice(index, 1) } } - }); + }) if (this.length === 0) { - this.emit('empty'); + this.emit('empty') } - return this; + return this } - join (...connections: RealTimeConnection[]) { - connections.forEach(connection => { + join(...connections: RealTimeConnection[]) { + connections.forEach((connection) => { if (connection && this.connections.indexOf(connection) === -1) { - this.connections.push(connection); + this.connections.push(connection) } - }); + }) - return this; + return this } - filter (fn: (connection: RealTimeConnection) => boolean) { - return new Channel(this.connections.filter(fn), this.data); + filter(fn: (connection: RealTimeConnection) => boolean) { + return new Channel(this.connections.filter(fn), this.data) } - send (data: any) { - return new Channel(this.connections, data); + send(data: any) { + return new Channel(this.connections, data) } } diff --git a/packages/transport-commons/src/channels/channel/combined.ts b/packages/transport-commons/src/channels/channel/combined.ts index 840f0a1fc9..c92f4cf85a 100644 --- a/packages/transport-commons/src/channels/channel/combined.ts +++ b/packages/transport-commons/src/channels/channel/combined.ts @@ -1,56 +1,56 @@ -import { Channel, RealTimeConnection } from './base'; +import { Channel, RealTimeConnection } from './base' -function collectConnections (children: Channel[]) { - const mappings = new WeakMap(); - const connections: RealTimeConnection[] = []; +function collectConnections(children: Channel[]) { + const mappings = new WeakMap() + const connections: RealTimeConnection[] = [] - children.forEach(channel => { - channel.connections.forEach(connection => { + children.forEach((channel) => { + channel.connections.forEach((connection) => { if (!mappings.has(connection)) { - connections.push(connection); - mappings.set(connection, channel.data); + connections.push(connection) + mappings.set(connection, channel.data) } - }); - }); + }) + }) - return { connections, mappings }; + return { connections, mappings } } export class CombinedChannel extends Channel { - children: Channel[]; - mappings: WeakMap; + children: Channel[] + mappings: WeakMap - constructor (children: Channel[], data: any = null) { - const { mappings, connections } = collectConnections(children); + constructor(children: Channel[], data: any = null) { + const { mappings, connections } = collectConnections(children) - super(connections, data); + super(connections, data) - this.children = children; - this.mappings = mappings; + this.children = children + this.mappings = mappings } - refresh () { - const collected = collectConnections(this.children); + refresh() { + const collected = collectConnections(this.children) - return Object.assign(this, collected); + return Object.assign(this, collected) } - leave (...connections: RealTimeConnection[]) { - return this.callChildren('leave', connections); + leave(...connections: RealTimeConnection[]) { + return this.callChildren('leave', connections) } - join (...connections: RealTimeConnection[]) { - return this.callChildren('join', connections); + join(...connections: RealTimeConnection[]) { + return this.callChildren('join', connections) } - dataFor (connection: RealTimeConnection) { - return this.mappings.get(connection); + dataFor(connection: RealTimeConnection) { + return this.mappings.get(connection) } - private callChildren (method: string, connections: RealTimeConnection[]) { - this.children.forEach((child: any) => child[method](...connections)); - this.refresh(); + private callChildren(method: string, connections: RealTimeConnection[]) { + this.children.forEach((child: any) => child[method](...connections)) + this.refresh() - return this; + return this } } diff --git a/packages/transport-commons/src/channels/index.ts b/packages/transport-commons/src/channels/index.ts index c8c5ca3a3b..1f443fd520 100644 --- a/packages/transport-commons/src/channels/index.ts +++ b/packages/transport-commons/src/channels/index.ts @@ -1,80 +1,83 @@ -import { Application, FeathersService, getServiceOptions } from '@feathersjs/feathers'; -import { createDebug } from '@feathersjs/commons'; -import { compact, flattenDeep, noop } from 'lodash'; -import { Channel, RealTimeConnection } from './channel/base'; -import { CombinedChannel } from './channel/combined'; -import { channelMixin, publishMixin, keys, PublishMixin, Event, Publisher } from './mixins'; -import EventEmitter from 'events'; +import { Application, FeathersService, getServiceOptions } from '@feathersjs/feathers' +import { createDebug } from '@feathersjs/commons' +import { compact, flattenDeep, noop } from 'lodash' +import { Channel, RealTimeConnection } from './channel/base' +import { CombinedChannel } from './channel/combined' +import { channelMixin, publishMixin, keys, PublishMixin, Event, Publisher } from './mixins' +import EventEmitter from 'events' -const debug = createDebug('@feathersjs/transport-commons/channels'); -const { CHANNELS } = keys; +const debug = createDebug('@feathersjs/transport-commons/channels') +const { CHANNELS } = keys declare module '@feathersjs/feathers/lib/declarations' { - interface ServiceAddons extends EventEmitter { // eslint-disable-line - publish (publisher: Publisher, A, this>): this; - publish (event: Event, publisher: Publisher, A, this>): this; + interface ServiceAddons extends EventEmitter { + // eslint-disable-line + publish(publisher: Publisher, A, this>): this + publish(event: Event, publisher: Publisher, A, this>): this - registerPublisher (publisher: Publisher, A, this>): this; - registerPublisher (event: Event, publisher: Publisher, A, this>): this; + registerPublisher(publisher: Publisher, A, this>): this + registerPublisher(event: Event, publisher: Publisher, A, this>): this } - interface Application { // eslint-disable-line - channels: string[]; + // eslint-disable-next-line @typescript-eslint/no-unused-vars + interface Application { + // eslint-disable-line + channels: string[] - channel (name: string | string[]): Channel; - channel (...names: string[]): Channel; + channel(name: string | string[]): Channel + channel(...names: string[]): Channel - publish (publisher: Publisher): this; - publish (event: Event, publisher: Publisher): this; + publish(publisher: Publisher): this + publish(event: Event, publisher: Publisher): this - registerPublisher (publisher: Publisher): this; - registerPublisher (event: Event, publisher: Publisher): this; + registerPublisher(publisher: Publisher): this + registerPublisher(event: Event, publisher: Publisher): this } interface Params { - connection?: RealTimeConnection; + connection?: RealTimeConnection } } -export { keys }; +export { keys } -export function channels () { +export function channels() { return (app: Application) => { if (typeof app.channel === 'function' && typeof app.publish === 'function') { - return; + return } - Object.assign(app, channelMixin(), publishMixin()); + Object.assign(app, channelMixin(), publishMixin()) Object.defineProperty(app, 'channels', { - get () { - return Object.keys(this[CHANNELS]); + get() { + return Object.keys(this[CHANNELS]) } - }); + }) app.mixins.push((service: FeathersService, path: string) => { - const { serviceEvents } = getServiceOptions(service); + const { serviceEvents } = getServiceOptions(service) if (typeof service.publish === 'function') { - return; + return } - Object.assign(service, publishMixin()); + Object.assign(service, publishMixin()) serviceEvents.forEach((event: string) => { service.on(event, function (data, hook) { if (!hook) { // Fake hook for custom events - hook = { path, service, app, result: data }; + hook = { path, service, app, result: data } } - debug('Publishing event', event, hook.path); + debug('Publishing event', event, hook.path) - const logError = (error: any) => debug(`Error in '${hook.path} ${event}' publisher`, error); - const servicePublishers = (service as unknown as PublishMixin)[keys.PUBLISHERS]; - const appPublishers = (app as unknown as PublishMixin)[keys.PUBLISHERS]; + const logError = (error: any) => debug(`Error in '${hook.path} ${event}' publisher`, error) + const servicePublishers = (service as unknown as PublishMixin)[keys.PUBLISHERS] + const appPublishers = (app as unknown as PublishMixin)[keys.PUBLISHERS] // This will return the first publisher list that is not empty // In the following precedence - const publisher = ( + const publisher = // 1. Service publisher for a specific event servicePublishers[event] || // 2. Service publisher for all events @@ -85,28 +88,31 @@ export function channels () { appPublishers[keys.ALL_EVENTS] || // 5. No publisher noop - ); try { - Promise.resolve(publisher(data, hook)).then((result: any) => { - if (!result) { - return; - } - - const results = (Array.isArray(result) ? compact(flattenDeep(result)) : [result] as Channel[]); - const channel = new CombinedChannel(results); - - if (channel && channel.length > 0) { - app.emit('publish', event, channel, hook, data); - } else { - debug('No connections to publish to'); - } - }).catch(logError); + Promise.resolve(publisher(data, hook)) + .then((result: any) => { + if (!result) { + return + } + + const results = Array.isArray(result) ? compact(flattenDeep(result)) : ([result] as Channel[]) + const channel = new CombinedChannel(results) + + if (channel && channel.length > 0) { + app.emit('publish', event, channel, hook, data) + } else { + debug('No connections to publish to') + } + }) + .catch(logError) } catch (error: any) { - logError(error); + logError(error) } - }); - }); - }); - }; + }) + }) + }) + } } + +export { Channel, CombinedChannel, RealTimeConnection } diff --git a/packages/transport-commons/src/channels/mixins.ts b/packages/transport-commons/src/channels/mixins.ts index 06861043aa..f60df6fe73 100644 --- a/packages/transport-commons/src/channels/mixins.ts +++ b/packages/transport-commons/src/channels/mixins.ts @@ -1,105 +1,108 @@ /* eslint-disable @typescript-eslint/no-unnecessary-type-assertion */ -import { Application, HookContext, getServiceOptions } from '@feathersjs/feathers'; -import { createDebug } from '@feathersjs/commons'; -import { Channel } from './channel/base'; -import { CombinedChannel } from './channel/combined'; +import { Application, HookContext, getServiceOptions } from '@feathersjs/feathers' +import { createDebug } from '@feathersjs/commons' +import { Channel } from './channel/base' +import { CombinedChannel } from './channel/combined' -const debug = createDebug('@feathersjs/transport-commons/channels/mixins'); -const PUBLISHERS = Symbol('@feathersjs/transport-commons/publishers'); -const CHANNELS = Symbol('@feathersjs/transport-commons/channels'); -const ALL_EVENTS = Symbol('@feathersjs/transport-commons/all-events'); +const debug = createDebug('@feathersjs/transport-commons/channels/mixins') +const PUBLISHERS = Symbol('@feathersjs/transport-commons/publishers') +const CHANNELS = Symbol('@feathersjs/transport-commons/channels') +const ALL_EVENTS = Symbol('@feathersjs/transport-commons/all-events') export const keys = { PUBLISHERS: PUBLISHERS as typeof PUBLISHERS, CHANNELS: CHANNELS as typeof CHANNELS, ALL_EVENTS: ALL_EVENTS as typeof ALL_EVENTS -}; +} export interface ChannelMixin { - [CHANNELS]: { [key: string]: Channel }; - channel (...names: string[]): Channel; + [CHANNELS]: { [key: string]: Channel } + channel(...names: string[]): Channel } -export function channelMixin () { +export function channelMixin() { const mixin: ChannelMixin = { [CHANNELS]: {}, - channel (...names: string[]): Channel { - debug('Returning channels', names); + channel(...names: string[]): Channel { + debug('Returning channels', names) if (names.length === 0) { - throw new Error('app.channel needs at least one channel name'); + throw new Error('app.channel needs at least one channel name') } if (names.length === 1) { - const [ name ] = names; + const [name] = names if (Array.isArray(name)) { - return this.channel(...name); + return this.channel(...name) } if (!this[CHANNELS][name]) { - const channel = new Channel(); + const channel = new Channel() channel.once('empty', () => { - channel.removeAllListeners(); - delete this[CHANNELS][name]; - }); + channel.removeAllListeners() + delete this[CHANNELS][name] + }) - this[CHANNELS][name] = channel; + this[CHANNELS][name] = channel } - return this[CHANNELS][name]; + return this[CHANNELS][name] } - const channels = names.map(name => this.channel(name)); + const channels = names.map((name) => this.channel(name)) - return new CombinedChannel(channels); + return new CombinedChannel(channels) } - }; + } - return mixin; + return mixin } -export type Event = string|(typeof ALL_EVENTS); +export type Event = string | typeof ALL_EVENTS -export type Publisher = (data: T, context: HookContext) => Channel | Channel[] | void | Promise; +export type Publisher = ( + data: T, + context: HookContext +) => Channel | Channel[] | void | Promise export interface PublishMixin { - [PUBLISHERS]: { [ALL_EVENTS]?: Publisher, [key: string]: Publisher }; - publish (event: Event, publisher: Publisher): this; - registerPublisher (event: Event, publisher: Publisher): this; + [PUBLISHERS]: { [ALL_EVENTS]?: Publisher; [key: string]: Publisher } + publish(event: Event, publisher: Publisher): this + registerPublisher(event: Event, publisher: Publisher): this } -export function publishMixin () { +export function publishMixin() { const result: PublishMixin = { [PUBLISHERS]: {}, - publish (...args) { - return this.registerPublisher(...args); + publish(...args) { + return this.registerPublisher(...args) }, - registerPublisher (event, publisher) { - debug('Registering publisher', event); + registerPublisher(event, publisher) { + debug('Registering publisher', event) if (!publisher && typeof event === 'function') { - publisher = event; - event = ALL_EVENTS; + publisher = event + event = ALL_EVENTS } - const { serviceEvents } = getServiceOptions(this); + const { serviceEvents } = getServiceOptions(this) if (event !== ALL_EVENTS && !serviceEvents.includes(event)) { - throw new Error(`'${event.toString()}' is not a valid service event`); + throw new Error(`'${event.toString()}' is not a valid service event`) } - const publishers = this[PUBLISHERS]; + const publishers = this[PUBLISHERS] - publishers[event] = publisher; + publishers[event] = publisher - return this; + return this } - }; + } - return result; + return result } diff --git a/packages/transport-commons/src/client.ts b/packages/transport-commons/src/client.ts index 8819fb95c3..2cf8b0a1ec 100644 --- a/packages/transport-commons/src/client.ts +++ b/packages/transport-commons/src/client.ts @@ -1,11 +1,13 @@ -import { convert } from '@feathersjs/errors'; -import { createDebug } from '@feathersjs/commons'; -import { Id, NullableId, Params, ServiceInterface } from '@feathersjs/feathers'; +/* eslint-disable @typescript-eslint/ban-ts-comment */ +import { convert } from '@feathersjs/errors' +import { createDebug } from '@feathersjs/commons' +import { Id, NullableId, Params, ServiceInterface } from '@feathersjs/feathers' -const debug = createDebug('@feathersjs/transport-commons/client'); +const debug = createDebug('@feathersjs/transport-commons/client') const namespacedEmitterMethods = [ 'addListener', + 'addEventListener', 'emit', 'listenerCount', 'listeners', @@ -14,128 +16,126 @@ const namespacedEmitterMethods = [ 'prependListener', 'prependOnceListener', 'removeAllListeners', + 'removeEventListener', 'removeListener' -]; -const otherEmitterMethods = [ - 'eventNames', - 'getMaxListeners', - 'setMaxListeners' -]; +] +const otherEmitterMethods = ['eventNames', 'getMaxListeners', 'setMaxListeners'] const addEmitterMethods = (service: any) => { - otherEmitterMethods.forEach(method => { + otherEmitterMethods.forEach((method) => { service[method] = function (...args: any[]) { if (typeof this.connection[method] !== 'function') { - throw new Error(`Can not call '${method}' on the client service connection`); + throw new Error(`Can not call '${method}' on the client service connection`) } - return this.connection[method](...args); - }; - }); + return this.connection[method](...args) + } + }) // Methods that should add the namespace (service path) - namespacedEmitterMethods.forEach(method => { + namespacedEmitterMethods.forEach((method) => { service[method] = function (name: string, ...args: any[]) { if (typeof this.connection[method] !== 'function') { - throw new Error(`Can not call '${method}' on the client service connection`); + throw new Error(`Can not call '${method}' on the client service connection`) } - const eventName = `${this.path} ${name}`; + const eventName = `${this.path} ${name}` - debug(`Calling emitter method ${method} with ` + - `namespaced event '${eventName}'`); + debug(`Calling emitter method ${method} with ` + `namespaced event '${eventName}'`) - const result = this.connection[method](eventName, ...args); + const result = this.connection[method](eventName, ...args) - return result === this.connection ? this : result; - }; - }); -}; + return result === this.connection ? this : result + } + }) +} interface ServiceOptions { - name: string; - connection: any; - method: string; - events?: string[]; + name: string + connection: any + method: string + events?: string[] } -export type SocketService> = Service; +export type SocketService, P extends Params = Params> = Service -export class Service> implements ServiceInterface { - events: string[]; - path: string; - connection: any; - method: string; +export class Service, P extends Params = Params> + implements ServiceInterface +{ + events: string[] + path: string + connection: any + method: string - constructor (options: ServiceOptions) { - this.events = options.events; - this.path = options.name; - this.connection = options.connection; - this.method = options.method; + constructor(options: ServiceOptions) { + this.events = options.events + this.path = options.name + this.connection = options.connection + this.method = options.method - addEmitterMethods(this); + addEmitterMethods(this) } - send (method: string, ...args: any[]) { + send(method: string, ...args: any[]) { return new Promise((resolve, reject) => { - args.unshift(method, this.path); + args.unshift(method, this.path) args.push(function (error: any, data: any) { - return error ? reject(convert(error)) : resolve(data); - }); + return error ? reject(convert(error)) : resolve(data) + }) - debug(`Sending socket.${this.method}`, args); + debug(`Sending socket.${this.method}`, args) - this.connection[this.method](...args); - }); + this.connection[this.method](...args) + }) } - methods (this: any, ...names: string[]) { - names.forEach(name => { + methods(this: any, ...names: string[]) { + names.forEach((name) => { this[name] = function (data: any, params: Params = {}) { - return this.send(name, data, params.query || {}); + return this.send(name, data, params.query || {}) } - }); - return this; + }) + return this } - find (params: Params = {}) { - return this.send('find', params.query || {}); + find(params: Params = {}) { + return this.send('find', params.query || {}) } - get (id: Id, params: Params = {}) { - return this.send('get', id, params.query || {}); + get(id: Id, params: Params = {}) { + return this.send('get', id, params.query || {}) } - create (data: any, params: Params = {}) { - return this.send('create', data, params.query || {}); + create(data: any, params: Params = {}) { + return this.send('create', data, params.query || {}) } - update (id: Id, data: any, params: Params = {}) { - return this.send ('update', id, data, params.query || {}); + update(id: Id, data: any, params: Params = {}) { + return this.send('update', id, data, params.query || {}) } - patch (id: NullableId, data: any, params: Params = {}) { - return this.send ('patch', id, data, params.query || {}); + patch(id: NullableId, data: any, params: Params = {}) { + return this.send('patch', id, data, params.query || {}) } - remove (id: NullableId, params: Params = {}) { - return this.send ('remove', id, params.query || {}); + remove(id: NullableId, params: Params = {}) { + return this.send('remove', id, params.query || {}) } // `off` is actually not part of the Node event emitter spec // but we are adding it since everybody is expecting it because // of the emitter-component Socket.io is using - off (name: string, ...args: any[]) { + off(name: string, ...args: any[]) { if (typeof this.connection.off === 'function') { - const result = this.connection.off(`${this.path} ${name}`, ...args); + const result = this.connection.off(`${this.path} ${name}`, ...args) - return result === this.connection ? this : result; + return result === this.connection ? this : result } else if (args.length === 0) { // @ts-ignore - return this.removeAllListeners(name); + return this.removeAllListeners(name) } // @ts-ignore - return this.removeListener(name, ...args); + return this.removeListener(name, ...args) } } diff --git a/packages/transport-commons/src/http.ts b/packages/transport-commons/src/http.ts index c61e51330a..262dde2176 100644 --- a/packages/transport-commons/src/http.ts +++ b/packages/transport-commons/src/http.ts @@ -1,11 +1,12 @@ -import { MethodNotAllowed } from '@feathersjs/errors/lib'; -import { HookContext, NullableId, Params } from '@feathersjs/feathers'; +import { MethodNotAllowed } from '@feathersjs/errors/lib' +import { HookContext, NullableId, Params } from '@feathersjs/feathers' +import encodeUrl from 'encodeurl' -export const METHOD_HEADER = 'x-service-method'; +export const METHOD_HEADER = 'x-service-method' export interface ServiceParams { - id: NullableId, - data: any, + id: NullableId + data: any params: Params } @@ -13,64 +14,82 @@ export const statusCodes = { created: 201, noContent: 204, methodNotAllowed: 405, - success: 200 -}; + success: 200, + seeOther: 303 +} export const knownMethods: { [key: string]: string } = { post: 'create', patch: 'patch', put: 'update', delete: 'remove' -}; +} + +export function getServiceMethod(_httpMethod: string, id: unknown, headerOverride?: string) { + const httpMethod = _httpMethod.toLowerCase() -export function getServiceMethod (_httpMethod: string, id: unknown, headerOverride?: string) { - const httpMethod = _httpMethod.toLowerCase(); - if (httpMethod === 'post' && headerOverride) { - return headerOverride; + return headerOverride } - const mappedMethod = knownMethods[httpMethod]; + const mappedMethod = knownMethods[httpMethod] if (mappedMethod) { - return mappedMethod; + return mappedMethod } if (httpMethod === 'get') { - return id === null ? 'find' : 'get'; + return id === null ? 'find' : 'get' } - throw new MethodNotAllowed(`Method ${_httpMethod} not allowed`); + throw new MethodNotAllowed(`Method ${_httpMethod} not allowed`) } export const argumentsFor = { - get: ({ id, params }: ServiceParams) => [ id, params ], - find: ({ params }: ServiceParams) => [ params ], - create: ({ data, params }: ServiceParams) => [ data, params ], - update: ({ id, data, params }: ServiceParams) => [ id, data, params ], - patch: ({ id, data, params }: ServiceParams) => [ id, data, params ], - remove: ({ id, params }: ServiceParams) => [ id, params ], - default: ({ data, params }: ServiceParams) => [ data, params ] + get: ({ id, params }: ServiceParams) => [id, params], + find: ({ params }: ServiceParams) => [params], + create: ({ data, params }: ServiceParams) => [data, params], + update: ({ id, data, params }: ServiceParams) => [id, data, params], + patch: ({ id, data, params }: ServiceParams) => [id, data, params], + remove: ({ id, params }: ServiceParams) => [id, params], + default: ({ data, params }: ServiceParams) => [data, params] } -export function getData (context: HookContext) { - return context.dispatch !== undefined - ? context.dispatch - : context.result; -} +export function getStatusCode(context: HookContext, body: any, location: string | string[]) { + const { http = {} } = context -export function getStatusCode (context: HookContext, data?: any) { - if (context.http?.statusCode) { - return context.http.statusCode; + if (http.status) { + return http.status } if (context.method === 'create') { - return statusCodes.created; + return statusCodes.created } - if (!data) { - return statusCodes.noContent; + if (location !== undefined) { + return statusCodes.seeOther } - return statusCodes.success; + if (!body) { + return statusCodes.noContent + } + + return statusCodes.success +} + +export function getResponse(context: HookContext) { + const { http = {} } = context + const body = context.dispatch !== undefined ? context.dispatch : context.result + + let headers = http.headers || {} + let location = headers.Location + + if (http.location !== undefined) { + location = encodeUrl(http.location) + headers = { ...headers, Location: location } + } + + const status = getStatusCode(context, body, location) + + return { status, headers, body } } diff --git a/packages/transport-commons/src/index.ts b/packages/transport-commons/src/index.ts index 6db39360b2..3c957e55c6 100644 --- a/packages/transport-commons/src/index.ts +++ b/packages/transport-commons/src/index.ts @@ -1,6 +1,6 @@ -import { socket } from './socket'; -import { routing } from './routing'; -import { channels } from './channels'; +import { socket } from './socket' +import { routing } from './routing' +import { channels, Channel, CombinedChannel, RealTimeConnection } from './channels' -export * as http from './http'; -export { socket, routing, channels }; +export * as http from './http' +export { socket, routing, channels, Channel, CombinedChannel, RealTimeConnection } diff --git a/packages/transport-commons/src/routing/index.ts b/packages/transport-commons/src/routing/index.ts index b8b504dbda..8e4870347f 100644 --- a/packages/transport-commons/src/routing/index.ts +++ b/packages/transport-commons/src/routing/index.ts @@ -1,50 +1,62 @@ -import { Application, Service, ServiceOptions } from '@feathersjs/feathers'; -import { Router } from './router'; +import { Application, FeathersService, ServiceOptions } from '@feathersjs/feathers' +import { Router } from './router' declare module '@feathersjs/feathers/lib/declarations' { interface RouteLookup { - service: Service, + service: Service params: { [key: string]: any } } - interface Application { // eslint-disable-line + // eslint-disable-next-line @typescript-eslint/no-unused-vars + interface Application { + // eslint-disable-line routes: Router<{ - service: Service, + service: Service params?: { [key: string]: any } - }>; - lookup (path: string): RouteLookup; + }> + lookup(path: string): RouteLookup } } -export * from './router'; +export * from './router' const lookup = function (this: Application, path: string) { - const result = this.routes.lookup(path); + const result = this.routes.lookup(path) if (result === null) { - return null; + return null } - const { params: colonParams, data: { service, params: dataParams } } = result; + const { + params: colonParams, + data: { service, params: dataParams } + } = result - const params = dataParams ? { ...dataParams, ...colonParams } : colonParams; + const params = dataParams ? { ...dataParams, ...colonParams } : colonParams - return { service, params }; -}; + return { service, params } +} export const routing = () => (app: Application) => { if (typeof app.lookup === 'function') { - return; + return } - app.routes = new Router(); - app.lookup = lookup; + const { unuse } = app + + app.routes = new Router() + app.lookup = lookup + app.unuse = function (path: string) { + app.routes.remove(path) + app.routes.remove(`${path}/:__id`) + return unuse.call(this, path) + } // Add a mixin that registers a service on the router - app.mixins.push((service: Service, path: string, options: ServiceOptions) => { - const { routeParams: params = {} } = options; + app.mixins.push((service: FeathersService, path: string, options: ServiceOptions) => { + const { routeParams: params = {} } = options - app.routes.insert(path, { service, params }); - app.routes.insert(`${path}/:__id`, { service, params }); - }); -}; + app.routes.insert(path, { service, params }) + app.routes.insert(`${path}/:__id`, { service, params }) + }) +} diff --git a/packages/transport-commons/src/routing/router.ts b/packages/transport-commons/src/routing/router.ts index bf883f853a..2fef8b1683 100644 --- a/packages/transport-commons/src/routing/router.ts +++ b/packages/transport-commons/src/routing/router.ts @@ -1,98 +1,136 @@ -import { stripSlashes } from '@feathersjs/commons'; +import { stripSlashes } from '@feathersjs/commons' export interface LookupData { - params: { [key: string]: string }; + params: { [key: string]: string } } export interface LookupResult extends LookupData { - data?: T; + data?: T } export class RouteNode { - data?: T; - children: { [key: string]: RouteNode } = {}; - placeholders: RouteNode[] = []; + data?: T + children: { [key: string]: RouteNode } = {} + placeholders: RouteNode[] = [] - constructor (public name: string, public depth: number) {} + constructor(public name: string, public depth: number) {} - insert (path: string[], data: T): RouteNode { + get hasChildren() { + return Object.keys(this.children).length !== 0 || this.placeholders.length !== 0 + } + + insert(path: string[], data: T): RouteNode { if (this.depth === path.length) { if (this.data !== undefined) { - throw new Error(`Path ${path.join('/')} already exists`); + throw new Error(`Path ${path.join('/')} already exists`) } - this.data = data; - return this; + this.data = data + return this } - const current = path[this.depth]; - const nextDepth = this.depth + 1; + const current = path[this.depth] + const nextDepth = this.depth + 1 if (current.startsWith(':')) { // Insert a placeholder node like /messages/:id - const placeholderName = current.substring(1); - let placeholder = this.placeholders.find(p => p.name === placeholderName); + const placeholderName = current.substring(1) + let placeholder = this.placeholders.find((p) => p.name === placeholderName) if (!placeholder) { - placeholder = new RouteNode(placeholderName, nextDepth); - this.placeholders.push(placeholder); + placeholder = new RouteNode(placeholderName, nextDepth) + this.placeholders.push(placeholder) } - return placeholder.insert(path, data); + return placeholder.insert(path, data) } - const child = this.children[current] || new RouteNode(current, nextDepth); + const child = this.children[current] || new RouteNode(current, nextDepth) - this.children[current] = child; + this.children[current] = child - return child.insert(path, data); + return child.insert(path, data) } - lookup (path: string[], info: LookupData): LookupResult|null { + remove(path: string[]) { if (path.length === this.depth) { - return this.data === undefined ? null : { - ...info, - data: this.data + return + } + + const current = path[this.depth] + + if (current.startsWith(':')) { + const placeholderName = current.substring(1) + const placeholder = this.placeholders.find((p) => p.name === placeholderName) + + placeholder.remove(path) + this.placeholders = this.placeholders.filter((p) => p !== placeholder) + } else if (this.children[current]) { + const child = this.children[current] + + child.remove(path) + + if (!child.hasChildren) { + delete this.children[current] } } + } + + lookup(path: string[], info: LookupData): LookupResult | null { + if (path.length === this.depth) { + return this.data === undefined + ? null + : { + ...info, + data: this.data + } + } - const current = path[this.depth]; - const child = this.children[current]; + const current = path[this.depth] + const child = this.children[current] if (child) { - return child.lookup(path, info); + const lookup = child.lookup(path, info) + + if (lookup !== null) { + return lookup + } } // This will return the first placeholder that matches early - for(const placeholder of this.placeholders) { - const result = placeholder.lookup(path, info); + for (const placeholder of this.placeholders) { + const result = placeholder.lookup(path, info) if (result !== null) { - result.params[placeholder.name] = current; - return result; + result.params[placeholder.name] = current + return result } } - return null; + return null } } export class Router { - constructor (public root: RouteNode = new RouteNode('', 0)) {} + constructor(public root: RouteNode = new RouteNode('', 0)) {} + + getPath(path: string) { + return stripSlashes(path).split('/') + } - getPath (path: string) { - return stripSlashes(path).split('/'); + insert(path: string, data: T) { + return this.root.insert(this.getPath(path), data) } - insert (path: string, data: T) { - return this.root.insert(this.getPath(path), data); + remove(path: string) { + return this.root.remove(this.getPath(path)) } - lookup (path: string) { + lookup(path: string) { if (typeof path !== 'string') { - return null; + return null } - return this.root.lookup(this.getPath(path), { params: {} }); + return this.root.lookup(this.getPath(path), { params: {} }) } } diff --git a/packages/transport-commons/src/socket/index.ts b/packages/transport-commons/src/socket/index.ts index 2aefea7748..0a009a4ce8 100644 --- a/packages/transport-commons/src/socket/index.ts +++ b/packages/transport-commons/src/socket/index.ts @@ -1,70 +1,70 @@ -import { Application, getServiceOptions, Params } from '@feathersjs/feathers'; -import { createDebug } from '@feathersjs/commons'; -import { channels } from '../channels'; -import { routing } from '../routing'; -import { getDispatcher, runMethod } from './utils'; -import { RealTimeConnection } from '../channels/channel/base'; +import { Application, getServiceOptions, Params } from '@feathersjs/feathers' +import { createDebug } from '@feathersjs/commons' +import { channels } from '../channels' +import { routing } from '../routing' +import { getDispatcher, runMethod } from './utils' +import { RealTimeConnection } from '../channels/channel/base' -const debug = createDebug('@feathersjs/transport-commons'); +const debug = createDebug('@feathersjs/transport-commons') export interface SocketOptions { - done: Promise; - emit: string; - socketMap: WeakMap; - socketKey?: any; - getParams: (socket: any) => RealTimeConnection; + done: Promise + emit: string + socketMap: WeakMap + socketKey?: any + getParams: (socket: any) => RealTimeConnection } -export function socket ({ done, emit, socketMap, socketKey, getParams }: SocketOptions) { +export function socket({ done, emit, socketMap, socketKey, getParams }: SocketOptions) { return (app: Application) => { const leaveChannels = (connection: RealTimeConnection) => { - const { channels } = app; + const { channels } = app if (channels.length) { - app.channel(app.channels).leave(connection); + app.channel(app.channels).leave(connection) } - }; + } - app.configure(channels()); - app.configure(routing()); + app.configure(channels()) + app.configure(routing()) - app.on('publish', getDispatcher(emit, socketMap, socketKey)); - app.on('disconnect', leaveChannels); + app.on('publish', getDispatcher(emit, socketMap, socketKey)) + app.on('disconnect', leaveChannels) app.on('logout', (_authResult: any, params: Params) => { - const { connection } = params; + const { connection } = params if (connection) { - leaveChannels(connection); + leaveChannels(connection) } - }); + }) // `connection` event - done.then(provider => provider.on('connection', (connection: any) => - app.emit('connection', getParams(connection))) - ); + done.then((provider) => + provider.on('connection', (connection: any) => app.emit('connection', getParams(connection))) + ) // `socket.emit('methodName', 'serviceName', ...args)` handlers - done.then(provider => provider.on('connection', (connection: any) => { - const methodHandlers = Object.keys(app.services).reduce((result, name) => { - const { methods } = getServiceOptions(app.service(name)); + done.then((provider) => + provider.on('connection', (connection: any) => { + const methodHandlers = Object.keys(app.services).reduce((result, name) => { + const { methods } = getServiceOptions(app.service(name)) - methods.forEach(method => { - if (!result[method]) { - result[method] = (...args: any[]) => { - const path = args.shift(); + methods.forEach((method) => { + if (!result[method]) { + result[method] = (...args: any[]) => { + const path = args.shift() - debug(`Got '${method}' call for service '${path}'`); - runMethod(app, getParams(connection), path, method, args); + debug(`Got '${method}' call for service '${path}'`) + runMethod(app, getParams(connection), path, method, args) + } } - } - }); + }) - return result; - }, {} as any); + return result + }, {} as any) - Object.keys(methodHandlers).forEach(key => - connection.on(key, methodHandlers[key]) - ); - })); - }; + Object.keys(methodHandlers).forEach((key) => connection.on(key, methodHandlers[key])) + }) + ) + } } diff --git a/packages/transport-commons/src/socket/utils.ts b/packages/transport-commons/src/socket/utils.ts index 9ccaa111e9..e4591b6533 100644 --- a/packages/transport-commons/src/socket/utils.ts +++ b/packages/transport-commons/src/socket/utils.ts @@ -1,114 +1,121 @@ -import { HookContext, Application, createContext, getServiceOptions } from '@feathersjs/feathers'; -import { NotFound, MethodNotAllowed, BadRequest } from '@feathersjs/errors'; -import { createDebug } from '@feathersjs/commons'; -import isEqual from 'lodash/isEqual'; -import { CombinedChannel } from '../channels/channel/combined'; -import { RealTimeConnection } from '../channels/channel/base'; +import { HookContext, Application, createContext, getServiceOptions } from '@feathersjs/feathers' +import { NotFound, MethodNotAllowed, BadRequest } from '@feathersjs/errors' +import { createDebug } from '@feathersjs/commons' +import isEqual from 'lodash/isEqual' +import { CombinedChannel } from '../channels/channel/combined' +import { RealTimeConnection } from '../channels/channel/base' -const debug = createDebug('@feathersjs/transport-commons'); +const debug = createDebug('@feathersjs/transport-commons') -export const DEFAULT_PARAMS_POSITION = 1; +export const DEFAULT_PARAMS_POSITION = 1 export const paramsPositions: { [key: string]: number } = { find: 0, update: 2, patch: 2 -}; +} -export function normalizeError (e: any) { - const hasToJSON = typeof e.toJSON === 'function'; - const result = hasToJSON ? e.toJSON() : {}; +export function normalizeError(e: any) { + const hasToJSON = typeof e.toJSON === 'function' + const result = hasToJSON ? e.toJSON() : {} if (!hasToJSON) { - Object.getOwnPropertyNames(e).forEach(key => { - result[key] = e[key]; - }); + Object.getOwnPropertyNames(e).forEach((key) => { + result[key] = e[key] + }) } if (process.env.NODE_ENV === 'production') { - delete result.stack; + delete result.stack } - delete result.hook; + delete result.hook - return result; + return result } -export function getDispatcher (emit: string, socketMap: WeakMap, socketKey?: any) { +export function getDispatcher(emit: string, socketMap: WeakMap, socketKey?: any) { return function (event: string, channel: CombinedChannel, context: HookContext, data?: any) { - debug(`Dispatching '${event}' to ${channel.length} connections`); + debug(`Dispatching '${event}' to ${channel.length} connections`) - channel.connections.forEach(connection => { + channel.connections.forEach((connection) => { // The reference between connection and socket is set in `app.setup` - const socket = socketKey ? connection[socketKey] : socketMap.get(connection); + const socket = socketKey ? connection[socketKey] : socketMap.get(connection) if (socket) { - const eventName = `${context.path || ''} ${event}`.trim(); + const eventName = `${context.path || ''} ${event}`.trim() - let result = channel.dataFor(connection) || context.dispatch || context.result; + let result = channel.dataFor(connection) || context.dispatch || context.result // If we are getting events from an array but try to dispatch individual data // try to get the individual item to dispatch from the correct index. if (!Array.isArray(data) && Array.isArray(context.result) && Array.isArray(result)) { - result = context.result.find(resultData => isEqual(resultData, data)); + result = context.result.find((resultData) => isEqual(resultData, data)) } - debug(`Dispatching '${eventName}' to Socket ${socket.id} with`, result); + debug(`Dispatching '${eventName}' to Socket ${socket.id} with`, result) - socket[emit](eventName, result); + socket[emit](eventName, result) } - }); - }; + }) + } } -export async function runMethod (app: Application, connection: RealTimeConnection, path: string, method: string, args: any[]) { - const trace = `method '${method}' on service '${path}'`; - const methodArgs = args.slice(0); - const callback = typeof methodArgs[methodArgs.length - 1] === 'function' - ? methodArgs.pop() : function () {}; - - debug(`Running ${trace}`, connection, args); +export async function runMethod( + app: Application, + connection: RealTimeConnection, + path: string, + method: string, + args: any[] +) { + const trace = `method '${method}' on service '${path}'` + const methodArgs = args.slice(0) + const callback = + // eslint-disable-next-line @typescript-eslint/no-empty-function + typeof methodArgs[methodArgs.length - 1] === 'function' ? methodArgs.pop() : function () {} + + debug(`Running ${trace}`, connection, args) const handleError = (error: any) => { - debug(`Error in ${trace}`, error); - callback(normalizeError(error)); - }; + debug(`Error in ${trace}`, error) + callback(normalizeError(error)) + } try { - const lookup = app.lookup(path); + const lookup = app.lookup(path) // No valid service was found throw a NotFound error if (lookup === null) { - throw new NotFound(`Service '${path}' not found`); + throw new NotFound(`Service '${path}' not found`) } - const { service, params: route = {} } = lookup; - const { methods } = getServiceOptions(service); + const { service, params: route = {} } = lookup + const { methods } = getServiceOptions(service) // Only service methods are allowed if (!methods.includes(method)) { - throw new MethodNotAllowed(`Method '${method}' not allowed on service '${path}'`); + throw new MethodNotAllowed(`Method '${method}' not allowed on service '${path}'`) } - const position = paramsPositions[method] !== undefined ? paramsPositions[method] : DEFAULT_PARAMS_POSITION; - const query = methodArgs[position] || {}; + const position = paramsPositions[method] !== undefined ? paramsPositions[method] : DEFAULT_PARAMS_POSITION + const query = Object.assign({}, methodArgs[position]) // `params` have to be re-mapped to the query and added with the route - const params = Object.assign({ query, route, connection }, connection); + const params = Object.assign({ query, route, connection }, connection) // `params` is always the last parameter. Error if we got more arguments. - if (methodArgs.length > (position + 1)) { - throw new BadRequest(`Too many arguments for '${method}' method`); + if (methodArgs.length > position + 1) { + throw new BadRequest(`Too many arguments for '${method}' method`) } - methodArgs[position] = params; + methodArgs[position] = params - const ctx = createContext(service, method); - const returnedCtx: HookContext = await (service as any)[method](...methodArgs, ctx); - const result = returnedCtx.dispatch || returnedCtx.result; + const ctx = createContext(service, method) + const returnedCtx: HookContext = await (service as any)[method](...methodArgs, ctx) + const result = returnedCtx.dispatch || returnedCtx.result - debug(`Returned successfully ${trace}`, result); - callback(null, result); + debug(`Returned successfully ${trace}`, result) + callback(null, result) } catch (error: any) { - handleError(error); + handleError(error) } } diff --git a/packages/transport-commons/test/channels/channel.test.ts b/packages/transport-commons/test/channels/channel.test.ts index 92e83942d6..42fd3dcec5 100644 --- a/packages/transport-commons/test/channels/channel.test.ts +++ b/packages/transport-commons/test/channels/channel.test.ts @@ -1,241 +1,242 @@ -import assert from 'assert'; -import { feathers, Application } from '@feathersjs/feathers'; -import { channels, keys } from '../../src/channels'; -import { Channel, RealTimeConnection } from '../../src/channels/channel/base'; -import { CombinedChannel } from '../../src/channels/channel/combined'; +/* eslint-disable @typescript-eslint/no-empty-function */ +import assert from 'assert' +import { feathers, Application } from '@feathersjs/feathers' +import { channels, keys } from '../../src/channels' +import { Channel, RealTimeConnection } from '../../src/channels/channel/base' +import { CombinedChannel } from '../../src/channels/channel/combined' -const { CHANNELS } = keys; +const { CHANNELS } = keys describe('app.channel', () => { - let app: Application; + let app: Application beforeEach(() => { - app = feathers().configure(channels()); - }); + app = feathers().configure(channels()) + }) describe('base channels', () => { it('creates a new channel, app.channels has names', () => { - assert.ok(app.channel('test') instanceof Channel); - assert.deepStrictEqual(app.channels, ['test']); - }); + assert.ok(app.channel('test') instanceof Channel) + assert.deepStrictEqual(app.channels, ['test']) + }) it('.join', () => { - const test = app.channel('test'); - const c1 = { id: 1 }; - const c2 = { id: 2 }; - const c3 = { id: 3 }; + const test = app.channel('test') + const c1 = { id: 1 } + const c2 = { id: 2 } + const c3 = { id: 3 } - assert.strictEqual(test.length, 0, 'Initial channel is empty'); + assert.strictEqual(test.length, 0, 'Initial channel is empty') - test.join(c1); - test.join(c1); + test.join(c1) + test.join(c1) - assert.strictEqual(test.length, 1, 'Joining twice only runs once'); + assert.strictEqual(test.length, 1, 'Joining twice only runs once') - test.join(c2, c3); + test.join(c2, c3) - assert.strictEqual(test.length, 3, 'New connections joined'); + assert.strictEqual(test.length, 3, 'New connections joined') - test.join(c1, c2, c3); + test.join(c1, c2, c3) - assert.strictEqual(test.length, 3, 'Joining multiple times does nothing'); - }); + assert.strictEqual(test.length, 3, 'Joining multiple times does nothing') + }) it('.leave', () => { - const test = app.channel('test'); - const c1 = { id: 1 }; - const c2 = { id: 2 }; + const test = app.channel('test') + const c1 = { id: 1 } + const c2 = { id: 2 } - assert.strictEqual(test.length, 0); + assert.strictEqual(test.length, 0) - test.join(c1, c2); + test.join(c1, c2) - assert.strictEqual(test.length, 2); + assert.strictEqual(test.length, 2) - test.leave(c2); - test.leave(c2); + test.leave(c2) + test.leave(c2) - assert.strictEqual(test.length, 1); - assert.strictEqual(test.connections.indexOf(c2), -1); - }); + assert.strictEqual(test.length, 1) + assert.strictEqual(test.connections.indexOf(c2), -1) + }) it('.leave conditional', () => { - const test = app.channel('test'); - const c1 = { id: 1, leave: true }; - const c2 = { id: 2 }; - const c3 = { id: 3 }; + const test = app.channel('test') + const c1 = { id: 1, leave: true } + const c2 = { id: 2 } + const c3 = { id: 3 } - test.join(c1, c2, c3); + test.join(c1, c2, c3) - assert.strictEqual(test.length, 3); + assert.strictEqual(test.length, 3) - test.leave((connection: RealTimeConnection) => connection.leave); + test.leave((connection: RealTimeConnection) => connection.leave) - assert.strictEqual(test.length, 2); - assert.strictEqual(test.connections.indexOf(c1), -1); - }); + assert.strictEqual(test.length, 2) + assert.strictEqual(test.connections.indexOf(c1), -1) + }) it('.filter', () => { - const test = app.channel('test'); - const c1 = { id: 1, filter: true }; - const c2 = { id: 2 }; - const c3 = { id: 3 }; + const test = app.channel('test') + const c1 = { id: 1, filter: true } + const c2 = { id: 2 } + const c3 = { id: 3 } - test.join(c1, c2, c3); + test.join(c1, c2, c3) - const filtered = test.filter(connection => connection.filter); + const filtered = test.filter((connection) => connection.filter) - assert.ok(filtered !== test, 'Returns a new channel instance'); - assert.ok(filtered instanceof Channel); - assert.strictEqual(filtered.length, 1); - }); + assert.ok(filtered !== test, 'Returns a new channel instance') + assert.ok(filtered instanceof Channel) + assert.strictEqual(filtered.length, 1) + }) it('.send', () => { - const data = { message: 'Hi' }; + const data = { message: 'Hi' } - const test = app.channel('test'); - const withData = test.send(data); + const test = app.channel('test') + const withData = test.send(data) - assert.ok(test !== withData); - assert.deepStrictEqual(withData.data, data); - }); + assert.ok(test !== withData) + assert.deepStrictEqual(withData.data, data) + }) describe('empty channels', () => { it('is an EventEmitter', () => { - const channel = app.channel('emitchannel'); + const channel = app.channel('emitchannel') return new Promise((resolve) => { - channel.once('message', data => { - assert.strictEqual(data, 'hello'); - resolve(); - }); + channel.once('message', (data) => { + assert.strictEqual(data, 'hello') + resolve() + }) - channel.emit('message', 'hello'); - }); - }); + channel.emit('message', 'hello') + }) + }) - it('empty', done => { - const channel = app.channel('test'); - const c1 = { id: 1 }; - const c2 = { id: 2 }; + it('empty', (done) => { + const channel = app.channel('test') + const c1 = { id: 1 } + const c2 = { id: 2 } - channel.once('empty', done); + channel.once('empty', done) - channel.join(c1, c2); - channel.leave(c1); - channel.leave(c2); - }); + channel.join(c1, c2) + channel.leave(c1) + channel.leave(c2) + }) it('removes an empty channel', () => { - const channel = app.channel('test'); - const appChannels = (app as any)[CHANNELS]; - const c1 = { id: 1 }; + const channel = app.channel('test') + const appChannels = (app as any)[CHANNELS] + const c1 = { id: 1 } - channel.join(c1); + channel.join(c1) - assert.ok(appChannels.test); - assert.strictEqual(Object.keys(appChannels).length, 1); - channel.leave(c1); + assert.ok(appChannels.test) + assert.strictEqual(Object.keys(appChannels).length, 1) + channel.leave(c1) - assert.ok((app as any)[CHANNELS].test === undefined); - assert.strictEqual(Object.keys(appChannels).length, 0); - }); + assert.ok((app as any)[CHANNELS].test === undefined) + assert.strictEqual(Object.keys(appChannels).length, 0) + }) it('removes all event listeners from an empty channel', () => { - const channel = app.channel('testing'); - const connection = { id: 1 }; + const channel = app.channel('testing') + const connection = { id: 1 } - channel.on('something', () => {}); - assert.strictEqual(channel.listenerCount('something'), 1); - assert.strictEqual(channel.listenerCount('empty'), 1); + channel.on('something', () => {}) + assert.strictEqual(channel.listenerCount('something'), 1) + assert.strictEqual(channel.listenerCount('empty'), 1) - channel.join(connection).leave(connection); + channel.join(connection).leave(connection) - assert.ok((app as any)[CHANNELS].testing === undefined); + assert.ok((app as any)[CHANNELS].testing === undefined) - assert.strictEqual(channel.listenerCount('something'), 0); - assert.strictEqual(channel.listenerCount('empty'), 0); - }); - }); - }); + assert.strictEqual(channel.listenerCount('something'), 0) + assert.strictEqual(channel.listenerCount('empty'), 0) + }) + }) + }) describe('combined channels', () => { it('combines multiple channels', () => { - const combined = app.channel('test', 'again'); + const combined = app.channel('test', 'again') - assert.deepStrictEqual(app.channels, ['test', 'again']); - assert.ok(combined instanceof CombinedChannel); - assert.strictEqual(combined.length, 0); - }); + assert.deepStrictEqual(app.channels, ['test', 'again']) + assert.ok(combined instanceof CombinedChannel) + assert.strictEqual(combined.length, 0) + }) it('de-dupes connections', () => { - const c1 = { id: 1 }; - const c2 = { id: 2 }; + const c1 = { id: 1 } + const c2 = { id: 2 } - app.channel('test').join(c1, c2); - app.channel('again').join(c1); + app.channel('test').join(c1, c2) + app.channel('again').join(c1) - const combined = app.channel('test', 'again'); + const combined = app.channel('test', 'again') - assert.ok(combined instanceof CombinedChannel); - assert.strictEqual(combined.length, 2); - }); + assert.ok(combined instanceof CombinedChannel) + assert.strictEqual(combined.length, 2) + }) it('does nothing when the channel is undefined (#2207)', () => { - const channel = app.channel('test', 'me'); + const channel = app.channel('test', 'me') - channel.join(undefined); - }); + channel.join(undefined) + }) it('.join all child channels', () => { - const c1 = { id: 1 }; - const c2 = { id: 2 }; + const c1 = { id: 1 } + const c2 = { id: 2 } - const combined = app.channel('test', 'again'); + const combined = app.channel('test', 'again') - combined.join(c1, c2); + combined.join(c1, c2) - assert.strictEqual(combined.length, 2); - assert.strictEqual(app.channel('test').length, 2); - assert.strictEqual(app.channel('again').length, 2); - }); + assert.strictEqual(combined.length, 2) + assert.strictEqual(app.channel('test').length, 2) + assert.strictEqual(app.channel('again').length, 2) + }) it('.leave all child channels', () => { - const c1 = { id: 1 }; - const c2 = { id: 2 }; + const c1 = { id: 1 } + const c2 = { id: 2 } - app.channel('test').join(c1, c2); - app.channel('again').join(c1); + app.channel('test').join(c1, c2) + app.channel('again').join(c1) - const combined = app.channel('test', 'again'); + const combined = app.channel('test', 'again') - combined.leave(c1); + combined.leave(c1) - assert.strictEqual(app.channel('test').length, 1); - assert.strictEqual(app.channel('again').length, 0); - }); + assert.strictEqual(app.channel('test').length, 1) + assert.strictEqual(app.channel('again').length, 0) + }) it('.leave all child channels conditionally', () => { - const c1 = { id: 1 }; - const c2 = { id: 2, leave: true }; - const combined = app.channel('test', 'again').join(c1, c2); + const c1 = { id: 1 } + const c2 = { id: 2, leave: true } + const combined = app.channel('test', 'again').join(c1, c2) - combined.leave((connection: RealTimeConnection) => connection.leave); + combined.leave((connection: RealTimeConnection) => connection.leave) - assert.strictEqual(app.channel('test').length, 1); - assert.strictEqual(app.channel('again').length, 1); - }); + assert.strictEqual(app.channel('test').length, 1) + assert.strictEqual(app.channel('again').length, 1) + }) it('app.channel(app.channels)', () => { - const c1 = { id: 1 }; - const c2 = { id: 2 }; + const c1 = { id: 1 } + const c2 = { id: 2 } - app.channel('test').join(c1, c2); - app.channel('again').join(c1); + app.channel('test').join(c1, c2) + app.channel('again').join(c1) - const combined = app.channel(app.channels); + const combined = app.channel(app.channels) - assert.deepStrictEqual(combined.connections, [ c1, c2 ]); - }); - }); -}); + assert.deepStrictEqual(combined.connections, [c1, c2]) + }) + }) +}) diff --git a/packages/transport-commons/test/channels/dispatch.test.ts b/packages/transport-commons/test/channels/dispatch.test.ts index fc06908bf7..8165e3b439 100644 --- a/packages/transport-commons/test/channels/dispatch.test.ts +++ b/packages/transport-commons/test/channels/dispatch.test.ts @@ -1,251 +1,239 @@ -import assert from 'assert'; -import { feathers, Application, HookContext } from '@feathersjs/feathers'; -import { channels } from '../../src/channels'; -import { Channel } from '../../src/channels/channel/base'; -import { CombinedChannel } from '../../src/channels/channel/combined'; +/* eslint-disable @typescript-eslint/no-empty-function */ +import assert from 'assert' +import { feathers, Application, HookContext } from '@feathersjs/feathers' +import { channels } from '../../src/channels' +import { Channel } from '../../src/channels/channel/base' +import { CombinedChannel } from '../../src/channels/channel/combined' class TestService { - events = ['foo']; + events = ['foo'] - async create (payload: any) { - return payload; + async create(payload: any) { + return payload } } describe('app.publish', () => { - let app: Application; + let app: Application beforeEach(() => { - app = feathers().configure(channels()); - }); + app = feathers().configure(channels()) + }) it('throws an error if service does not send the event', () => { try { app.use('/test', { - create (data: any) { - return Promise.resolve(data); + create(data: any) { + return Promise.resolve(data) } - }); + }) - app.service('test').registerPublisher('created', function () {}); - app.service('test').registerPublisher('bla', function () {}); - assert.ok(false, 'Should never get here'); + app.service('test').registerPublisher('created', function () {}) + app.service('test').registerPublisher('bla', function () {}) + assert.ok(false, 'Should never get here') } catch (e: any) { - assert.strictEqual(e.message, '\'bla\' is not a valid service event'); + assert.strictEqual(e.message, "'bla' is not a valid service event") } - }); + }) describe('registration and `dispatch` event', () => { - const c1 = { id: 1, test: true }; - const c2 = { id: 2, test: true }; - const data = { message: 'This is a test' }; + const c1 = { id: 1, test: true } + const c2 = { id: 2, test: true } + const data = { message: 'This is a test' } beforeEach(() => { - app.use('/test', new TestService()); - }); + app.use('/test', new TestService()) + }) it('error in publisher is handled gracefully (#1707)', async () => { app.service('test').publish('created', () => { - throw new Error('Something went wrong'); - }); + throw new Error('Something went wrong') + }) try { - await app.service('test').create({ message: 'something' }); + await app.service('test').create({ message: 'something' }) } catch (error: any) { - assert.fail('Should never get here'); + assert.fail('Should never get here') } - }); + }) - it('simple event registration and dispatching', done => { - app.channel('testing').join(c1); + it('simple event registration and dispatching', (done) => { + app.channel('testing').join(c1) - app.service('test').registerPublisher('created', () => app.channel('testing')); + app.service('test').registerPublisher('created', () => app.channel('testing')) app.once('publish', (event: string, channel: Channel, hook: HookContext) => { try { - assert.strictEqual(event, 'created'); - assert.strictEqual(hook.path, 'test'); - assert.deepStrictEqual(hook.result, data); - assert.deepStrictEqual(channel.connections, [ c1 ]); - done(); + assert.strictEqual(event, 'created') + assert.strictEqual(hook.path, 'test') + assert.deepStrictEqual(hook.result, data) + assert.deepStrictEqual(channel.connections, [c1]) + done() } catch (error: any) { - done(error); + done(error) } - }); + }) - app.service('test') - .create(data) - .catch(done); - }); + app.service('test').create(data).catch(done) + }) - it('app and global level dispatching and precedence', done => { - app.channel('testing').join(c1); - app.channel('other').join(c2); + it('app and global level dispatching and precedence', (done) => { + app.channel('testing').join(c1) + app.channel('other').join(c2) - app.registerPublisher('created', () => app.channel('testing')); - app.registerPublisher(() => app.channel('other')); + app.registerPublisher('created', () => app.channel('testing')) + app.registerPublisher(() => app.channel('other')) app.once('publish', (_event: string, channel: Channel) => { - assert.ok(channel.connections.indexOf(c1) !== -1); - done(); - }); - - app.service('test') - .create(data) - .catch(done); - }); - - it('promise event dispatching', done => { - app.channel('testing').join(c1); - app.channel('othertest').join(c2); - - app.service('test').registerPublisher('created', () => - new Promise(resolve => - setTimeout(() => resolve(app.channel('testing')), 50) + assert.ok(channel.connections.indexOf(c1) !== -1) + done() + }) + + app.service('test').create(data).catch(done) + }) + + it('promise event dispatching', (done) => { + app.channel('testing').join(c1) + app.channel('othertest').join(c2) + + app + .service('test') + .registerPublisher( + 'created', + () => new Promise((resolve) => setTimeout(() => resolve(app.channel('testing')), 50)) ) - ); - app.service('test').registerPublisher('created', () => - new Promise(resolve => - setTimeout(() => resolve(app.channel('testing', 'othertest')), 100) + app + .service('test') + .registerPublisher( + 'created', + () => new Promise((resolve) => setTimeout(() => resolve(app.channel('testing', 'othertest')), 100)) ) - ); app.once('publish', (_event: string, channel: Channel, hook: HookContext) => { - assert.deepStrictEqual(hook.result, data); - assert.deepStrictEqual(channel.connections, [ c1, c2 ]); - done(); - }); + assert.deepStrictEqual(hook.result, data) + assert.deepStrictEqual(channel.connections, [c1, c2]) + done() + }) - app.service('test') - .create(data) - .catch(done); - }); + app.service('test').create(data).catch(done) + }) - it('custom event dispatching', done => { - const eventData = { testing: true }; + it('custom event dispatching', (done) => { + const eventData = { testing: true } - app.channel('testing').join(c1); - app.channel('othertest').join(c2); + app.channel('testing').join(c1) + app.channel('othertest').join(c2) - app.service('test').registerPublisher('foo', () => app.channel('testing')); + app.service('test').registerPublisher('foo', () => app.channel('testing')) app.once('publish', (event: string, channel: Channel, hook: HookContext) => { - assert.strictEqual(event, 'foo'); + assert.strictEqual(event, 'foo') assert.deepStrictEqual(hook, { app, path: 'test', service: app.service('test'), result: eventData - }); - assert.deepStrictEqual(channel.connections, [ c1 ]); - done(); - }); + }) + assert.deepStrictEqual(channel.connections, [c1]) + done() + }) - app.service('test').emit('foo', eventData); - }); + app.service('test').emit('foo', eventData) + }) - it('does not sent `dispatch` event if there are no dispatchers', done => { - app.once('publish', () => - done(new Error('Should never get here')) - ); + it('does not sent `dispatch` event if there are no dispatchers', (done) => { + app.once('publish', () => done(new Error('Should never get here'))) - process.once('unhandledRejection', error => done(error)); + process.once('unhandledRejection', (error) => done(error)) - app.service('test') + app + .service('test') .create(data) .then(() => done()) - .catch(done); - }); - - it('does not send `dispatch` event if there are no connections', done => { - app.service('test').registerPublisher('created', () => - app.channel('dummy') - ); - app.once('publish', () => - done(new Error('Should never get here')) - ); - - app.service('test') + .catch(done) + }) + + it('does not send `dispatch` event if there are no connections', (done) => { + app.service('test').registerPublisher('created', () => app.channel('dummy')) + app.once('publish', () => done(new Error('Should never get here'))) + + app + .service('test') .create(data) .then(() => done()) - .catch(done); - }); + .catch(done) + }) - it('dispatcher returning an array of channels', done => { - app.channel('testing').join(c1); - app.channel('othertest').join(c2); + it('dispatcher returning an array of channels', (done) => { + app.channel('testing').join(c1) + app.channel('othertest').join(c2) - app.service('test').registerPublisher('created', () => [ - app.channel('testing'), - app.channel('othertest') - ]); + app + .service('test') + .registerPublisher('created', () => [app.channel('testing'), app.channel('othertest')]) app.once('publish', (_event: string, channel: Channel, hook: HookContext) => { - assert.deepStrictEqual(hook.result, data); - assert.deepStrictEqual(channel.connections, [ c1, c2 ]); - done(); - }); + assert.deepStrictEqual(hook.result, data) + assert.deepStrictEqual(channel.connections, [c1, c2]) + done() + }) - app.service('test') - .create(data) - .catch(done); - }); + app.service('test').create(data).catch(done) + }) - it('dispatcher can send data', done => { - const c1data = { channel: 'testing' }; + it('dispatcher can send data', (done) => { + const c1data = { channel: 'testing' } - app.channel('testing').join(c1); - app.channel('othertest').join(c2); + app.channel('testing').join(c1) + app.channel('othertest').join(c2) - app.service('test').registerPublisher('created', () => [ - app.channel('testing').send(c1data), - app.channel('othertest') - ]); + app + .service('test') + .registerPublisher('created', () => [app.channel('testing').send(c1data), app.channel('othertest')]) app.once('publish', (_event: string, channel: CombinedChannel, hook: HookContext) => { - assert.deepStrictEqual(hook.result, data); - assert.deepStrictEqual(channel.dataFor(c1), c1data); - assert.ok(channel.dataFor(c2) === null); - assert.deepStrictEqual(channel.connections, [ c1, c2 ]); - done(); - }); + assert.deepStrictEqual(hook.result, data) + assert.deepStrictEqual(channel.dataFor(c1), c1data) + assert.ok(channel.dataFor(c2) === null) + assert.deepStrictEqual(channel.connections, [c1, c2]) + done() + }) - app.service('test').create(data).catch(done); - }); + app.service('test').create(data).catch(done) + }) - it('publisher precedence and preventing publishing', done => { - app.channel('test').join(c1); + it('publisher precedence and preventing publishing', (done) => { + app.channel('test').join(c1) - app.registerPublisher(() => app.channel('test')); - app.service('test').registerPublisher('created', (): null => null); + app.registerPublisher(() => app.channel('test')) + app.service('test').registerPublisher('created', (): null => null) - app.once('publish', () => done(new Error('Should never get here'))); + app.once('publish', () => done(new Error('Should never get here'))) - app.service('test').create(data).then(() => done()).catch(done); - }); + app + .service('test') + .create(data) + .then(() => done()) + .catch(done) + }) - it('data of first channel has precedence', done => { - const sendData = { test: true }; + it('data of first channel has precedence', (done) => { + const sendData = { test: true } - app.channel('testing').join(c1); - app.channel('othertest').join(c1); + app.channel('testing').join(c1) + app.channel('othertest').join(c1) app.service('test').registerPublisher('created', () => { - return [ - app.channel('testing'), - app.channel('othertest').send(sendData) - ]; - }); + return [app.channel('testing'), app.channel('othertest').send(sendData)] + }) app.once('publish', (_event: string, channel: CombinedChannel) => { - assert.strictEqual(channel.dataFor(c1), null); - assert.deepStrictEqual(channel.connections, [ c1 ]); - done(); - }); - - app.service('test') - .create(data) - .catch(done); - }); - }); -}); + assert.strictEqual(channel.dataFor(c1), null) + assert.deepStrictEqual(channel.connections, [c1]) + done() + }) + + app.service('test').create(data).catch(done) + }) + }) +}) diff --git a/packages/transport-commons/test/channels/index.test.ts b/packages/transport-commons/test/channels/index.test.ts index 4c29107777..1aedf10643 100644 --- a/packages/transport-commons/test/channels/index.test.ts +++ b/packages/transport-commons/test/channels/index.test.ts @@ -1,45 +1,44 @@ -import assert from 'assert'; -import { feathers } from '@feathersjs/feathers'; -import { channels, keys } from '../../src/channels'; +/* eslint-disable @typescript-eslint/no-empty-function */ +import assert from 'assert' +import { feathers } from '@feathersjs/feathers' +import { channels, keys } from '../../src/channels' describe('feathers-channels', () => { it('has app.channel', () => { - const app = feathers().configure(channels()); + const app = feathers().configure(channels()) - assert.strictEqual(typeof app.channel, 'function'); - assert.strictEqual(typeof (app as any)[keys.CHANNELS], 'object'); - assert.strictEqual(app.channels.length, 0); - }); + assert.strictEqual(typeof app.channel, 'function') + assert.strictEqual(typeof (app as any)[keys.CHANNELS], 'object') + assert.strictEqual(app.channels.length, 0) + }) it('throws an error when called with nothing', () => { - const app = feathers().configure(channels()); + const app = feathers().configure(channels()) try { - app.channel(); - assert.ok(false, 'Should never get here'); + app.channel() + assert.ok(false, 'Should never get here') } catch (e: any) { - assert.strictEqual(e.message, 'app.channel needs at least one channel name'); + assert.strictEqual(e.message, 'app.channel needs at least one channel name') } - }); + }) it('configuring twice does nothing', () => { - feathers() - .configure(channels()) - .configure(channels()); - }); + feathers().configure(channels()).configure(channels()) + }) it('does not add things to the service if `dispatch` exists', () => { const app = feathers() .configure(channels()) .use('/test', { - async setup () {}, - publish () { - return this; + async setup() {}, + publish() { + return this } - } as any); + } as any) - const service: any = app.service('test') ; + const service: any = app.service('test') - assert.ok(!service[keys.PUBLISHERS]); - }); -}); + assert.ok(!service[keys.PUBLISHERS]) + }) +}) diff --git a/packages/transport-commons/test/client.test.ts b/packages/transport-commons/test/client.test.ts index f141e7f8eb..edd5c01506 100644 --- a/packages/transport-commons/test/client.test.ts +++ b/packages/transport-commons/test/client.test.ts @@ -1,207 +1,211 @@ -import assert from 'assert'; -import { EventEmitter } from 'events'; -import { CustomMethods } from '@feathersjs/feathers'; -import { NotAuthenticated } from '@feathersjs/errors'; -import { Service, SocketService } from '../src/client'; +/* eslint-disable @typescript-eslint/ban-ts-comment, @typescript-eslint/no-empty-function */ +import assert from 'assert' +import { EventEmitter } from 'events' +import { CustomMethods } from '@feathersjs/feathers' +import { NotAuthenticated } from '@feathersjs/errors' +import { Service, SocketService } from '../src/client' -declare type DummyCallback = (err: any, data?: any) => void; +declare type DummyCallback = (err: any, data?: any) => void describe('client', () => { - let connection: any; - let testData: any; - let service: SocketService & CustomMethods<{customMethod: any}> & EventEmitter; + let connection: any + let testData: any + let service: SocketService & CustomMethods<{ customMethod: any }> & EventEmitter beforeEach(() => { - connection = new EventEmitter(); - testData = { data: 'testing ' }; + connection = new EventEmitter() + testData = { data: 'testing ' } service = new Service({ - events: [ 'created' ], + events: ['created'], name: 'todos', method: 'emit', connection - }) as any; - }); + }) as any + }) it('sets `events` property on service', () => { - assert.ok(service.events); - }); + assert.ok(service.events) + }) it('throws an error when the emitter does not have the method', () => { const clientService = new Service({ name: 'todos', method: 'emit', connection: {} - }) as Service & EventEmitter; + }) as Service & EventEmitter try { - clientService.eventNames(); - assert.ok(false, 'Should never get here'); + clientService.eventNames() + assert.ok(false, 'Should never get here') } catch (e: any) { - assert.strictEqual(e.message, 'Can not call \'eventNames\' on the client service connection'); + assert.strictEqual(e.message, "Can not call 'eventNames' on the client service connection") } try { - clientService.on('test', () => {}); - assert.ok(false, 'Should never get here'); + clientService.on('test', () => {}) + assert.ok(false, 'Should never get here') } catch (e: any) { - assert.strictEqual(e.message, 'Can not call \'on\' on the client service connection'); + assert.strictEqual(e.message, "Can not call 'on' on the client service connection") } - }); + }) it('allows chaining event listeners', () => { - assert.strictEqual(service, service.on('thing', () => {})); - assert.strictEqual(service, service.once('other thing', () => {})); - }); - - it('initializes and emits namespaced events', done => { + assert.strictEqual( + service, + service.on('thing', () => {}) + ) + assert.strictEqual( + service, + service.once('other thing', () => {}) + ) + }) + + it('initializes and emits namespaced events', (done) => { connection.once('todos test', (data: any) => { - assert.deepStrictEqual(data, testData); - done(); - }); - service.emit('test', testData); - }); + assert.deepStrictEqual(data, testData) + done() + }) + service.emit('test', testData) + }) it('has other emitter methods', () => { - assert.ok(service.eventNames()); - }); + assert.ok(service.eventNames()) + }) - it('can receive pathed events', done => { - service.once('thing', data => { - assert.deepStrictEqual(data, testData); - done(); - }); + it('can receive pathed events', (done) => { + service.once('thing', (data) => { + assert.deepStrictEqual(data, testData) + done() + }) - connection.emit('todos thing', testData); - }); + connection.emit('todos thing', testData) + }) it('sends all service and custom methods with acknowledgement', async () => { - const idCb = (_path: any, id: any, _params: any, callback: DummyCallback) => - callback(null, { id }); + const idCb = (_path: any, id: any, _params: any, callback: DummyCallback) => callback(null, { id }) const idDataCb = (_path: any, _id: any, data: any, _params: any, callback: DummyCallback) => - callback(null, data); + callback(null, data) const dataCb = (_path: any, data: any, _params: any, callback: DummyCallback) => { - data.created = true; - callback(null, data); - }; + data.created = true + callback(null, data) + } - connection.once('create', dataCb); - service.methods('customMethod'); + connection.once('create', dataCb) + service.methods('customMethod') - let res = await service.create(testData); + let res = await service.create(testData) - assert.ok(res.created); + assert.ok(res.created) - connection.once('get', idCb); - res = await service.get(1); - assert.deepStrictEqual(res, { id: 1 }); + connection.once('get', idCb) + res = await service.get(1) + assert.deepStrictEqual(res, { id: 1 }) - connection.once('remove', idCb); + connection.once('remove', idCb) res = await service.remove(12) - assert.deepStrictEqual(res, { id: 12 }); + assert.deepStrictEqual(res, { id: 12 }) - connection.once('update', idDataCb); - res = await service.update(12, testData); - assert.deepStrictEqual(res, testData); + connection.once('update', idDataCb) + res = await service.update(12, testData) + assert.deepStrictEqual(res, testData) - connection.once('patch', idDataCb); - res = await service.patch(12, testData); - assert.deepStrictEqual(res, testData); + connection.once('patch', idDataCb) + res = await service.patch(12, testData) + assert.deepStrictEqual(res, testData) - connection.once('customMethod', dataCb); - res = await service.customMethod({ message: 'test' }); + connection.once('customMethod', dataCb) + res = await service.customMethod({ message: 'test' }) assert.deepStrictEqual(res, { created: true, message: 'test' - }); + }) - connection.once('find', (_path: any, params: any, callback: DummyCallback) => - callback(null, { params }) - ); + connection.once('find', (_path: any, params: any, callback: DummyCallback) => callback(null, { params })) - res = await service.find({ query: { test: true } }); + res = await service.find({ query: { test: true } }) assert.deepStrictEqual(res, { params: { test: true } - }); - }); + }) + }) it('converts to feathers-errors (#19)', async () => { connection.once('create', (_path: any, _data: any, _params: any, callback: DummyCallback) => callback(new NotAuthenticated('Test', { hi: 'me' }).toJSON()) - ); + ) await assert.rejects(() => service.create(testData), { name: 'NotAuthenticated', message: 'Test', code: 401, data: { hi: 'me' } - }); - }); + }) + }) it('converts other errors (#19)', async () => { - connection.once('create', (_path: string, _data: any, _params: any, callback: (x: string) => void) => + connection.once('create', (_path: string, _data: any, _params: any, callback: (x: string) => void) => { callback('Something went wrong') // eslint-disable-line - ); + }) await assert.rejects(() => service.create(testData), { message: 'Something went wrong' - }); - }); + }) + }) - it('has all EventEmitter methods', done => { - const testing = { hello: 'world' }; + it('has all EventEmitter methods', (done) => { + const testing = { hello: 'world' } const callback = (data: any) => { - assert.deepStrictEqual(data, testing); - assert.strictEqual(service.listenerCount('test'), 1); - service.removeListener('test', callback); - assert.strictEqual(service.listenerCount('test'), 0); - done(); - }; + assert.deepStrictEqual(data, testing) + assert.strictEqual(service.listenerCount('test'), 1) + service.removeListener('test', callback) + assert.strictEqual(service.listenerCount('test'), 0) + done() + } - service.addListener('test', callback); + service.addListener('test', callback) - connection.emit('todos test', testing); - }); + connection.emit('todos test', testing) + }) - it('properly handles on/off methods', done => { - const testing = { hello: 'world' }; + it('properly handles on/off methods', (done) => { + const testing = { hello: 'world' } const callback1 = (data: any) => { - assert.deepStrictEqual(data, testing); - assert.strictEqual(service.listenerCount('test'), 3); - service.off('test', callback1); - assert.strictEqual(service.listenerCount('test'), 2); - service.removeAllListeners('test'); - assert.strictEqual(service.listenerCount('test'), 0); - done(); - }; + assert.deepStrictEqual(data, testing) + assert.strictEqual(service.listenerCount('test'), 3) + service.off('test', callback1) + assert.strictEqual(service.listenerCount('test'), 2) + service.removeAllListeners('test') + assert.strictEqual(service.listenerCount('test'), 0) + done() + } const callback2 = () => { // noop - }; + } - service.on('test', callback1); - service.on('test', callback2); - service.on('test', callback2); + service.on('test', callback1) + service.on('test', callback2) + service.on('test', callback2) - connection.emit('todos test', testing); - }); + connection.emit('todos test', testing) + }) it('forwards namespaced call to .off, returns service instance', () => { // Use it's own connection and service so off method gets detected - const conn = new EventEmitter(); + const conn = new EventEmitter() // @ts-ignore conn.off = function (name) { - assert.strictEqual(name, 'todos test'); + assert.strictEqual(name, 'todos test') - return this; - }; + return this + } const client = new Service({ name: 'todos', method: 'emit', connection: conn - }); + }) - assert.strictEqual(client.off('test'), client); - }); -}); + assert.strictEqual(client.off('test'), client) + }) +}) diff --git a/packages/transport-commons/test/http.test.ts b/packages/transport-commons/test/http.test.ts index 2856a70657..dfbe4ef74f 100644 --- a/packages/transport-commons/test/http.test.ts +++ b/packages/transport-commons/test/http.test.ts @@ -1,42 +1,63 @@ -import assert from 'assert'; -import { HookContext } from '@feathersjs/feathers'; -import { http } from '../src'; +import assert from 'assert' +import { HookContext } from '@feathersjs/feathers' +import { http } from '../src' describe('@feathersjs/transport-commons HTTP helpers', () => { - it('getData', () => { - const plainData = { message: 'hi' }; - const dispatch = { message: 'from dispatch' }; + it('getResponse body', () => { + const plainData = { message: 'hi' } + const dispatch = { message: 'from dispatch' } const resultContext = { result: plainData - }; + } const dispatchContext = { dispatch - }; + } - assert.deepStrictEqual(http.getData(resultContext as HookContext), plainData); - assert.deepStrictEqual(http.getData(dispatchContext as HookContext), dispatch); - }); + assert.strictEqual(http.getResponse(resultContext as HookContext).body, plainData) + assert.strictEqual(http.getResponse(dispatchContext as HookContext).body, dispatch) + }) - it('getStatusCode', async () => { + it('getResponse status', () => { const statusContext = { - http: { statusCode: 202 } - }; + http: { status: 202 } + } const createContext = { method: 'create' - }; + } + const redirectContext = { + http: { location: '/' } + } - assert.strictEqual(http.getStatusCode(statusContext as HookContext, {}), 202); - assert.strictEqual(http.getStatusCode(createContext as HookContext, {}), http.statusCodes.created); - assert.strictEqual(http.getStatusCode({} as HookContext), http.statusCodes.noContent); - assert.strictEqual(http.getStatusCode({} as HookContext, {}), http.statusCodes.success); - }); + assert.strictEqual(http.getResponse(statusContext as HookContext).status, 202) + assert.strictEqual(http.getResponse(createContext as HookContext).status, http.statusCodes.created) + assert.strictEqual(http.getResponse(redirectContext as HookContext).status, http.statusCodes.seeOther) + assert.strictEqual(http.getResponse({} as HookContext).status, http.statusCodes.noContent) + assert.strictEqual(http.getResponse({ result: true } as HookContext).status, http.statusCodes.success) + }) + + it('getResponse headers', () => { + const headers = { key: 'value' } as any + const headersContext = { + http: { headers } + } + const locationContext = { + http: { location: '/' } + } + + assert.deepStrictEqual(http.getResponse({} as HookContext).headers, {}) + assert.deepStrictEqual(http.getResponse({ http: {} } as HookContext).headers, {}) + assert.strictEqual(http.getResponse(headersContext as HookContext).headers, headers) + assert.deepStrictEqual(http.getResponse(locationContext as HookContext).headers, { + Location: '/' + }) + }) it('getServiceMethod', () => { - assert.strictEqual(http.getServiceMethod('GET', 2), 'get'); - assert.strictEqual(http.getServiceMethod('GET', null), 'find'); - assert.strictEqual(http.getServiceMethod('PoST', null), 'create'); - assert.strictEqual(http.getServiceMethod('PoST', null, 'customMethod'), 'customMethod'); - assert.strictEqual(http.getServiceMethod('delete', null), 'remove'); - assert.throws(() => http.getServiceMethod('nonsense', null)); - }); -}); + assert.strictEqual(http.getServiceMethod('GET', 2), 'get') + assert.strictEqual(http.getServiceMethod('GET', null), 'find') + assert.strictEqual(http.getServiceMethod('PoST', null), 'create') + assert.strictEqual(http.getServiceMethod('PoST', null, 'customMethod'), 'customMethod') + assert.strictEqual(http.getServiceMethod('delete', null), 'remove') + assert.throws(() => http.getServiceMethod('nonsense', null)) + }) +}) diff --git a/packages/transport-commons/test/routing/index.test.ts b/packages/transport-commons/test/routing/index.test.ts index eeec0e6898..0131533b3f 100644 --- a/packages/transport-commons/test/routing/index.test.ts +++ b/packages/transport-commons/test/routing/index.test.ts @@ -1,105 +1,120 @@ -import assert from 'assert'; -import { feathers, Application } from '@feathersjs/feathers'; -import { routing } from '../../src/routing'; +/* eslint-disable @typescript-eslint/ban-ts-comment */ +import assert from 'assert' +import { feathers, Application } from '@feathersjs/feathers' +import { routing } from '../../src/routing' describe('app.routes', () => { - let app: Application; + let app: Application beforeEach(() => { - app = feathers().configure(routing()); + app = feathers().configure(routing()) app.use('/my/service', { - get (id: string|number) { - return Promise.resolve({ id }); + get(id: string | number) { + return Promise.resolve({ id }) } - }); - }); + }) + }) it('does nothing when configured twice', () => { - feathers().configure(routing()).configure(routing()); - }); + feathers().configure(routing()).configure(routing()) + }) it('has app.lookup and app.routes', () => { - assert.strictEqual(typeof app.lookup, 'function'); - assert.ok(app.routes); - }); + assert.strictEqual(typeof app.lookup, 'function') + assert.ok(app.routes) + }) it('returns null when nothing is found', () => { - const result = app.lookup('me/service'); + const result = app.lookup('me/service') - assert.strictEqual(result, null); - }); + assert.strictEqual(result, null) + }) it('returns null for invalid service path', () => { - assert.strictEqual(app.lookup(null), null); + assert.strictEqual(app.lookup(null), null) // @ts-ignore - assert.strictEqual(app.lookup({}), null); - }); + assert.strictEqual(app.lookup({}), null) + }) it('can look up and strips slashes', () => { - const result = app.lookup('my/service'); + const result = app.lookup('my/service') - assert.strictEqual(result.service, app.service('/my/service/')); - }); + assert.strictEqual(result.service, app.service('/my/service/')) + }) it('can look up with id', () => { - const result = app.lookup('/my/service/1234'); + const result = app.lookup('/my/service/1234') - assert.strictEqual(result.service, app.service('/my/service')); + assert.strictEqual(result.service, app.service('/my/service')) assert.deepStrictEqual(result.params, { __id: '1234' - }); - }); + }) + }) it('can look up with params, id and special characters', () => { - const path = '/test/:first/my/:second'; + const path = '/test/:first/my/:second' app.use(path, { - async get (id: string|number) { - return { id }; + async get(id: string | number) { + return { id } } - }); + }) - const result = app.lookup('/test/me/my/::special/testing'); + const result = app.lookup('/test/me/my/::special/testing') - assert.strictEqual(result.service, app.service(path)); + assert.strictEqual(result.service, app.service(path)) assert.deepStrictEqual(result.params, { __id: 'testing', first: 'me', second: '::special' - }); - }); + }) + }) it('can register routes with preset params', () => { app.routes.insert('/my/service/:__id/preset', { service: app.service('/my/service'), params: { preset: true } - }); + }) - const result = app.lookup('/my/service/1234/preset'); + const result = app.lookup('/my/service/1234/preset') - assert.strictEqual(result.service, app.service('/my/service')); + assert.strictEqual(result.service, app.service('/my/service')) assert.deepStrictEqual(result.params, { preset: true, __id: '1234' - }); - }); + }) + }) it('can pass route params during a service registration', () => { - app.use('/other/service', { - async get (id: any) { - return id; + app.use( + '/other/service', + { + async get(id: any) { + return id + } + }, + { + routeParams: { used: true } } - }, { - routeParams: { used: true } - }); + ) - const result = app.lookup('/other/service/1234'); + const result = app.lookup('/other/service/1234') - assert.strictEqual(result.service, app.service('/other/service')); + assert.strictEqual(result.service, app.service('/other/service')) assert.deepStrictEqual(result.params, { used: true, __id: '1234' - }); - }); -}); + }) + }) + + it('can unregister a service (#2035)', async () => { + const result = app.lookup('my/service') + + assert.strictEqual(result.service, app.service('/my/service/')) + + await app.unuse('/my/service') + + assert.strictEqual(app.lookup('my/service'), null) + }) +}) diff --git a/packages/transport-commons/test/routing/router.test.ts b/packages/transport-commons/test/routing/router.test.ts index e9590ffa3e..307aeccbd8 100644 --- a/packages/transport-commons/test/routing/router.test.ts +++ b/packages/transport-commons/test/routing/router.test.ts @@ -1,62 +1,62 @@ -import assert from 'assert'; -import { Router } from '../../src/routing'; +import assert from 'assert' +import { Router } from '../../src/routing' describe('router', () => { it('can lookup and insert a simple path and returns null for invalid path', () => { - const r = new Router(); + const r = new Router() - r.insert('/hello/there/you', 'test'); + r.insert('/hello/there/you', 'test') - const result = r.lookup('hello/there/you/'); + const result = r.lookup('hello/there/you/') assert.deepStrictEqual(result, { params: {}, data: 'test' - }); + }) - assert.strictEqual(r.lookup('not/there'), null); - assert.strictEqual(r.lookup('not-me'), null); - }); + assert.strictEqual(r.lookup('not/there'), null) + assert.strictEqual(r.lookup('not-me'), null) + }) it('can insert data at the root', () => { - const r = new Router(); + const r = new Router() - r.insert('', 'hi'); + r.insert('', 'hi') - const result = r.lookup('/'); + const result = r.lookup('/') assert.deepStrictEqual(result, { params: {}, data: 'hi' - }); - }); + }) + }) it('can insert with placeholder and has proper specificity', () => { - const r = new Router(); + const r = new Router() - r.insert('/hello/:id', 'one'); - r.insert('/hello/:id/you', 'two'); - r.insert('/hello/:id/:other', 'three'); + r.insert('/hello/:id', 'one') + r.insert('/hello/:id/you', 'two') + r.insert('/hello/:id/:other', 'three') - const first = r.lookup('hello/there/'); + const first = r.lookup('hello/there/') assert.throws(() => r.insert('/hello/:id/you', 'two'), { message: 'Path hello/:id/you already exists' - }); + }) assert.deepStrictEqual(first, { params: { id: 'there' }, data: 'one' - }); + }) - const second = r.lookup('hello/yes/you'); + const second = r.lookup('hello/yes/you') assert.deepStrictEqual(second, { params: { id: 'yes' }, data: 'two' - }); + }) - const third = r.lookup('hello/yes/they'); + const third = r.lookup('hello/yes/they') assert.deepStrictEqual(third, { params: { @@ -64,35 +64,58 @@ describe('router', () => { other: 'they' }, data: 'three' - }); + }) - assert.strictEqual(r.lookup('hello/yes/they/here'), null); - }); + assert.strictEqual(r.lookup('hello/yes/they/here'), null) + }) it('works with different placeholders in different paths (#2327)', () => { - const r = new Router(); + const r = new Router() - r.insert('/hello/:id', 'one'); - r.insert('/hello/:test/you', 'two'); - r.insert('/hello/:test/:two/hi/:three', 'three'); - r.insert('/hello/:test/:two/hi', 'four'); + r.insert('/hello/:id', 'one') + r.insert('/hello/:test/you', 'two') + r.insert('/hello/:test/:two/hi/:three', 'three') + r.insert('/hello/:test/:two/hi', 'four') assert.deepStrictEqual(r.lookup('/hello/there'), { params: { id: 'there' }, data: 'one' - }); + }) assert.deepStrictEqual(r.lookup('/hello/there/you'), { params: { test: 'there' }, data: 'two' - }); - assert.strictEqual(r.lookup('/hello/there/bla'), null); + }) + assert.strictEqual(r.lookup('/hello/there/bla'), null) assert.deepStrictEqual(r.lookup('/hello/there/maybe/hi'), { params: { test: 'there', two: 'maybe' }, data: 'four' - }); + }) assert.deepStrictEqual(r.lookup('/hello/there/maybe/hi/test'), { params: { three: 'test', two: 'maybe', test: 'there' }, data: 'three' - }); - }); -}); + }) + }) + + it('can remove paths (#2035)', () => { + const r = new Router() + + r.insert('/hello/:id', 'one') + r.insert('/hello/:test/you', 'two') + r.insert('/hello/here/thing', 'else') + + assert.deepStrictEqual(r.lookup('hello/there'), { params: { id: 'there' }, data: 'one' }) + + r.remove('/hello/:id') + + assert.deepStrictEqual(r.lookup('hello/here/you'), { params: { test: 'here' }, data: 'two' }) + assert.deepStrictEqual(r.lookup('hello/here/thing'), { params: {}, data: 'else' }) + assert.strictEqual(r.lookup('hello/there'), null) + + r.remove('/hello/:test/you') + assert.deepStrictEqual(r.lookup('hello/here/you'), null) + assert.deepStrictEqual(r.lookup('hello/here/thing'), { params: {}, data: 'else' }) + + r.remove('/hello/here/thing') + assert.ok(!r.root.hasChildren) + }) +}) diff --git a/packages/transport-commons/test/socket/index.test.ts b/packages/transport-commons/test/socket/index.test.ts index 09fa96bada..e2c107f7d1 100644 --- a/packages/transport-commons/test/socket/index.test.ts +++ b/packages/transport-commons/test/socket/index.test.ts @@ -1,22 +1,22 @@ -import assert from 'assert'; -import { EventEmitter } from 'events'; -import { feathers, Application, Id, Params } from '@feathersjs/feathers'; +import assert from 'assert' +import { EventEmitter } from 'events' +import { feathers, Application, Id, Params } from '@feathersjs/feathers' -import { socket as commons, SocketOptions } from '../../src/socket'; +import { socket as commons, SocketOptions } from '../../src/socket' class DummyService { - async get (id: Id, params: Params) { - return { id, params }; + async get(id: Id, params: Params) { + return { id, params } } - async create (data: any, params: Params) { + async create(data: any, params: Params) { return { ...data, params - }; + } } - async custom (data: any, params: Params) { + async custom(data: any, params: Params) { return { ...data, params, @@ -26,135 +26,156 @@ class DummyService { } describe('@feathersjs/transport-commons', () => { - let provider: EventEmitter; - let options: SocketOptions; - let app: Application; - let connection: any; + let provider: EventEmitter + let options: SocketOptions + let app: Application + let connection: any beforeEach(() => { - connection = { testing: true }; - provider = new EventEmitter(); + connection = { testing: true } + provider = new EventEmitter() options = { emit: 'emit', done: Promise.resolve(provider), socketMap: new WeakMap(), - getParams () { - return connection; + getParams() { + return connection } - }; + } app = feathers() .configure(commons(options)) .use('/myservice', new DummyService(), { - methods: [ 'get', 'create', 'custom' ] - }); + methods: ['get', 'create', 'custom'] + }) - return options.done; - }); + return options.done + }) - it('`connection` event', done => { - const socket = new EventEmitter(); + it('`connection` event', (done) => { + const socket = new EventEmitter() - app.once('connection', data => { - assert.strictEqual(connection, data); - done(); - }); + app.once('connection', (data) => { + assert.strictEqual(connection, data) + done() + }) - provider.emit('connection', socket); - }); + provider.emit('connection', socket) + }) describe('method name based socket events', () => { - it('.get without params', done => { - const socket = new EventEmitter(); + it('.get without params', (done) => { + const socket = new EventEmitter() - provider.emit('connection', socket); + provider.emit('connection', socket) socket.emit('get', 'myservice', 10, (error: any, result: any) => { try { - assert.ok(!error); + assert.ok(!error) assert.deepStrictEqual(result, { id: 10, - params: Object.assign({ - query: {}, - route: {}, + params: Object.assign( + { + query: {}, + route: {}, + connection + }, connection - }, connection) - }); - done(); + ) + }) + done() } catch (e: any) { - done(e); + done(e) } - }); - }); + }) + }) - it('.get with invalid service name and arguments', done => { - const socket = new EventEmitter(); + it('.get with invalid service name and arguments', (done) => { + const socket = new EventEmitter() - provider.emit('connection', socket); + provider.emit('connection', socket) socket.emit('get', null, (error: any) => { - assert.strictEqual(error.name, 'NotFound'); - assert.strictEqual(error.message, 'Service \'null\' not found'); - done(); - }); - }); - - it('.create with params', done => { - const socket = new EventEmitter(); + assert.strictEqual(error.name, 'NotFound') + assert.strictEqual(error.message, "Service 'null' not found") + done() + }) + }) + + it('.create with params', (done) => { + const socket = new EventEmitter() const data = { test: 'data' - }; - - provider.emit('connection', socket); + } - socket.emit('create', 'myservice', data, { - fromQuery: true - }, (error: any, result: any) => { - try { - const params = Object.assign({ - query: { fromQuery: true }, - route: {}, - connection - }, connection); - - assert.ok(!error); - assert.deepStrictEqual(result, Object.assign({ params }, data)); - done(); - } catch (e: any) { - done(e); + provider.emit('connection', socket) + + socket.emit( + 'create', + 'myservice', + data, + { + fromQuery: true + }, + (error: any, result: any) => { + try { + const params = Object.assign( + { + query: { fromQuery: true }, + route: {}, + connection + }, + connection + ) + + assert.ok(!error) + assert.deepStrictEqual(result, Object.assign({ params }, data)) + done() + } catch (e: any) { + done(e) + } } - }); - }); + ) + }) - it('custom method with params', done => { - const socket = new EventEmitter(); + it('custom method with params', (done) => { + const socket = new EventEmitter() const data = { test: 'data' - }; - - provider.emit('connection', socket); - - socket.emit('custom', 'myservice', data, { - fromQuery: true - }, (error: any, result: any) => { - try { - const params = Object.assign({ - query: { fromQuery: true }, - route: {}, - connection - }, connection); + } - assert.ok(!error); - assert.deepStrictEqual(result, { - ...data, - params, - message: 'From custom method' - }); - done(); - } catch (e: any) { - done(e); + provider.emit('connection', socket) + + socket.emit( + 'custom', + 'myservice', + data, + { + fromQuery: true + }, + (error: any, result: any) => { + try { + const params = Object.assign( + { + query: { fromQuery: true }, + route: {}, + connection + }, + connection + ) + + assert.ok(!error) + assert.deepStrictEqual(result, { + ...data, + params, + message: 'From custom method' + }) + done() + } catch (e: any) { + done(e) + } } - }); - }); - }); -}); + ) + }) + }) +}) diff --git a/packages/transport-commons/test/socket/utils.test.ts b/packages/transport-commons/test/socket/utils.test.ts index 9695ac1499..eba454834b 100644 --- a/packages/transport-commons/test/socket/utils.test.ts +++ b/packages/transport-commons/test/socket/utils.test.ts @@ -1,224 +1,243 @@ -import assert from 'assert'; -import { EventEmitter } from 'events'; -import { feathers, Application, Params } from '@feathersjs/feathers'; -import { NotAuthenticated } from '@feathersjs/errors'; - -import { routing } from '../../src/routing'; -import { - normalizeError, - getDispatcher, - runMethod -} from '../../src/socket/utils'; -import { RealTimeConnection } from '../../src/channels/channel/base'; +import assert from 'assert' +import { EventEmitter } from 'events' +import { feathers, Application, Params } from '@feathersjs/feathers' +import { NotAuthenticated } from '@feathersjs/errors' +import { isPlainObject } from 'lodash' + +import { routing } from '../../src/routing' +import { normalizeError, getDispatcher, runMethod } from '../../src/socket/utils' +import { RealTimeConnection } from '../../src/channels/channel/base' describe('socket commons utils', () => { describe('.normalizeError', () => { it('simple error normalization', () => { - const message = 'Something went wrong'; - const e = new Error(message); + const message = 'Something went wrong' + const e = new Error(message) assert.deepStrictEqual(normalizeError(e), { message, stack: e.stack.toString() - }); - }); + }) + }) it('calls .toJSON', () => { - const json = { message: 'toJSON called' }; + const json = { message: 'toJSON called' } - assert.deepStrictEqual(normalizeError({ - toJSON () { - return json; - } - }), json); - }); + assert.deepStrictEqual( + normalizeError({ + toJSON() { + return json + } + }), + json + ) + }) it('removes `hook` property', () => { const e = { hook: true - }; + } - assert.deepStrictEqual(normalizeError(e), {}); - assert.ok(e.hook, 'Does not mutate the original object'); - }); + assert.deepStrictEqual(normalizeError(e), {}) + assert.ok(e.hook, 'Does not mutate the original object') + }) it('hides stack in production', () => { - const oldEnv = process.env.NODE_ENV; + const oldEnv = process.env.NODE_ENV - process.env.NODE_ENV = 'production'; + process.env.NODE_ENV = 'production' - const message = 'Something went wrong'; - const e = new Error(message); - const normalized = normalizeError(e); + const message = 'Something went wrong' + const e = new Error(message) + const normalized = normalizeError(e) - assert.strictEqual(normalized.message, message); - assert.ok(!normalized.stack); + assert.strictEqual(normalized.message, message) + assert.ok(!normalized.stack) - process.env.NODE_ENV = oldEnv; - }); - }); + process.env.NODE_ENV = oldEnv + }) + }) describe('.getDispatcher', () => { it('returns a dispatcher function', () => - assert.strictEqual(typeof getDispatcher('test', new WeakMap()), 'function') - ); + assert.strictEqual(typeof getDispatcher('test', new WeakMap()), 'function')) - it('works with backwards compatible socketKey', done => { - const socketKey = Symbol('@feathersjs/test'); - const dispatcher = getDispatcher('emit', undefined, socketKey); - const socket = new EventEmitter(); + it('works with backwards compatible socketKey', (done) => { + const socketKey = Symbol('@feathersjs/test') + const dispatcher = getDispatcher('emit', undefined, socketKey) + const socket = new EventEmitter() const connection = { [socketKey]: socket - }; + } const channel: any = { - connections: [ connection ], - dataFor (): null { - return null; + connections: [connection], + dataFor(): null { + return null } - }; + } - socket.once('testing', data => { - assert.strictEqual(data, 'hi'); - done(); - }); + socket.once('testing', (data) => { + assert.strictEqual(data, 'hi') + done() + }) - dispatcher('testing', channel, { result: 'hi' } as any); - }); + dispatcher('testing', channel, { result: 'hi' } as any) + }) describe('dispatcher logic', () => { - let dispatcher: any; - let dummySocket: EventEmitter; - let dummyHook: any; - let dummyChannel: any; - let dummyConnection: RealTimeConnection; - let dummyMap: WeakMap; + let dispatcher: any + let dummySocket: EventEmitter + let dummyHook: any + let dummyChannel: any + let dummyConnection: RealTimeConnection + let dummyMap: WeakMap beforeEach(() => { - dummyConnection = {}; - dummyMap = new WeakMap(); - dispatcher = getDispatcher('emit', dummyMap); - dummySocket = new EventEmitter(); - dummyHook = { result: 'hi' }; + dummyConnection = {} + dummyMap = new WeakMap() + dispatcher = getDispatcher('emit', dummyMap) + dummySocket = new EventEmitter() + dummyHook = { result: 'hi' } dummyChannel = { - connections: [ dummyConnection ], - dataFor (): null { - return null; + connections: [dummyConnection], + dataFor(): null { + return null } - }; - dummyMap.set(dummyConnection, dummySocket); - }); + } + dummyMap.set(dummyConnection, dummySocket) + }) - it('dispatches a basic event', done => { - dummySocket.once('testing', data => { - assert.strictEqual(data, 'hi'); - done(); - }); + it('dispatches a basic event', (done) => { + dummySocket.once('testing', (data) => { + assert.strictEqual(data, 'hi') + done() + }) - dispatcher('testing', dummyChannel, dummyHook); - }); + dispatcher('testing', dummyChannel, dummyHook) + }) - it('dispatches event on a hooks path event', done => { - dummyHook.path = 'myservice'; + it('dispatches event on a hooks path event', (done) => { + dummyHook.path = 'myservice' - dummySocket.once('myservice testing', data => { - assert.strictEqual(data, 'hi'); - done(); - }); + dummySocket.once('myservice testing', (data) => { + assert.strictEqual(data, 'hi') + done() + }) - dispatcher('testing', dummyChannel, dummyHook); - }); + dispatcher('testing', dummyChannel, dummyHook) + }) - it('dispatches `hook.dispatch` instead', done => { - const message = 'hi from dispatch'; + it('dispatches `hook.dispatch` instead', (done) => { + const message = 'hi from dispatch' - dummyHook.dispatch = message; + dummyHook.dispatch = message - dummySocket.once('testing', data => { - assert.strictEqual(data, message); - done(); - }); + dummySocket.once('testing', (data) => { + assert.strictEqual(data, message) + done() + }) - dispatcher('testing', dummyChannel, dummyHook); - }); + dispatcher('testing', dummyChannel, dummyHook) + }) it('does nothing if there is no socket', () => { - dummyChannel.connections[0].test = null; + dummyChannel.connections[0].test = null - dispatcher('testing', dummyChannel, dummyHook); - }); + dispatcher('testing', dummyChannel, dummyHook) + }) - it('dispatches arrays properly hook events', done => { - const data1 = { message: 'First message' }; - const data2 = { message: 'Second message' }; + it('dispatches arrays properly hook events', (done) => { + const data1 = { message: 'First message' } + const data2 = { message: 'Second message' } - dummyHook.result = [ data1, data2 ]; + dummyHook.result = [data1, data2] - dummySocket.once('testing', data => { - assert.deepStrictEqual(data, data1); - dummySocket.once('testing', result => { - assert.deepStrictEqual(result, data2); - done(); - }); - }); + dummySocket.once('testing', (data) => { + assert.deepStrictEqual(data, data1) + dummySocket.once('testing', (result) => { + assert.deepStrictEqual(result, data2) + done() + }) + }) - dispatcher('testing', dummyChannel, dummyHook, data1); - dispatcher('testing', dummyChannel, dummyHook, data2); - }); + dispatcher('testing', dummyChannel, dummyHook, data1) + dispatcher('testing', dummyChannel, dummyHook, data2) + }) - it('dispatches arrays properly for custom events', done => { - const result = [ - { message: 'First' }, - { message: 'Second' } - ]; + it('dispatches arrays properly for custom events', (done) => { + const result = [{ message: 'First' }, { message: 'Second' }] - dummyHook.result = result; + dummyHook.result = result - dummySocket.once('otherEvent', data => { - assert.deepStrictEqual(data, result); - done(); - }); + dummySocket.once('otherEvent', (data) => { + assert.deepStrictEqual(data, result) + done() + }) - dispatcher('otherEvent', dummyChannel, dummyHook, result); - }); - }); - }); + dispatcher('otherEvent', dummyChannel, dummyHook, result) + }) + }) + }) describe('.runMethod', () => { - let app: Application; + let app: Application beforeEach(() => { - app = feathers().configure(routing()); + app = feathers().configure(routing()) app.use('/myservice', { - get (id: number|string, params: Params) { + async get(id: number | string, params: Params) { if (params.query.error) { - return Promise.reject(new NotAuthenticated('None shall pass')); + throw new NotAuthenticated('None shall pass') + } + if (!isPlainObject(params.query)) { + throw new Error('Query is not a plain object') } - return Promise.resolve({ id }); + + return { id } } - }); - }); + }) + }) describe('running methods', () => { - it('basic', done => { + it('basic', (done) => { const callback = (error: any, result: any) => { if (error) { - return done(error); + return done(error) } - assert.deepStrictEqual(result, { id: 10 }); - done(); - }; + assert.deepStrictEqual(result, { id: 10 }) + done() + } - runMethod(app, {}, 'myservice', 'get', [ 10, {}, callback ]); - }); + runMethod(app, {}, 'myservice', 'get', [10, {}, callback]) + }) - it('merges params with connection and passes connection', done => { + it('queries are always plain objects', (done) => { + const callback = (error: any, result: any) => { + if (error) { + return done(error) + } + + assert.deepStrictEqual(result, { id: 10 }) + done() + } + + runMethod(app, {}, 'myservice', 'get', [ + 10, + { + __proto__: [] + }, + callback + ]) + }) + + it('merges params with connection and passes connection', (done) => { const connection = { testing: true - }; + } const callback = (error: any, result: any) => { if (error) { - return done(error); + return done(error) } assert.deepStrictEqual(result, { @@ -229,117 +248,118 @@ describe('socket commons utils', () => { route: {}, testing: true } - }); - done(); - }; + }) + done() + } app.use('/otherservice', { - get (id, params) { - return Promise.resolve({ id, params }); + get(id, params) { + return Promise.resolve({ id, params }) } - }); + }) - runMethod(app, connection, 'otherservice', 'get', [ 10, {}, callback ]); - }); + runMethod(app, connection, 'otherservice', 'get', [10, {}, callback]) + }) - it('with params missing', done => { + it('with params missing', (done) => { const callback = (error: any, result: any) => { if (error) { - return done(error); + return done(error) } - assert.deepStrictEqual(result, { id: 10 }); - done(); - }; + assert.deepStrictEqual(result, { id: 10 }) + done() + } - runMethod(app, {}, 'myservice', 'get', [ 10, callback ]); - }); + runMethod(app, {}, 'myservice', 'get', [10, callback]) + }) - it('with params but missing callback', done => { + it('with params but missing callback', (done) => { app.use('/otherservice', { - get (id: number|string) { - assert.strictEqual(id, 'dishes'); + get(id: number | string) { + assert.strictEqual(id, 'dishes') - return Promise.resolve({ id }).then(res => { - done(); - return res; - }); + return Promise.resolve({ id }).then((res) => { + done() + return res + }) } - }); + }) - runMethod(app, {}, 'otherservice', 'get', [ 'dishes', {} ]); - }); + runMethod(app, {}, 'otherservice', 'get', ['dishes', {}]) + }) - it('with params and callback missing', done => { + it('with params and callback missing', (done) => { app.use('/otherservice', { - get (id: number|string) { - assert.strictEqual(id, 'laundry'); + get(id: number | string) { + assert.strictEqual(id, 'laundry') - return Promise.resolve({ id }).then(res => { - done(); - return res; - }); + return Promise.resolve({ id }).then((res) => { + done() + return res + }) } - }); + }) - runMethod(app, {}, 'otherservice', 'get', [ 'laundry' ]); - }); - }); + runMethod(app, {}, 'otherservice', 'get', ['laundry']) + }) + }) - it('throws NotFound for invalid service', done => { + it('throws NotFound for invalid service', (done) => { const callback = (error: any) => { try { - assert.deepStrictEqual(error, { name: 'NotFound', - message: 'Service \'ohmyservice\' not found', + assert.deepStrictEqual(error, { + name: 'NotFound', + message: "Service 'ohmyservice' not found", code: 404, className: 'not-found' - }); - done(); + }) + done() } catch (e: any) { - done(e); + done(e) } - }; + } - runMethod(app, {}, 'ohmyservice', 'get', [ 10, callback ]); - }); + runMethod(app, {}, 'ohmyservice', 'get', [10, callback]) + }) - it('throws MethodNotAllowed undefined method', done => { + it('throws MethodNotAllowed undefined method', (done) => { const callback = (error: any) => { try { assert.deepStrictEqual(error, { name: 'MethodNotAllowed', - message: 'Method \'create\' not allowed on service \'myservice\'', + message: "Method 'create' not allowed on service 'myservice'", code: 405, className: 'method-not-allowed' - }); - done(); + }) + done() } catch (e: any) { - done(e); + done(e) } - }; + } - runMethod(app, {}, 'myservice', 'create', [ {}, callback ]); - }); + runMethod(app, {}, 'myservice', 'create', [{}, callback]) + }) - it('throws MethodNotAllowed for invalid service method', done => { + it('throws MethodNotAllowed for invalid service method', (done) => { const callback = (error: any) => { try { assert.deepStrictEqual(error, { name: 'MethodNotAllowed', - message: 'Method \'blabla\' not allowed on service \'myservice\'', + message: "Method 'blabla' not allowed on service 'myservice'", code: 405, className: 'method-not-allowed' - }); - done(); + }) + done() } catch (e: any) { - done(e); + done(e) } - }; + } - runMethod(app, {}, 'myservice', 'blabla', [ {}, callback ]); - }); + runMethod(app, {}, 'myservice', 'blabla', [{}, callback]) + }) - it('method error calls back with normalized error', done => { + it('method error calls back with normalized error', (done) => { const callback = (error: any) => { try { assert.deepStrictEqual(error, { @@ -347,16 +367,14 @@ describe('socket commons utils', () => { message: 'None shall pass', code: 401, className: 'not-authenticated' - }); - done(); + }) + done() } catch (e: any) { - done(e); + done(e) } - }; - - runMethod(app, {}, 'myservice', 'get', [ - 42, { error: true }, callback - ]); - }); - }); -}); + } + + runMethod(app, {}, 'myservice', 'get', [42, { error: true }, callback]) + }) + }) +}) diff --git a/packages/typebox/CHANGELOG.md b/packages/typebox/CHANGELOG.md new file mode 100644 index 0000000000..11dda6c6c0 --- /dev/null +++ b/packages/typebox/CHANGELOG.md @@ -0,0 +1,16 @@ +# Change Log + +All notable changes to this project will be documented in this file. +See [Conventional Commits](https://conventionalcommits.org) for commit guidelines. + +# [5.0.0-pre.31](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.30...v5.0.0-pre.31) (2022-10-12) + +### Features + +- **cli:** Improve generated schema definitions ([#2783](https://github.com/feathersjs/feathers/issues/2783)) ([474a9fd](https://github.com/feathersjs/feathers/commit/474a9fda2107e9bcf357746320a8e00cda8182b6)) + +# [5.0.0-pre.30](https://github.com/feathersjs/feathers/compare/v5.0.0-pre.29...v5.0.0-pre.30) (2022-10-07) + +### Features + +- **schema:** Make schemas validation library independent and add TypeBox support ([#2772](https://github.com/feathersjs/feathers/issues/2772)) ([44172d9](https://github.com/feathersjs/feathers/commit/44172d99b566d11d9ceda04f1d0bf72b6d05ce76)) diff --git a/packages/typebox/LICENSE b/packages/typebox/LICENSE new file mode 100644 index 0000000000..59604f46f3 --- /dev/null +++ b/packages/typebox/LICENSE @@ -0,0 +1,22 @@ +The MIT License (MIT) + +Copyright (c) 2022 Feathers + +Permission is hereby granted, free of charge, to any person obtaining a copy +of this software and associated documentation files (the "Software"), to deal +in the Software without restriction, including without limitation the rights +to use, copy, modify, merge, publish, distribute, sublicense, and/or sell +copies of the Software, and to permit persons to whom the Software is +furnished to do so, subject to the following conditions: + +The above copyright notice and this permission notice shall be included in all +copies or substantial portions of the Software. + +THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE +AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, +OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE +SOFTWARE. + diff --git a/packages/typebox/README.md b/packages/typebox/README.md new file mode 100644 index 0000000000..6f5982118c --- /dev/null +++ b/packages/typebox/README.md @@ -0,0 +1,23 @@ +# @feathersjs/typebox + +[![CI](https://github.com/feathersjs/feathers/workflows/CI/badge.svg)](https://github.com/feathersjs/feathers/actions?query=workflow%3ACI) +[![Download Status](https://img.shields.io/npm/dm/@feathersjs/typebox.svg?style=flat-square)](https://www.npmjs.com/package/@feathersjs/typebox) +[![Discord](https://badgen.net/badge/icon/discord?icon=discord&label)](https://discord.gg/qa8kez8QBx) + +> [TypeBox](https://github.com/sinclairzx81/typebox) integration for @feathersjs/schema + +## Installation + +``` +npm install @feathersjs/typebox --save +``` + +## Documentation + +Refer to the [Feathers documentation](https://docs.feathersjs.com) for more details. + +## License + +Copyright (c) 2022 [Feathers contributors](https://github.com/feathersjs/feathers/graphs/contributors) + +Licensed under the [MIT license](LICENSE). diff --git a/packages/typebox/package.json b/packages/typebox/package.json new file mode 100644 index 0000000000..17c7c550d8 --- /dev/null +++ b/packages/typebox/package.json @@ -0,0 +1,68 @@ +{ + "name": "@feathersjs/typebox", + "description": "TypeBox integration for @feathersjs/schema", + "version": "5.0.0-pre.31", + "homepage": "https://feathersjs.com", + "main": "lib/", + "types": "lib/", + "keywords": [ + "feathers", + "feathers-plugin" + ], + "license": "MIT", + "funding": { + "type": "github", + "url": "https://github.com/sponsors/daffl" + }, + "repository": { + "type": "git", + "url": "git://github.com/feathersjs/feathers.git", + "directory": "packages/schema" + }, + "author": { + "name": "Feathers contributors", + "email": "hello@feathersjs.com", + "url": "https://feathersjs.com" + }, + "contributors": [], + "bugs": { + "url": "https://github.com/feathersjs/feathers/issues" + }, + "engines": { + "node": ">= 12" + }, + "files": [ + "CHANGELOG.md", + "LICENSE", + "README.md", + "src/**", + "lib/**", + "*.d.ts", + "*.js" + ], + "scripts": { + "prepublish": "npm run compile", + "pack": "npm pack --pack-destination ../cli/test/build", + "compile": "shx rm -rf lib/ && tsc && npm run pack", + "mocha": "mocha --config ../../.mocharc.json --recursive test/**.test.ts test/**/*.test.ts", + "test": "npm run compile && npm run mocha" + }, + "directories": { + "lib": "lib" + }, + "publishConfig": { + "access": "public" + }, + "dependencies": { + "@feathersjs/schema": "^5.0.0-pre.31", + "@sinclair/typebox": "^0.24.44" + }, + "devDependencies": { + "@types/mocha": "^10.0.0", + "@types/node": "^18.8.2", + "mocha": "^10.0.0", + "shx": "^0.3.4", + "typescript": "^4.8.4" + }, + "gitHead": "4500dbeb8cea566678cf88b3313a88efd93a2ed9" +} diff --git a/packages/typebox/src/default-schemas.ts b/packages/typebox/src/default-schemas.ts new file mode 100644 index 0000000000..e5dd715db5 --- /dev/null +++ b/packages/typebox/src/default-schemas.ts @@ -0,0 +1,87 @@ +import { Type, Static } from '@sinclair/typebox' + +export const authenticationSettingsSchema = Type.Object({ + secret: Type.String({ description: 'The JWT signing secret' }), + entity: Type.Optional(Type.String({ description: 'The name of the authentication entity (e.g. user)' })), + entityId: Type.Optional(Type.String({ description: 'The name of the authentication entity id property' })), + service: Type.Optional(Type.String({ description: 'The path of the entity service' })), + authStrategies: Type.Array(Type.String(), { + description: 'A list of authentication strategy names that are allowed to create JWT access tokens' + }), + parseStrategies: Type.Optional( + Type.Array(Type.String(), { + description: + 'A list of authentication strategy names that should parse HTTP headers for authentication information (defaults to `authStrategies`)' + }) + ), + jwtOptions: Type.Optional(Type.Object({})), + jwt: Type.Optional( + Type.Object({ + header: Type.String({ default: 'Authorization', description: 'The HTTP header containing the JWT' }), + schemes: Type.String({ description: 'An array of schemes to support' }) + }) + ), + local: Type.Optional( + Type.Object({ + usernameField: Type.String({ description: 'Name of the username field (e.g. `email`)' }), + passwordField: Type.String({ description: 'Name of the password field (e.g. `password`)' }), + hashSize: Type.Optional(Type.Number({ description: 'The BCrypt salt length' })), + errorMessage: Type.Optional(Type.String({ description: 'The error message to return on errors' })), + entityUsernameField: Type.Optional( + Type.String({ + description: + 'Name of the username field on the entity if authentication request data and entity field names are different' + }) + ), + entityPasswordField: Type.Optional( + Type.String({ + description: + 'Name of the password field on the entity if authentication request data and entity field names are different' + }) + ) + }) + ), + oauth: Type.Optional( + Type.Object({ + redirect: Type.Optional(Type.String()), + origins: Type.Optional(Type.Array(Type.String())), + defaults: Type.Optional( + Type.Object({ + key: Type.Optional(Type.String()), + secret: Type.Optional(Type.String()) + }) + ) + }) + ) +}) + +export const sqlSettingsSchema = Type.Optional( + Type.Object({ + client: Type.String(), + connection: Type.String() + }) +) + +export const defaultAppConfiguration = Type.Object( + { + authentication: Type.Optional(authenticationSettingsSchema), + paginate: Type.Optional( + Type.Object( + { + default: Type.Number(), + max: Type.Number() + }, + { additionalProperties: false } + ) + ), + origins: Type.Optional(Type.Array(Type.String())), + mongodb: Type.Optional(Type.String()), + mysql: sqlSettingsSchema, + postgresql: sqlSettingsSchema, + sqlite: sqlSettingsSchema, + mssql: sqlSettingsSchema + }, + { $id: 'ApplicationConfiguration', additionalProperties: false } +) + +export type DefaultAppConfiguration = Static diff --git a/packages/typebox/src/index.ts b/packages/typebox/src/index.ts new file mode 100644 index 0000000000..350cb29d4d --- /dev/null +++ b/packages/typebox/src/index.ts @@ -0,0 +1,112 @@ +import { Type, TObject, TInteger, TOptional, TSchema, TIntersect } from '@sinclair/typebox' +import { jsonSchema, Validator, DataValidatorMap, Ajv } from '@feathersjs/schema' + +export * from '@sinclair/typebox' +export * from './default-schemas' + +export type TDataSchemaMap = { + create: TObject + update?: TObject + patch?: TObject +} + +/** + * Returns a compiled validation function for a TypeBox object and AJV validator instance. + * + * @param schema The JSON schema definition + * @param validator The AJV validation instance + * @returns A compiled validation function + */ +export const getValidator = (schema: TObject, validator: Ajv): Validator => + jsonSchema.getValidator(schema as any, validator) + +/** + * Returns compiled validation functions to validate data for the `create`, `update` and `patch` + * service methods. If not passed explicitly, the `update` validator will be the same as the `create` + * and `patch` will be the `create` validator with no required fields. + * + * @param def Either general TypeBox object definition or a mapping of `create`, `update` and `patch` + * to their respective type object + * @param validator The Ajv instance to use as the validator + * @returns A map of validator functions + */ +export const getDataValidator = (def: TObject | TDataSchemaMap, validator: Ajv): DataValidatorMap => + jsonSchema.getDataValidator(def as any, validator) + +const arrayOfKeys = (type: T) => { + const keys = Object.keys(type.properties) + return Type.Unsafe<(keyof T['properties'])[]>({ type: 'array', items: { type: 'string', enum: keys } }) +} + +export function sortDefinition(schema: T) { + const properties = Object.keys(schema.properties).reduce((res, key) => { + const result = res as any + + result[key] = Type.Optional(Type.Integer({ minimum: -1, maximum: 1 })) + + return result + }, {} as { [K in keyof T['properties']]: TOptional }) + + return { + type: 'object', + additionalProperties: false, + properties + } as TObject +} + +export const queryProperty = (def: T) => { + return Type.Optional( + Type.Union([ + def, + Type.Object({ + $gt: Type.Optional(def), + $gte: Type.Optional(def), + $lt: Type.Optional(def), + $lte: Type.Optional(def), + $ne: Type.Optional(def), + $in: Type.Optional(Type.Array(def)), + $nin: Type.Optional(Type.Array(def)) + }) + ]) + ) +} + +type QueryProperty = ReturnType> + +export const queryProperties = (type: T) => { + const properties = Object.keys(type.properties).reduce((res, key) => { + const result = res as any + + result[key] = queryProperty(type.properties[key]) + + return result + }, {} as { [K in keyof T['properties']]: QueryProperty }) + + return { + type: 'object', + additionalProperties: false, + properties + } as TObject +} + +/** + * Creates a TypeBox schema for the complete Feathers query syntax including `$limit`, $skip` + * and `$sort` and `$select` for the allowed properties. + * + * @param type The properties to create the query syntax for + * @returns A TypeBox object representing the complete Feathers query syntax for the given properties + */ +export const querySyntax = (type: T) => { + return Type.Intersect([ + Type.Object( + { + $limit: Type.Optional(Type.Number({ minimum: 0 })), + $skip: Type.Optional(Type.Number({ minimum: 0 })), + $sort: Type.Optional(sortDefinition(type)), + $select: Type.Optional(arrayOfKeys(type)) + }, + { additionalProperties: false } + ), + queryProperties(type) + ]) +} diff --git a/packages/typebox/test/index.test.ts b/packages/typebox/test/index.test.ts new file mode 100644 index 0000000000..01c6133d2b --- /dev/null +++ b/packages/typebox/test/index.test.ts @@ -0,0 +1,55 @@ +import assert from 'assert' +import { Ajv } from '@feathersjs/schema' +import { querySyntax, Type, Static, defaultAppConfiguration, getDataValidator, getValidator } from '../src' + +describe('@feathersjs/schema/typebox', () => { + it('querySyntax', async () => { + const schema = Type.Object({ + name: Type.String(), + age: Type.Number() + }) + + const querySchema = querySyntax(schema) + + type Query = Static + + const query: Query = { + name: 'Dave', + age: { $gt: 42, $in: [50, 51] }, + $select: ['age', 'name'], + $sort: { + age: 1 + } + } + + const validator = new Ajv().compile(querySchema) + const validated = (await validator(query)) as any as Query + + assert.ok(validated) + }) + + it('defaultAppConfiguration', async () => { + const configSchema = Type.Intersect([ + defaultAppConfiguration, + Type.Object({ + host: Type.String(), + port: Type.Number(), + public: Type.String() + }) + ]) + + const validator = new Ajv().compile(configSchema) + const validated = await validator({ + host: 'something', + port: 3030, + public: './' + }) + + assert.ok(validated) + }) + + it('validators', () => { + assert.strictEqual(typeof getDataValidator(Type.Object({}), new Ajv()), 'object') + assert.strictEqual(typeof getValidator(Type.Object({}), new Ajv()), 'function') + }) +}) diff --git a/packages/typebox/tsconfig.json b/packages/typebox/tsconfig.json new file mode 100644 index 0000000000..316fd41336 --- /dev/null +++ b/packages/typebox/tsconfig.json @@ -0,0 +1,9 @@ +{ + "extends": "../../tsconfig", + "include": [ + "src/**/*.ts" + ], + "compilerOptions": { + "outDir": "lib" + } +} diff --git a/pnpm-lock.yaml b/pnpm-lock.yaml new file mode 100644 index 0000000000..7876e4dbe1 --- /dev/null +++ b/pnpm-lock.yaml @@ -0,0 +1,6733 @@ +lockfileVersion: 5.4 + +specifiers: + '@typescript-eslint/eslint-plugin': ^5.8.1 + '@typescript-eslint/parser': ^5.8.1 + eslint: ^8.6.0 + eslint-plugin-import: ^2.25.3 + eslint-plugin-prefer-arrow: ^1.2.3 + lerna: ^4.0.0 + npm-check-updates: ^12.0.5 + nyc: ^15.1.0 + typescript: ^4.5.4 + +devDependencies: + '@typescript-eslint/eslint-plugin': 5.40.0_25sstg4uu2sk4pm7xcyzuov7xq + '@typescript-eslint/parser': 5.40.0_z4bbprzjrhnsfa24uvmcbu7f5q + eslint: 8.25.0 + eslint-plugin-import: 2.26.0_zb5prbqp7qzcgafjm73dfpyyvm + eslint-plugin-prefer-arrow: 1.2.3_eslint@8.25.0 + lerna: 4.0.0 + npm-check-updates: 12.5.12 + nyc: 15.1.0 + typescript: 4.8.4 + +packages: + + /@ampproject/remapping/2.2.0: + resolution: {integrity: sha512-qRmjj8nj9qmLTQXXmaR1cck3UXSRMPrbsLJAasZpF+t3riI71BXed5ebIOYwQntykeZuhjsdweEc9BxH5Jc26w==} + engines: {node: '>=6.0.0'} + dependencies: + '@jridgewell/gen-mapping': 0.1.1 + '@jridgewell/trace-mapping': 0.3.17 + dev: true + + /@babel/code-frame/7.18.6: + resolution: {integrity: sha512-TDCmlK5eOvH+eH7cdAFlNXeVJqWIQ7gW9tY1GJIpUtFb6CmjVyq2VM3u71bOyR8CRihcCgMUYoDNyLXao3+70Q==} + engines: {node: '>=6.9.0'} + dependencies: + '@babel/highlight': 7.18.6 + dev: true + + /@babel/compat-data/7.19.4: + resolution: {integrity: sha512-CHIGpJcUQ5lU9KrPHTjBMhVwQG6CQjxfg36fGXl3qk/Gik1WwWachaXFuo0uCWJT/mStOKtcbFJCaVLihC1CMw==} + engines: {node: '>=6.9.0'} + dev: true + + /@babel/core/7.19.3: + resolution: {integrity: sha512-WneDJxdsjEvyKtXKsaBGbDeiyOjR5vYq4HcShxnIbG0qixpoHjI3MqeZM9NDvsojNCEBItQE4juOo/bU6e72gQ==} + engines: {node: '>=6.9.0'} + dependencies: + '@ampproject/remapping': 2.2.0 + '@babel/code-frame': 7.18.6 + '@babel/generator': 7.19.5 + '@babel/helper-compilation-targets': 7.19.3_@babel+core@7.19.3 + '@babel/helper-module-transforms': 7.19.0 + '@babel/helpers': 7.19.4 + '@babel/parser': 7.19.4 + '@babel/template': 7.18.10 + '@babel/traverse': 7.19.4 + '@babel/types': 7.19.4 + convert-source-map: 1.9.0 + debug: 4.3.4 + gensync: 1.0.0-beta.2 + json5: 2.2.1 + semver: 6.3.0 + transitivePeerDependencies: + - supports-color + dev: true + + /@babel/generator/7.19.5: + resolution: {integrity: sha512-DxbNz9Lz4aMZ99qPpO1raTbcrI1ZeYh+9NR9qhfkQIbFtVEqotHojEBxHzmxhVONkGt6VyrqVQcgpefMy9pqcg==} + engines: {node: '>=6.9.0'} + dependencies: + '@babel/types': 7.19.4 + '@jridgewell/gen-mapping': 0.3.2 + jsesc: 2.5.2 + dev: true + + /@babel/helper-compilation-targets/7.19.3_@babel+core@7.19.3: + resolution: {integrity: sha512-65ESqLGyGmLvgR0mst5AdW1FkNlj9rQsCKduzEoEPhBCDFGXvz2jW6bXFG6i0/MrV2s7hhXjjb2yAzcPuQlLwg==} + engines: {node: '>=6.9.0'} + peerDependencies: + '@babel/core': ^7.0.0 + dependencies: + '@babel/compat-data': 7.19.4 + '@babel/core': 7.19.3 + '@babel/helper-validator-option': 7.18.6 + browserslist: 4.21.4 + semver: 6.3.0 + dev: true + + /@babel/helper-environment-visitor/7.18.9: + resolution: {integrity: sha512-3r/aACDJ3fhQ/EVgFy0hpj8oHyHpQc+LPtJoY9SzTThAsStm4Ptegq92vqKoE3vD706ZVFWITnMnxucw+S9Ipg==} + engines: {node: '>=6.9.0'} + dev: true + + /@babel/helper-function-name/7.19.0: + resolution: {integrity: sha512-WAwHBINyrpqywkUH0nTnNgI5ina5TFn85HKS0pbPDfxFfhyR/aNQEn4hGi1P1JyT//I0t4OgXUlofzWILRvS5w==} + engines: {node: '>=6.9.0'} + dependencies: + '@babel/template': 7.18.10 + '@babel/types': 7.19.4 + dev: true + + /@babel/helper-hoist-variables/7.18.6: + resolution: {integrity: sha512-UlJQPkFqFULIcyW5sbzgbkxn2FKRgwWiRexcuaR8RNJRy8+LLveqPjwZV/bwrLZCN0eUHD/x8D0heK1ozuoo6Q==} + engines: {node: '>=6.9.0'} + dependencies: + '@babel/types': 7.19.4 + dev: true + + /@babel/helper-module-imports/7.18.6: + resolution: {integrity: sha512-0NFvs3VkuSYbFi1x2Vd6tKrywq+z/cLeYC/RJNFrIX/30Bf5aiGYbtvGXolEktzJH8o5E5KJ3tT+nkxuuZFVlA==} + engines: {node: '>=6.9.0'} + dependencies: + '@babel/types': 7.19.4 + dev: true + + /@babel/helper-module-transforms/7.19.0: + resolution: {integrity: sha512-3HBZ377Fe14RbLIA+ac3sY4PTgpxHVkFrESaWhoI5PuyXPBBX8+C34qblV9G89ZtycGJCmCI/Ut+VUDK4bltNQ==} + engines: {node: '>=6.9.0'} + dependencies: + '@babel/helper-environment-visitor': 7.18.9 + '@babel/helper-module-imports': 7.18.6 + '@babel/helper-simple-access': 7.19.4 + '@babel/helper-split-export-declaration': 7.18.6 + '@babel/helper-validator-identifier': 7.19.1 + '@babel/template': 7.18.10 + '@babel/traverse': 7.19.4 + '@babel/types': 7.19.4 + transitivePeerDependencies: + - supports-color + dev: true + + /@babel/helper-simple-access/7.19.4: + resolution: {integrity: sha512-f9Xq6WqBFqaDfbCzn2w85hwklswz5qsKlh7f08w4Y9yhJHpnNC0QemtSkK5YyOY8kPGvyiwdzZksGUhnGdaUIg==} + engines: {node: '>=6.9.0'} + dependencies: + '@babel/types': 7.19.4 + dev: true + + /@babel/helper-split-export-declaration/7.18.6: + resolution: {integrity: sha512-bde1etTx6ZyTmobl9LLMMQsaizFVZrquTEHOqKeQESMKo4PlObf+8+JA25ZsIpZhT/WEd39+vOdLXAFG/nELpA==} + engines: {node: '>=6.9.0'} + dependencies: + '@babel/types': 7.19.4 + dev: true + + /@babel/helper-string-parser/7.19.4: + resolution: {integrity: sha512-nHtDoQcuqFmwYNYPz3Rah5ph2p8PFeFCsZk9A/48dPc/rGocJ5J3hAAZ7pb76VWX3fZKu+uEr/FhH5jLx7umrw==} + engines: {node: '>=6.9.0'} + dev: true + + /@babel/helper-validator-identifier/7.19.1: + resolution: {integrity: sha512-awrNfaMtnHUr653GgGEs++LlAvW6w+DcPrOliSMXWCKo597CwL5Acf/wWdNkf/tfEQE3mjkeD1YOVZOUV/od1w==} + engines: {node: '>=6.9.0'} + dev: true + + /@babel/helper-validator-option/7.18.6: + resolution: {integrity: sha512-XO7gESt5ouv/LRJdrVjkShckw6STTaB7l9BrpBaAHDeF5YZT+01PCwmR0SJHnkW6i8OwW/EVWRShfi4j2x+KQw==} + engines: {node: '>=6.9.0'} + dev: true + + /@babel/helpers/7.19.4: + resolution: {integrity: sha512-G+z3aOx2nfDHwX/kyVii5fJq+bgscg89/dJNWpYeKeBv3v9xX8EIabmx1k6u9LS04H7nROFVRVK+e3k0VHp+sw==} + engines: {node: '>=6.9.0'} + dependencies: + '@babel/template': 7.18.10 + '@babel/traverse': 7.19.4 + '@babel/types': 7.19.4 + transitivePeerDependencies: + - supports-color + dev: true + + /@babel/highlight/7.18.6: + resolution: {integrity: sha512-u7stbOuYjaPezCuLj29hNW1v64M2Md2qupEKP1fHc7WdOA3DgLh37suiSrZYY7haUB7iBeQZ9P1uiRF359do3g==} + engines: {node: '>=6.9.0'} + dependencies: + '@babel/helper-validator-identifier': 7.19.1 + chalk: 2.4.2 + js-tokens: 4.0.0 + dev: true + + /@babel/parser/7.19.4: + resolution: {integrity: sha512-qpVT7gtuOLjWeDTKLkJ6sryqLliBaFpAtGeqw5cs5giLldvh+Ch0plqnUMKoVAUS6ZEueQQiZV+p5pxtPitEsA==} + engines: {node: '>=6.0.0'} + hasBin: true + dependencies: + '@babel/types': 7.19.4 + dev: true + + /@babel/template/7.18.10: + resolution: {integrity: sha512-TI+rCtooWHr3QJ27kJxfjutghu44DLnasDMwpDqCXVTal9RLp3RSYNh4NdBrRP2cQAoG9A8juOQl6P6oZG4JxA==} + engines: {node: '>=6.9.0'} + dependencies: + '@babel/code-frame': 7.18.6 + '@babel/parser': 7.19.4 + '@babel/types': 7.19.4 + dev: true + + /@babel/traverse/7.19.4: + resolution: {integrity: sha512-w3K1i+V5u2aJUOXBFFC5pveFLmtq1s3qcdDNC2qRI6WPBQIDaKFqXxDEqDO/h1dQ3HjsZoZMyIy6jGLq0xtw+g==} + engines: {node: '>=6.9.0'} + dependencies: + '@babel/code-frame': 7.18.6 + '@babel/generator': 7.19.5 + '@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.19.4 + '@babel/types': 7.19.4 + debug: 4.3.4 + globals: 11.12.0 + transitivePeerDependencies: + - supports-color + dev: true + + /@babel/types/7.19.4: + resolution: {integrity: sha512-M5LK7nAeS6+9j7hAq+b3fQs+pNfUtTGq+yFFfHnauFA8zQtLRfmuipmsKDKKLuyG+wC8ABW43A153YNawNTEtw==} + engines: {node: '>=6.9.0'} + dependencies: + '@babel/helper-string-parser': 7.19.4 + '@babel/helper-validator-identifier': 7.19.1 + to-fast-properties: 2.0.0 + dev: true + + /@eslint/eslintrc/1.3.3: + resolution: {integrity: sha512-uj3pT6Mg+3t39fvLrj8iuCIJ38zKO9FpGtJ4BBJebJhEwjoT+KLVNCcHT5QC9NGRIEi7fZ0ZR8YRb884auB4Lg==} + engines: {node: ^12.22.0 || ^14.17.0 || >=16.0.0} + dependencies: + ajv: 6.12.6 + debug: 4.3.4 + espree: 9.4.0 + globals: 13.17.0 + ignore: 5.2.0 + import-fresh: 3.3.0 + js-yaml: 4.1.0 + minimatch: 3.1.2 + strip-json-comments: 3.1.1 + transitivePeerDependencies: + - supports-color + dev: true + + /@gar/promisify/1.1.3: + resolution: {integrity: sha512-k2Ty1JcVojjJFwrg/ThKi2ujJ7XNLYaFGNB/bWT9wGR+oSMJHMa5w+CUq6p/pVrKeNNgA7pCqEcjSnHVoqJQFw==} + dev: true + + /@humanwhocodes/config-array/0.10.7: + resolution: {integrity: sha512-MDl6D6sBsaV452/QSdX+4CXIjZhIcI0PELsxUjk4U828yd58vk3bTIvk/6w5FY+4hIy9sLW0sfrV7K7Kc++j/w==} + engines: {node: '>=10.10.0'} + dependencies: + '@humanwhocodes/object-schema': 1.2.1 + debug: 4.3.4 + minimatch: 3.1.2 + transitivePeerDependencies: + - supports-color + dev: true + + /@humanwhocodes/module-importer/1.0.1: + resolution: {integrity: sha512-bxveV4V8v5Yb4ncFTT3rPSgZBOpCkjfK0y4oVVVJwIuDVBRMDXrPyXRL988i5ap9m9bnyEEjWfm5WkBmtffLfA==} + engines: {node: '>=12.22'} + dev: true + + /@humanwhocodes/object-schema/1.2.1: + resolution: {integrity: sha512-ZnQMnLV4e7hDlUvw8H+U8ASL02SS2Gn6+9Ac3wGGLIe7+je2AeAOxPY+izIPJDfFDb7eDjev0Us8MO1iFRN8hA==} + dev: true + + /@hutson/parse-repository-url/3.0.2: + resolution: {integrity: sha512-H9XAx3hc0BQHY6l+IFSWHDySypcXsvsuLhgYLUGywmJ5pswRVQJUHpOsobnLYp2ZUaUlKiKDrgWWhosOwAEM8Q==} + engines: {node: '>=6.9.0'} + dev: true + + /@istanbuljs/load-nyc-config/1.1.0: + resolution: {integrity: sha512-VjeHSlIzpv/NyD3N0YuHfXOPDIixcA1q2ZV98wsMqcYlPmv2n3Yb2lYP9XMElnaFVXg5A7YLTeLu6V84uQDjmQ==} + engines: {node: '>=8'} + dependencies: + camelcase: 5.3.1 + find-up: 4.1.0 + get-package-type: 0.1.0 + js-yaml: 3.14.1 + resolve-from: 5.0.0 + dev: true + + /@istanbuljs/schema/0.1.3: + resolution: {integrity: sha512-ZXRY4jNvVgSVQ8DL3LTcakaAtXwTVUxE81hslsyD2AtoXW/wVob10HkOJ1X/pAlcI7D+2YoZKg5do8G/w6RYgA==} + engines: {node: '>=8'} + dev: true + + /@jridgewell/gen-mapping/0.1.1: + resolution: {integrity: sha512-sQXCasFk+U8lWYEe66WxRDOE9PjVz4vSM51fTu3Hw+ClTpUSQb718772vH3pyS5pShp6lvQM7SxgIDXXXmOX7w==} + engines: {node: '>=6.0.0'} + dependencies: + '@jridgewell/set-array': 1.1.2 + '@jridgewell/sourcemap-codec': 1.4.14 + dev: true + + /@jridgewell/gen-mapping/0.3.2: + resolution: {integrity: sha512-mh65xKQAzI6iBcFzwv28KVWSmCkdRBWoOh+bYQGW3+6OZvbbN3TqMGo5hqYxQniRcH9F2VZIoJCm4pa3BPDK/A==} + engines: {node: '>=6.0.0'} + dependencies: + '@jridgewell/set-array': 1.1.2 + '@jridgewell/sourcemap-codec': 1.4.14 + '@jridgewell/trace-mapping': 0.3.17 + dev: true + + /@jridgewell/resolve-uri/3.1.0: + resolution: {integrity: sha512-F2msla3tad+Mfht5cJq7LSXcdudKTWCVYUgw6pLFOOHSTtZlj6SWNYAp+AhuqLmWdBO2X5hPrLcu8cVP8fy28w==} + engines: {node: '>=6.0.0'} + dev: true + + /@jridgewell/set-array/1.1.2: + resolution: {integrity: sha512-xnkseuNADM0gt2bs+BvhO0p78Mk762YnZdsuzFV018NoG1Sj1SCQvpSqa7XUaTam5vAGasABV9qXASMKnFMwMw==} + engines: {node: '>=6.0.0'} + dev: true + + /@jridgewell/sourcemap-codec/1.4.14: + resolution: {integrity: sha512-XPSJHWmi394fuUuzDnGz1wiKqWfo1yXecHQMRf2l6hztTO+nPru658AyDngaBe7isIxEkRsPR3FZh+s7iVa4Uw==} + dev: true + + /@jridgewell/trace-mapping/0.3.17: + resolution: {integrity: sha512-MCNzAp77qzKca9+W/+I0+sEpaUnZoeasnghNeVc41VZCEKaCH73Vq3BZZ/SzWIgrqE4H4ceI+p+b6C0mHf9T4g==} + dependencies: + '@jridgewell/resolve-uri': 3.1.0 + '@jridgewell/sourcemap-codec': 1.4.14 + dev: true + + /@lerna/add/4.0.0: + resolution: {integrity: sha512-cpmAH1iS3k8JBxNvnMqrGTTjbY/ZAiKa1ChJzFevMYY3eeqbvhsBKnBcxjRXtdrJ6bd3dCQM+ZtK+0i682Fhng==} + engines: {node: '>= 10.18.0'} + dependencies: + '@lerna/bootstrap': 4.0.0 + '@lerna/command': 4.0.0 + '@lerna/filter-options': 4.0.0 + '@lerna/npm-conf': 4.0.0 + '@lerna/validation-error': 4.0.0 + dedent: 0.7.0 + npm-package-arg: 8.1.5 + p-map: 4.0.0 + pacote: 11.3.5 + semver: 7.3.8 + transitivePeerDependencies: + - bluebird + - supports-color + dev: true + + /@lerna/bootstrap/4.0.0: + resolution: {integrity: sha512-RkS7UbeM2vu+kJnHzxNRCLvoOP9yGNgkzRdy4UV2hNalD7EP41bLvRVOwRYQ7fhc2QcbhnKNdOBihYRL0LcKtw==} + engines: {node: '>= 10.18.0'} + dependencies: + '@lerna/command': 4.0.0 + '@lerna/filter-options': 4.0.0 + '@lerna/has-npm-version': 4.0.0 + '@lerna/npm-install': 4.0.0 + '@lerna/package-graph': 4.0.0 + '@lerna/pulse-till-done': 4.0.0 + '@lerna/rimraf-dir': 4.0.0 + '@lerna/run-lifecycle': 4.0.0 + '@lerna/run-topologically': 4.0.0 + '@lerna/symlink-binary': 4.0.0 + '@lerna/symlink-dependencies': 4.0.0 + '@lerna/validation-error': 4.0.0 + dedent: 0.7.0 + get-port: 5.1.1 + multimatch: 5.0.0 + npm-package-arg: 8.1.5 + npmlog: 4.1.2 + p-map: 4.0.0 + p-map-series: 2.1.0 + p-waterfall: 2.1.1 + read-package-tree: 5.3.1 + semver: 7.3.8 + dev: true + + /@lerna/changed/4.0.0: + resolution: {integrity: sha512-cD+KuPRp6qiPOD+BO6S6SN5cARspIaWSOqGBpGnYzLb4uWT8Vk4JzKyYtc8ym1DIwyoFXHosXt8+GDAgR8QrgQ==} + engines: {node: '>= 10.18.0'} + dependencies: + '@lerna/collect-updates': 4.0.0 + '@lerna/command': 4.0.0 + '@lerna/listable': 4.0.0 + '@lerna/output': 4.0.0 + dev: true + + /@lerna/check-working-tree/4.0.0: + resolution: {integrity: sha512-/++bxM43jYJCshBiKP5cRlCTwSJdRSxVmcDAXM+1oUewlZJVSVlnks5eO0uLxokVFvLhHlC5kHMc7gbVFPHv6Q==} + engines: {node: '>= 10.18.0'} + dependencies: + '@lerna/collect-uncommitted': 4.0.0 + '@lerna/describe-ref': 4.0.0 + '@lerna/validation-error': 4.0.0 + dev: true + + /@lerna/child-process/4.0.0: + resolution: {integrity: sha512-XtCnmCT9eyVsUUHx6y/CTBYdV9g2Cr/VxyseTWBgfIur92/YKClfEtJTbOh94jRT62hlKLqSvux/UhxXVh613Q==} + engines: {node: '>= 10.18.0'} + dependencies: + chalk: 4.1.2 + execa: 5.1.1 + strong-log-transformer: 2.1.0 + dev: true + + /@lerna/clean/4.0.0: + resolution: {integrity: sha512-uugG2iN9k45ITx2jtd8nEOoAtca8hNlDCUM0N3lFgU/b1mEQYAPRkqr1qs4FLRl/Y50ZJ41wUz1eazS+d/0osA==} + engines: {node: '>= 10.18.0'} + dependencies: + '@lerna/command': 4.0.0 + '@lerna/filter-options': 4.0.0 + '@lerna/prompt': 4.0.0 + '@lerna/pulse-till-done': 4.0.0 + '@lerna/rimraf-dir': 4.0.0 + p-map: 4.0.0 + p-map-series: 2.1.0 + p-waterfall: 2.1.1 + dev: true + + /@lerna/cli/4.0.0: + resolution: {integrity: sha512-Neaw3GzFrwZiRZv2g7g6NwFjs3er1vhraIniEs0jjVLPMNC4eata0na3GfE5yibkM/9d3gZdmihhZdZ3EBdvYA==} + engines: {node: '>= 10.18.0'} + dependencies: + '@lerna/global-options': 4.0.0 + dedent: 0.7.0 + npmlog: 4.1.2 + yargs: 16.2.0 + dev: true + + /@lerna/collect-uncommitted/4.0.0: + resolution: {integrity: sha512-ufSTfHZzbx69YNj7KXQ3o66V4RC76ffOjwLX0q/ab//61bObJ41n03SiQEhSlmpP+gmFbTJ3/7pTe04AHX9m/g==} + engines: {node: '>= 10.18.0'} + dependencies: + '@lerna/child-process': 4.0.0 + chalk: 4.1.2 + npmlog: 4.1.2 + dev: true + + /@lerna/collect-updates/4.0.0: + resolution: {integrity: sha512-bnNGpaj4zuxsEkyaCZLka9s7nMs58uZoxrRIPJ+nrmrZYp1V5rrd+7/NYTuunOhY2ug1sTBvTAxj3NZQ+JKnOw==} + engines: {node: '>= 10.18.0'} + dependencies: + '@lerna/child-process': 4.0.0 + '@lerna/describe-ref': 4.0.0 + minimatch: 3.1.2 + npmlog: 4.1.2 + slash: 3.0.0 + dev: true + + /@lerna/command/4.0.0: + resolution: {integrity: sha512-LM9g3rt5FsPNFqIHUeRwWXLNHJ5NKzOwmVKZ8anSp4e1SPrv2HNc1V02/9QyDDZK/w+5POXH5lxZUI1CHaOK/A==} + engines: {node: '>= 10.18.0'} + dependencies: + '@lerna/child-process': 4.0.0 + '@lerna/package-graph': 4.0.0 + '@lerna/project': 4.0.0 + '@lerna/validation-error': 4.0.0 + '@lerna/write-log-file': 4.0.0 + clone-deep: 4.0.1 + dedent: 0.7.0 + execa: 5.1.1 + is-ci: 2.0.0 + npmlog: 4.1.2 + dev: true + + /@lerna/conventional-commits/4.0.0: + resolution: {integrity: sha512-CSUQRjJHFrH8eBn7+wegZLV3OrNc0Y1FehYfYGhjLE2SIfpCL4bmfu/ViYuHh9YjwHaA+4SX6d3hR+xkeseKmw==} + engines: {node: '>= 10.18.0'} + dependencies: + '@lerna/validation-error': 4.0.0 + conventional-changelog-angular: 5.0.13 + conventional-changelog-core: 4.2.4 + conventional-recommended-bump: 6.1.0 + fs-extra: 9.1.0 + get-stream: 6.0.1 + lodash.template: 4.5.0 + npm-package-arg: 8.1.5 + npmlog: 4.1.2 + pify: 5.0.0 + semver: 7.3.8 + dev: true + + /@lerna/create-symlink/4.0.0: + resolution: {integrity: sha512-I0phtKJJdafUiDwm7BBlEUOtogmu8+taxq6PtIrxZbllV9hWg59qkpuIsiFp+no7nfRVuaasNYHwNUhDAVQBig==} + engines: {node: '>= 10.18.0'} + dependencies: + cmd-shim: 4.1.0 + fs-extra: 9.1.0 + npmlog: 4.1.2 + dev: true + + /@lerna/create/4.0.0: + resolution: {integrity: sha512-mVOB1niKByEUfxlbKTM1UNECWAjwUdiioIbRQZEeEabtjCL69r9rscIsjlGyhGWCfsdAG5wfq4t47nlDXdLLag==} + engines: {node: '>= 10.18.0'} + dependencies: + '@lerna/child-process': 4.0.0 + '@lerna/command': 4.0.0 + '@lerna/npm-conf': 4.0.0 + '@lerna/validation-error': 4.0.0 + dedent: 0.7.0 + fs-extra: 9.1.0 + globby: 11.1.0 + init-package-json: 2.0.5 + npm-package-arg: 8.1.5 + p-reduce: 2.1.0 + pacote: 11.3.5 + pify: 5.0.0 + semver: 7.3.8 + slash: 3.0.0 + validate-npm-package-license: 3.0.4 + validate-npm-package-name: 3.0.0 + whatwg-url: 8.7.0 + yargs-parser: 20.2.4 + transitivePeerDependencies: + - bluebird + - supports-color + dev: true + + /@lerna/describe-ref/4.0.0: + resolution: {integrity: sha512-eTU5+xC4C5Gcgz+Ey4Qiw9nV2B4JJbMulsYJMW8QjGcGh8zudib7Sduj6urgZXUYNyhYpRs+teci9M2J8u+UvQ==} + engines: {node: '>= 10.18.0'} + dependencies: + '@lerna/child-process': 4.0.0 + npmlog: 4.1.2 + dev: true + + /@lerna/diff/4.0.0: + resolution: {integrity: sha512-jYPKprQVg41+MUMxx6cwtqsNm0Yxx9GDEwdiPLwcUTFx+/qKCEwifKNJ1oGIPBxyEHX2PFCOjkK39lHoj2qiag==} + engines: {node: '>= 10.18.0'} + dependencies: + '@lerna/child-process': 4.0.0 + '@lerna/command': 4.0.0 + '@lerna/validation-error': 4.0.0 + npmlog: 4.1.2 + dev: true + + /@lerna/exec/4.0.0: + resolution: {integrity: sha512-VGXtL/b/JfY84NB98VWZpIExfhLOzy0ozm/0XaS4a2SmkAJc5CeUfrhvHxxkxiTBLkU+iVQUyYEoAT0ulQ8PCw==} + engines: {node: '>= 10.18.0'} + dependencies: + '@lerna/child-process': 4.0.0 + '@lerna/command': 4.0.0 + '@lerna/filter-options': 4.0.0 + '@lerna/profiler': 4.0.0 + '@lerna/run-topologically': 4.0.0 + '@lerna/validation-error': 4.0.0 + p-map: 4.0.0 + dev: true + + /@lerna/filter-options/4.0.0: + resolution: {integrity: sha512-vV2ANOeZhOqM0rzXnYcFFCJ/kBWy/3OA58irXih9AMTAlQLymWAK0akWybl++sUJ4HB9Hx12TOqaXbYS2NM5uw==} + engines: {node: '>= 10.18.0'} + dependencies: + '@lerna/collect-updates': 4.0.0 + '@lerna/filter-packages': 4.0.0 + dedent: 0.7.0 + npmlog: 4.1.2 + dev: true + + /@lerna/filter-packages/4.0.0: + resolution: {integrity: sha512-+4AJIkK7iIiOaqCiVTYJxh/I9qikk4XjNQLhE3kixaqgMuHl1NQ99qXRR0OZqAWB9mh8Z1HA9bM5K1HZLBTOqA==} + engines: {node: '>= 10.18.0'} + dependencies: + '@lerna/validation-error': 4.0.0 + multimatch: 5.0.0 + npmlog: 4.1.2 + dev: true + + /@lerna/get-npm-exec-opts/4.0.0: + resolution: {integrity: sha512-yvmkerU31CTWS2c7DvmAWmZVeclPBqI7gPVr5VATUKNWJ/zmVcU4PqbYoLu92I9Qc4gY1TuUplMNdNuZTSL7IQ==} + engines: {node: '>= 10.18.0'} + dependencies: + npmlog: 4.1.2 + dev: true + + /@lerna/get-packed/4.0.0: + resolution: {integrity: sha512-rfWONRsEIGyPJTxFzC8ECb3ZbsDXJbfqWYyeeQQDrJRPnEJErlltRLPLgC2QWbxFgFPsoDLeQmFHJnf0iDfd8w==} + engines: {node: '>= 10.18.0'} + dependencies: + fs-extra: 9.1.0 + ssri: 8.0.1 + tar: 6.1.11 + dev: true + + /@lerna/github-client/4.0.0: + resolution: {integrity: sha512-2jhsldZtTKXYUBnOm23Lb0Fx8G4qfSXF9y7UpyUgWUj+YZYd+cFxSuorwQIgk5P4XXrtVhsUesIsli+BYSThiw==} + engines: {node: '>= 10.18.0'} + dependencies: + '@lerna/child-process': 4.0.0 + '@octokit/plugin-enterprise-rest': 6.0.1 + '@octokit/rest': 18.12.0 + git-url-parse: 11.6.0 + npmlog: 4.1.2 + transitivePeerDependencies: + - encoding + dev: true + + /@lerna/gitlab-client/4.0.0: + resolution: {integrity: sha512-OMUpGSkeDWFf7BxGHlkbb35T7YHqVFCwBPSIR6wRsszY8PAzCYahtH3IaJzEJyUg6vmZsNl0FSr3pdA2skhxqA==} + engines: {node: '>= 10.18.0'} + dependencies: + node-fetch: 2.6.7 + npmlog: 4.1.2 + whatwg-url: 8.7.0 + transitivePeerDependencies: + - encoding + dev: true + + /@lerna/global-options/4.0.0: + resolution: {integrity: sha512-TRMR8afAHxuYBHK7F++Ogop2a82xQjoGna1dvPOY6ltj/pEx59pdgcJfYcynYqMkFIk8bhLJJN9/ndIfX29FTQ==} + engines: {node: '>= 10.18.0'} + dev: true + + /@lerna/has-npm-version/4.0.0: + resolution: {integrity: sha512-LQ3U6XFH8ZmLCsvsgq1zNDqka0Xzjq5ibVN+igAI5ccRWNaUsE/OcmsyMr50xAtNQMYMzmpw5GVLAivT2/YzCg==} + engines: {node: '>= 10.18.0'} + dependencies: + '@lerna/child-process': 4.0.0 + semver: 7.3.8 + dev: true + + /@lerna/import/4.0.0: + resolution: {integrity: sha512-FaIhd+4aiBousKNqC7TX1Uhe97eNKf5/SC7c5WZANVWtC7aBWdmswwDt3usrzCNpj6/Wwr9EtEbYROzxKH8ffg==} + engines: {node: '>= 10.18.0'} + dependencies: + '@lerna/child-process': 4.0.0 + '@lerna/command': 4.0.0 + '@lerna/prompt': 4.0.0 + '@lerna/pulse-till-done': 4.0.0 + '@lerna/validation-error': 4.0.0 + dedent: 0.7.0 + fs-extra: 9.1.0 + p-map-series: 2.1.0 + dev: true + + /@lerna/info/4.0.0: + resolution: {integrity: sha512-8Uboa12kaCSZEn4XRfPz5KU9XXoexSPS4oeYGj76s2UQb1O1GdnEyfjyNWoUl1KlJ2i/8nxUskpXIftoFYH0/Q==} + engines: {node: '>= 10.18.0'} + dependencies: + '@lerna/command': 4.0.0 + '@lerna/output': 4.0.0 + envinfo: 7.8.1 + dev: true + + /@lerna/init/4.0.0: + resolution: {integrity: sha512-wY6kygop0BCXupzWj5eLvTUqdR7vIAm0OgyV9WHpMYQGfs1V22jhztt8mtjCloD/O0nEe4tJhdG62XU5aYmPNQ==} + engines: {node: '>= 10.18.0'} + dependencies: + '@lerna/child-process': 4.0.0 + '@lerna/command': 4.0.0 + fs-extra: 9.1.0 + p-map: 4.0.0 + write-json-file: 4.3.0 + dev: true + + /@lerna/link/4.0.0: + resolution: {integrity: sha512-KlvPi7XTAcVOByfaLlOeYOfkkDcd+bejpHMCd1KcArcFTwijOwXOVi24DYomIeHvy6HsX/IUquJ4PPUJIeB4+w==} + engines: {node: '>= 10.18.0'} + dependencies: + '@lerna/command': 4.0.0 + '@lerna/package-graph': 4.0.0 + '@lerna/symlink-dependencies': 4.0.0 + p-map: 4.0.0 + slash: 3.0.0 + dev: true + + /@lerna/list/4.0.0: + resolution: {integrity: sha512-L2B5m3P+U4Bif5PultR4TI+KtW+SArwq1i75QZ78mRYxPc0U/piau1DbLOmwrdqr99wzM49t0Dlvl6twd7GHFg==} + engines: {node: '>= 10.18.0'} + dependencies: + '@lerna/command': 4.0.0 + '@lerna/filter-options': 4.0.0 + '@lerna/listable': 4.0.0 + '@lerna/output': 4.0.0 + dev: true + + /@lerna/listable/4.0.0: + resolution: {integrity: sha512-/rPOSDKsOHs5/PBLINZOkRIX1joOXUXEtyUs5DHLM8q6/RP668x/1lFhw6Dx7/U+L0+tbkpGtZ1Yt0LewCLgeQ==} + engines: {node: '>= 10.18.0'} + dependencies: + '@lerna/query-graph': 4.0.0 + chalk: 4.1.2 + columnify: 1.6.0 + dev: true + + /@lerna/log-packed/4.0.0: + resolution: {integrity: sha512-+dpCiWbdzgMAtpajLToy9PO713IHoE6GV/aizXycAyA07QlqnkpaBNZ8DW84gHdM1j79TWockGJo9PybVhrrZQ==} + engines: {node: '>= 10.18.0'} + dependencies: + byte-size: 7.0.1 + columnify: 1.6.0 + has-unicode: 2.0.1 + npmlog: 4.1.2 + dev: true + + /@lerna/npm-conf/4.0.0: + resolution: {integrity: sha512-uS7H02yQNq3oejgjxAxqq/jhwGEE0W0ntr8vM3EfpCW1F/wZruwQw+7bleJQ9vUBjmdXST//tk8mXzr5+JXCfw==} + engines: {node: '>= 10.18.0'} + dependencies: + config-chain: 1.1.13 + pify: 5.0.0 + dev: true + + /@lerna/npm-dist-tag/4.0.0: + resolution: {integrity: sha512-F20sg28FMYTgXqEQihgoqSfwmq+Id3zT23CnOwD+XQMPSy9IzyLf1fFVH319vXIw6NF6Pgs4JZN2Qty6/CQXGw==} + engines: {node: '>= 10.18.0'} + dependencies: + '@lerna/otplease': 4.0.0 + npm-package-arg: 8.1.5 + npm-registry-fetch: 9.0.0 + npmlog: 4.1.2 + transitivePeerDependencies: + - bluebird + - supports-color + dev: true + + /@lerna/npm-install/4.0.0: + resolution: {integrity: sha512-aKNxq2j3bCH3eXl3Fmu4D54s/YLL9WSwV8W7X2O25r98wzrO38AUN6AB9EtmAx+LV/SP15et7Yueg9vSaanRWg==} + engines: {node: '>= 10.18.0'} + dependencies: + '@lerna/child-process': 4.0.0 + '@lerna/get-npm-exec-opts': 4.0.0 + fs-extra: 9.1.0 + npm-package-arg: 8.1.5 + npmlog: 4.1.2 + signal-exit: 3.0.7 + write-pkg: 4.0.0 + dev: true + + /@lerna/npm-publish/4.0.0: + resolution: {integrity: sha512-vQb7yAPRo5G5r77DRjHITc9piR9gvEKWrmfCH7wkfBnGWEqu7n8/4bFQ7lhnkujvc8RXOsYpvbMQkNfkYibD/w==} + engines: {node: '>= 10.18.0'} + dependencies: + '@lerna/otplease': 4.0.0 + '@lerna/run-lifecycle': 4.0.0 + fs-extra: 9.1.0 + libnpmpublish: 4.0.2 + npm-package-arg: 8.1.5 + npmlog: 4.1.2 + pify: 5.0.0 + read-package-json: 3.0.1 + transitivePeerDependencies: + - bluebird + - supports-color + dev: true + + /@lerna/npm-run-script/4.0.0: + resolution: {integrity: sha512-Jmyh9/IwXJjOXqKfIgtxi0bxi1pUeKe5bD3S81tkcy+kyng/GNj9WSqD5ZggoNP2NP//s4CLDAtUYLdP7CU9rA==} + engines: {node: '>= 10.18.0'} + dependencies: + '@lerna/child-process': 4.0.0 + '@lerna/get-npm-exec-opts': 4.0.0 + npmlog: 4.1.2 + dev: true + + /@lerna/otplease/4.0.0: + resolution: {integrity: sha512-Sgzbqdk1GH4psNiT6hk+BhjOfIr/5KhGBk86CEfHNJTk9BK4aZYyJD4lpDbDdMjIV4g03G7pYoqHzH765T4fxw==} + engines: {node: '>= 10.18.0'} + dependencies: + '@lerna/prompt': 4.0.0 + dev: true + + /@lerna/output/4.0.0: + resolution: {integrity: sha512-Un1sHtO1AD7buDQrpnaYTi2EG6sLF+KOPEAMxeUYG5qG3khTs2Zgzq5WE3dt2N/bKh7naESt20JjIW6tBELP0w==} + engines: {node: '>= 10.18.0'} + dependencies: + npmlog: 4.1.2 + dev: true + + /@lerna/pack-directory/4.0.0: + resolution: {integrity: sha512-NJrmZNmBHS+5aM+T8N6FVbaKFScVqKlQFJNY2k7nsJ/uklNKsLLl6VhTQBPwMTbf6Tf7l6bcKzpy7aePuq9UiQ==} + engines: {node: '>= 10.18.0'} + dependencies: + '@lerna/get-packed': 4.0.0 + '@lerna/package': 4.0.0 + '@lerna/run-lifecycle': 4.0.0 + npm-packlist: 2.2.2 + npmlog: 4.1.2 + tar: 6.1.11 + temp-write: 4.0.0 + dev: true + + /@lerna/package-graph/4.0.0: + resolution: {integrity: sha512-QED2ZCTkfXMKFoTGoccwUzjHtZMSf3UKX14A4/kYyBms9xfFsesCZ6SLI5YeySEgcul8iuIWfQFZqRw+Qrjraw==} + engines: {node: '>= 10.18.0'} + dependencies: + '@lerna/prerelease-id-from-version': 4.0.0 + '@lerna/validation-error': 4.0.0 + npm-package-arg: 8.1.5 + npmlog: 4.1.2 + semver: 7.3.8 + dev: true + + /@lerna/package/4.0.0: + resolution: {integrity: sha512-l0M/izok6FlyyitxiQKr+gZLVFnvxRQdNhzmQ6nRnN9dvBJWn+IxxpM+cLqGACatTnyo9LDzNTOj2Db3+s0s8Q==} + engines: {node: '>= 10.18.0'} + dependencies: + load-json-file: 6.2.0 + npm-package-arg: 8.1.5 + write-pkg: 4.0.0 + dev: true + + /@lerna/prerelease-id-from-version/4.0.0: + resolution: {integrity: sha512-GQqguzETdsYRxOSmdFZ6zDBXDErIETWOqomLERRY54f4p+tk4aJjoVdd9xKwehC9TBfIFvlRbL1V9uQGHh1opg==} + engines: {node: '>= 10.18.0'} + dependencies: + semver: 7.3.8 + dev: true + + /@lerna/profiler/4.0.0: + resolution: {integrity: sha512-/BaEbqnVh1LgW/+qz8wCuI+obzi5/vRE8nlhjPzdEzdmWmZXuCKyWSEzAyHOJWw1ntwMiww5dZHhFQABuoFz9Q==} + engines: {node: '>= 10.18.0'} + dependencies: + fs-extra: 9.1.0 + npmlog: 4.1.2 + upath: 2.0.1 + dev: true + + /@lerna/project/4.0.0: + resolution: {integrity: sha512-o0MlVbDkD5qRPkFKlBZsXZjoNTWPyuL58564nSfZJ6JYNmgAptnWPB2dQlAc7HWRZkmnC2fCkEdoU+jioPavbg==} + engines: {node: '>= 10.18.0'} + dependencies: + '@lerna/package': 4.0.0 + '@lerna/validation-error': 4.0.0 + cosmiconfig: 7.0.1 + dedent: 0.7.0 + dot-prop: 6.0.1 + glob-parent: 5.1.2 + globby: 11.1.0 + load-json-file: 6.2.0 + npmlog: 4.1.2 + p-map: 4.0.0 + resolve-from: 5.0.0 + write-json-file: 4.3.0 + dev: true + + /@lerna/prompt/4.0.0: + resolution: {integrity: sha512-4Ig46oCH1TH5M7YyTt53fT6TuaKMgqUUaqdgxvp6HP6jtdak6+amcsqB8YGz2eQnw/sdxunx84DfI9XpoLj4bQ==} + engines: {node: '>= 10.18.0'} + dependencies: + inquirer: 7.3.3 + npmlog: 4.1.2 + dev: true + + /@lerna/publish/4.0.0: + resolution: {integrity: sha512-K8jpqjHrChH22qtkytA5GRKIVFEtqBF6JWj1I8dWZtHs4Jywn8yB1jQ3BAMLhqmDJjWJtRck0KXhQQKzDK2UPg==} + engines: {node: '>= 10.18.0'} + dependencies: + '@lerna/check-working-tree': 4.0.0 + '@lerna/child-process': 4.0.0 + '@lerna/collect-updates': 4.0.0 + '@lerna/command': 4.0.0 + '@lerna/describe-ref': 4.0.0 + '@lerna/log-packed': 4.0.0 + '@lerna/npm-conf': 4.0.0 + '@lerna/npm-dist-tag': 4.0.0 + '@lerna/npm-publish': 4.0.0 + '@lerna/otplease': 4.0.0 + '@lerna/output': 4.0.0 + '@lerna/pack-directory': 4.0.0 + '@lerna/prerelease-id-from-version': 4.0.0 + '@lerna/prompt': 4.0.0 + '@lerna/pulse-till-done': 4.0.0 + '@lerna/run-lifecycle': 4.0.0 + '@lerna/run-topologically': 4.0.0 + '@lerna/validation-error': 4.0.0 + '@lerna/version': 4.0.0 + fs-extra: 9.1.0 + libnpmaccess: 4.0.3 + npm-package-arg: 8.1.5 + npm-registry-fetch: 9.0.0 + npmlog: 4.1.2 + p-map: 4.0.0 + p-pipe: 3.1.0 + pacote: 11.3.5 + semver: 7.3.8 + transitivePeerDependencies: + - bluebird + - encoding + - supports-color + dev: true + + /@lerna/pulse-till-done/4.0.0: + resolution: {integrity: sha512-Frb4F7QGckaybRhbF7aosLsJ5e9WuH7h0KUkjlzSByVycxY91UZgaEIVjS2oN9wQLrheLMHl6SiFY0/Pvo0Cxg==} + engines: {node: '>= 10.18.0'} + dependencies: + npmlog: 4.1.2 + dev: true + + /@lerna/query-graph/4.0.0: + resolution: {integrity: sha512-YlP6yI3tM4WbBmL9GCmNDoeQyzcyg1e4W96y/PKMZa5GbyUvkS2+Jc2kwPD+5KcXou3wQZxSPzR3Te5OenaDdg==} + engines: {node: '>= 10.18.0'} + dependencies: + '@lerna/package-graph': 4.0.0 + dev: true + + /@lerna/resolve-symlink/4.0.0: + resolution: {integrity: sha512-RtX8VEUzqT+uLSCohx8zgmjc6zjyRlh6i/helxtZTMmc4+6O4FS9q5LJas2uGO2wKvBlhcD6siibGt7dIC3xZA==} + engines: {node: '>= 10.18.0'} + dependencies: + fs-extra: 9.1.0 + npmlog: 4.1.2 + read-cmd-shim: 2.0.0 + dev: true + + /@lerna/rimraf-dir/4.0.0: + resolution: {integrity: sha512-QNH9ABWk9mcMJh2/muD9iYWBk1oQd40y6oH+f3wwmVGKYU5YJD//+zMiBI13jxZRtwBx0vmBZzkBkK1dR11cBg==} + engines: {node: '>= 10.18.0'} + dependencies: + '@lerna/child-process': 4.0.0 + npmlog: 4.1.2 + path-exists: 4.0.0 + rimraf: 3.0.2 + dev: true + + /@lerna/run-lifecycle/4.0.0: + resolution: {integrity: sha512-IwxxsajjCQQEJAeAaxF8QdEixfI7eLKNm4GHhXHrgBu185JcwScFZrj9Bs+PFKxwb+gNLR4iI5rpUdY8Y0UdGQ==} + engines: {node: '>= 10.18.0'} + dependencies: + '@lerna/npm-conf': 4.0.0 + npm-lifecycle: 3.1.5 + npmlog: 4.1.2 + dev: true + + /@lerna/run-topologically/4.0.0: + resolution: {integrity: sha512-EVZw9hGwo+5yp+VL94+NXRYisqgAlj0jWKWtAIynDCpghRxCE5GMO3xrQLmQgqkpUl9ZxQFpICgYv5DW4DksQA==} + engines: {node: '>= 10.18.0'} + dependencies: + '@lerna/query-graph': 4.0.0 + p-queue: 6.6.2 + dev: true + + /@lerna/run/4.0.0: + resolution: {integrity: sha512-9giulCOzlMPzcZS/6Eov6pxE9gNTyaXk0Man+iCIdGJNMrCnW7Dme0Z229WWP/UoxDKg71F2tMsVVGDiRd8fFQ==} + engines: {node: '>= 10.18.0'} + dependencies: + '@lerna/command': 4.0.0 + '@lerna/filter-options': 4.0.0 + '@lerna/npm-run-script': 4.0.0 + '@lerna/output': 4.0.0 + '@lerna/profiler': 4.0.0 + '@lerna/run-topologically': 4.0.0 + '@lerna/timer': 4.0.0 + '@lerna/validation-error': 4.0.0 + p-map: 4.0.0 + dev: true + + /@lerna/symlink-binary/4.0.0: + resolution: {integrity: sha512-zualodWC4q1QQc1pkz969hcFeWXOsVYZC5AWVtAPTDfLl+TwM7eG/O6oP+Rr3fFowspxo6b1TQ6sYfDV6HXNWA==} + engines: {node: '>= 10.18.0'} + dependencies: + '@lerna/create-symlink': 4.0.0 + '@lerna/package': 4.0.0 + fs-extra: 9.1.0 + p-map: 4.0.0 + dev: true + + /@lerna/symlink-dependencies/4.0.0: + resolution: {integrity: sha512-BABo0MjeUHNAe2FNGty1eantWp8u83BHSeIMPDxNq0MuW2K3CiQRaeWT3EGPAzXpGt0+hVzBrA6+OT0GPn7Yuw==} + engines: {node: '>= 10.18.0'} + dependencies: + '@lerna/create-symlink': 4.0.0 + '@lerna/resolve-symlink': 4.0.0 + '@lerna/symlink-binary': 4.0.0 + fs-extra: 9.1.0 + p-map: 4.0.0 + p-map-series: 2.1.0 + dev: true + + /@lerna/timer/4.0.0: + resolution: {integrity: sha512-WFsnlaE7SdOvjuyd05oKt8Leg3ENHICnvX3uYKKdByA+S3g+TCz38JsNs7OUZVt+ba63nC2nbXDlUnuT2Xbsfg==} + engines: {node: '>= 10.18.0'} + dev: true + + /@lerna/validation-error/4.0.0: + resolution: {integrity: sha512-1rBOM5/koiVWlRi3V6dB863E1YzJS8v41UtsHgMr6gB2ncJ2LsQtMKlJpi3voqcgh41H8UsPXR58RrrpPpufyw==} + engines: {node: '>= 10.18.0'} + dependencies: + npmlog: 4.1.2 + dev: true + + /@lerna/version/4.0.0: + resolution: {integrity: sha512-otUgiqs5W9zGWJZSCCMRV/2Zm2A9q9JwSDS7s/tlKq4mWCYriWo7+wsHEA/nPTMDyYyBO5oyZDj+3X50KDUzeA==} + engines: {node: '>= 10.18.0'} + dependencies: + '@lerna/check-working-tree': 4.0.0 + '@lerna/child-process': 4.0.0 + '@lerna/collect-updates': 4.0.0 + '@lerna/command': 4.0.0 + '@lerna/conventional-commits': 4.0.0 + '@lerna/github-client': 4.0.0 + '@lerna/gitlab-client': 4.0.0 + '@lerna/output': 4.0.0 + '@lerna/prerelease-id-from-version': 4.0.0 + '@lerna/prompt': 4.0.0 + '@lerna/run-lifecycle': 4.0.0 + '@lerna/run-topologically': 4.0.0 + '@lerna/validation-error': 4.0.0 + chalk: 4.1.2 + dedent: 0.7.0 + load-json-file: 6.2.0 + minimatch: 3.1.2 + npmlog: 4.1.2 + p-map: 4.0.0 + p-pipe: 3.1.0 + p-reduce: 2.1.0 + p-waterfall: 2.1.1 + semver: 7.3.8 + slash: 3.0.0 + temp-write: 4.0.0 + write-json-file: 4.3.0 + transitivePeerDependencies: + - encoding + dev: true + + /@lerna/write-log-file/4.0.0: + resolution: {integrity: sha512-XRG5BloiArpXRakcnPHmEHJp+4AtnhRtpDIHSghmXD5EichI1uD73J7FgPp30mm2pDRq3FdqB0NbwSEsJ9xFQg==} + engines: {node: '>= 10.18.0'} + dependencies: + npmlog: 4.1.2 + write-file-atomic: 3.0.3 + dev: true + + /@nodelib/fs.scandir/2.1.5: + resolution: {integrity: sha512-vq24Bq3ym5HEQm2NKCr3yXDwjc7vTsEThRDnkp2DK9p1uqLR+DHurm/NOTo0KG7HYHU7eppKZj3MyqYuMBf62g==} + engines: {node: '>= 8'} + dependencies: + '@nodelib/fs.stat': 2.0.5 + run-parallel: 1.2.0 + dev: true + + /@nodelib/fs.stat/2.0.5: + resolution: {integrity: sha512-RkhPPp2zrqDAQA/2jNhnztcPAlv64XdhIp7a7454A5ovI7Bukxgt7MX7udwAu3zg1DcpPU0rz3VV1SeaqvY4+A==} + engines: {node: '>= 8'} + dev: true + + /@nodelib/fs.walk/1.2.8: + resolution: {integrity: sha512-oGB+UxlgWcgQkgwo8GcEGwemoTFt3FIO9ababBmaGwXIoBKZ+GTy0pP185beGg7Llih/NSHSV2XAs1lnznocSg==} + engines: {node: '>= 8'} + dependencies: + '@nodelib/fs.scandir': 2.1.5 + fastq: 1.13.0 + dev: true + + /@npmcli/ci-detect/1.4.0: + resolution: {integrity: sha512-3BGrt6FLjqM6br5AhWRKTr3u5GIVkjRYeAFrMp3HjnfICrg4xOrVRwFavKT6tsp++bq5dluL5t8ME/Nha/6c1Q==} + dev: true + + /@npmcli/fs/1.1.1: + resolution: {integrity: sha512-8KG5RD0GVP4ydEzRn/I4BNDuxDtqVbOdm8675T49OIG/NGhaK0pjPX7ZcDlvKYbA+ulvVK3ztfcF4uBdOxuJbQ==} + dependencies: + '@gar/promisify': 1.1.3 + semver: 7.3.8 + dev: true + + /@npmcli/fs/2.1.2: + resolution: {integrity: sha512-yOJKRvohFOaLqipNtwYB9WugyZKhC/DZC4VYPmpaCzDBrA8YpK3qHZ8/HGscMnE4GqbkLNuVcCnxkeQEdGt6LQ==} + engines: {node: ^12.13.0 || ^14.15.0 || >=16.0.0} + dependencies: + '@gar/promisify': 1.1.3 + semver: 7.3.8 + dev: true + + /@npmcli/git/2.1.0: + resolution: {integrity: sha512-/hBFX/QG1b+N7PZBFs0bi+evgRZcK9nWBxQKZkGoXUT5hJSwl5c4d7y8/hm+NQZRPhQ67RzFaj5UM9YeyKoryw==} + dependencies: + '@npmcli/promise-spawn': 1.3.2 + lru-cache: 6.0.0 + mkdirp: 1.0.4 + npm-pick-manifest: 6.1.1 + promise-inflight: 1.0.1 + promise-retry: 2.0.1 + semver: 7.3.8 + which: 2.0.2 + transitivePeerDependencies: + - bluebird + dev: true + + /@npmcli/git/3.0.2: + resolution: {integrity: sha512-CAcd08y3DWBJqJDpfuVL0uijlq5oaXaOJEKHKc4wqrjd00gkvTZB+nFuLn+doOOKddaQS9JfqtNoFCO2LCvA3w==} + engines: {node: ^12.13.0 || ^14.15.0 || >=16.0.0} + dependencies: + '@npmcli/promise-spawn': 3.0.0 + lru-cache: 7.14.0 + mkdirp: 1.0.4 + npm-pick-manifest: 7.0.2 + proc-log: 2.0.1 + promise-inflight: 1.0.1 + promise-retry: 2.0.1 + semver: 7.3.8 + which: 2.0.2 + transitivePeerDependencies: + - bluebird + dev: true + + /@npmcli/installed-package-contents/1.0.7: + resolution: {integrity: sha512-9rufe0wnJusCQoLpV9ZPKIVP55itrM5BxOXs10DmdbRfgWtHy1LDyskbwRnBghuB0PrF7pNPOqREVtpz4HqzKw==} + engines: {node: '>= 10'} + hasBin: true + dependencies: + npm-bundled: 1.1.2 + npm-normalize-package-bin: 1.0.1 + dev: true + + /@npmcli/move-file/1.1.2: + resolution: {integrity: sha512-1SUf/Cg2GzGDyaf15aR9St9TWlb+XvbZXWpDx8YKs7MLzMH/BCeopv+y9vzrzgkfykCGuWOlSu3mZhj2+FQcrg==} + engines: {node: '>=10'} + dependencies: + mkdirp: 1.0.4 + rimraf: 3.0.2 + dev: true + + /@npmcli/move-file/2.0.1: + resolution: {integrity: sha512-mJd2Z5TjYWq/ttPLLGqArdtnC74J6bOzg4rMDnN+p1xTacZ2yPRCk2y0oSWQtygLR9YVQXgOcONrwtnk3JupxQ==} + engines: {node: ^12.13.0 || ^14.15.0 || >=16.0.0} + dependencies: + mkdirp: 1.0.4 + rimraf: 3.0.2 + dev: true + + /@npmcli/node-gyp/1.0.3: + resolution: {integrity: sha512-fnkhw+fmX65kiLqk6E3BFLXNC26rUhK90zVwe2yncPliVT/Qos3xjhTLE59Df8KnPlcwIERXKVlU1bXoUQ+liA==} + dev: true + + /@npmcli/node-gyp/2.0.0: + resolution: {integrity: sha512-doNI35wIe3bBaEgrlPfdJPaCpUR89pJWep4Hq3aRdh6gKazIVWfs0jHttvSSoq47ZXgC7h73kDsUl8AoIQUB+A==} + engines: {node: ^12.13.0 || ^14.15.0 || >=16.0.0} + dev: true + + /@npmcli/promise-spawn/1.3.2: + resolution: {integrity: sha512-QyAGYo/Fbj4MXeGdJcFzZ+FkDkomfRBrPM+9QYJSg+PxgAUL+LU3FneQk37rKR2/zjqkCV1BLHccX98wRXG3Sg==} + dependencies: + infer-owner: 1.0.4 + dev: true + + /@npmcli/promise-spawn/3.0.0: + resolution: {integrity: sha512-s9SgS+p3a9Eohe68cSI3fi+hpcZUmXq5P7w0kMlAsWVtR7XbK3ptkZqKT2cK1zLDObJ3sR+8P59sJE0w/KTL1g==} + engines: {node: ^12.13.0 || ^14.15.0 || >=16.0.0} + dependencies: + infer-owner: 1.0.4 + dev: true + + /@npmcli/run-script/1.8.6: + resolution: {integrity: sha512-e42bVZnC6VluBZBAFEr3YrdqSspG3bgilyg4nSLBJ7TRGNCzxHa92XAHxQBLYg0BmgwO4b2mf3h/l5EkEWRn3g==} + dependencies: + '@npmcli/node-gyp': 1.0.3 + '@npmcli/promise-spawn': 1.3.2 + node-gyp: 7.1.2 + read-package-json-fast: 2.0.3 + dev: true + + /@npmcli/run-script/4.2.1: + resolution: {integrity: sha512-7dqywvVudPSrRCW5nTHpHgeWnbBtz8cFkOuKrecm6ih+oO9ciydhWt6OF7HlqupRRmB8Q/gECVdB9LMfToJbRg==} + engines: {node: ^12.13.0 || ^14.15.0 || >=16.0.0} + dependencies: + '@npmcli/node-gyp': 2.0.0 + '@npmcli/promise-spawn': 3.0.0 + node-gyp: 9.3.0 + read-package-json-fast: 2.0.3 + which: 2.0.2 + transitivePeerDependencies: + - bluebird + - supports-color + dev: true + + /@octokit/auth-token/2.5.0: + resolution: {integrity: sha512-r5FVUJCOLl19AxiuZD2VRZ/ORjp/4IN98Of6YJoJOkY75CIBuYfmiNHGrDwXr+aLGG55igl9QrxX3hbiXlLb+g==} + dependencies: + '@octokit/types': 6.41.0 + dev: true + + /@octokit/core/3.6.0: + resolution: {integrity: sha512-7RKRKuA4xTjMhY+eG3jthb3hlZCsOwg3rztWh75Xc+ShDWOfDDATWbeZpAHBNRpm4Tv9WgBMOy1zEJYXG6NJ7Q==} + dependencies: + '@octokit/auth-token': 2.5.0 + '@octokit/graphql': 4.8.0 + '@octokit/request': 5.6.3 + '@octokit/request-error': 2.1.0 + '@octokit/types': 6.41.0 + before-after-hook: 2.2.3 + universal-user-agent: 6.0.0 + transitivePeerDependencies: + - encoding + dev: true + + /@octokit/endpoint/6.0.12: + resolution: {integrity: sha512-lF3puPwkQWGfkMClXb4k/eUT/nZKQfxinRWJrdZaJO85Dqwo/G0yOC434Jr2ojwafWJMYqFGFa5ms4jJUgujdA==} + dependencies: + '@octokit/types': 6.41.0 + is-plain-object: 5.0.0 + universal-user-agent: 6.0.0 + dev: true + + /@octokit/graphql/4.8.0: + resolution: {integrity: sha512-0gv+qLSBLKF0z8TKaSKTsS39scVKF9dbMxJpj3U0vC7wjNWFuIpL/z76Qe2fiuCbDRcJSavkXsVtMS6/dtQQsg==} + dependencies: + '@octokit/request': 5.6.3 + '@octokit/types': 6.41.0 + universal-user-agent: 6.0.0 + transitivePeerDependencies: + - encoding + dev: true + + /@octokit/openapi-types/12.11.0: + resolution: {integrity: sha512-VsXyi8peyRq9PqIz/tpqiL2w3w80OgVMwBHltTml3LmVvXiphgeqmY9mvBw9Wu7e0QWk/fqD37ux8yP5uVekyQ==} + dev: true + + /@octokit/plugin-enterprise-rest/6.0.1: + resolution: {integrity: sha512-93uGjlhUD+iNg1iWhUENAtJata6w5nE+V4urXOAlIXdco6xNZtUSfYY8dzp3Udy74aqO/B5UZL80x/YMa5PKRw==} + dev: true + + /@octokit/plugin-paginate-rest/2.21.3_@octokit+core@3.6.0: + resolution: {integrity: sha512-aCZTEf0y2h3OLbrgKkrfFdjRL6eSOo8komneVQJnYecAxIej7Bafor2xhuDJOIFau4pk0i/P28/XgtbyPF0ZHw==} + peerDependencies: + '@octokit/core': '>=2' + dependencies: + '@octokit/core': 3.6.0 + '@octokit/types': 6.41.0 + dev: true + + /@octokit/plugin-request-log/1.0.4_@octokit+core@3.6.0: + resolution: {integrity: sha512-mLUsMkgP7K/cnFEw07kWqXGF5LKrOkD+lhCrKvPHXWDywAwuDUeDwWBpc69XK3pNX0uKiVt8g5z96PJ6z9xCFA==} + peerDependencies: + '@octokit/core': '>=3' + dependencies: + '@octokit/core': 3.6.0 + dev: true + + /@octokit/plugin-rest-endpoint-methods/5.16.2_@octokit+core@3.6.0: + resolution: {integrity: sha512-8QFz29Fg5jDuTPXVtey05BLm7OB+M8fnvE64RNegzX7U+5NUXcOcnpTIK0YfSHBg8gYd0oxIq3IZTe9SfPZiRw==} + peerDependencies: + '@octokit/core': '>=3' + dependencies: + '@octokit/core': 3.6.0 + '@octokit/types': 6.41.0 + deprecation: 2.3.1 + dev: true + + /@octokit/request-error/2.1.0: + resolution: {integrity: sha512-1VIvgXxs9WHSjicsRwq8PlR2LR2x6DwsJAaFgzdi0JfJoGSO8mYI/cHJQ+9FbN21aa+DrgNLnwObmyeSC8Rmpg==} + dependencies: + '@octokit/types': 6.41.0 + deprecation: 2.3.1 + once: 1.4.0 + dev: true + + /@octokit/request/5.6.3: + resolution: {integrity: sha512-bFJl0I1KVc9jYTe9tdGGpAMPy32dLBXXo1dS/YwSCTL/2nd9XeHsY616RE3HPXDVk+a+dBuzyz5YdlXwcDTr2A==} + dependencies: + '@octokit/endpoint': 6.0.12 + '@octokit/request-error': 2.1.0 + '@octokit/types': 6.41.0 + is-plain-object: 5.0.0 + node-fetch: 2.6.7 + universal-user-agent: 6.0.0 + transitivePeerDependencies: + - encoding + dev: true + + /@octokit/rest/18.12.0: + resolution: {integrity: sha512-gDPiOHlyGavxr72y0guQEhLsemgVjwRePayJ+FcKc2SJqKUbxbkvf5kAZEWA/MKvsfYlQAMVzNJE3ezQcxMJ2Q==} + dependencies: + '@octokit/core': 3.6.0 + '@octokit/plugin-paginate-rest': 2.21.3_@octokit+core@3.6.0 + '@octokit/plugin-request-log': 1.0.4_@octokit+core@3.6.0 + '@octokit/plugin-rest-endpoint-methods': 5.16.2_@octokit+core@3.6.0 + transitivePeerDependencies: + - encoding + dev: true + + /@octokit/types/6.41.0: + resolution: {integrity: sha512-eJ2jbzjdijiL3B4PrSQaSjuF2sPEQPVCPzBvTHJD9Nz+9dw2SGH4K4xeQJ77YfTq5bRQ+bD8wT11JbeDPmxmGg==} + dependencies: + '@octokit/openapi-types': 12.11.0 + dev: true + + /@sindresorhus/is/0.14.0: + resolution: {integrity: sha512-9NET910DNaIPngYnLLPeg+Ogzqsi9uM4mSboU5y6p8S5DzMTVEsJZrawi+BoDNUVBa2DhJqQYUFvMDfgU062LQ==} + engines: {node: '>=6'} + dev: true + + /@szmarczak/http-timer/1.1.2: + resolution: {integrity: sha512-XIB2XbzHTN6ieIjfIMV9hlVcfPU26s2vafYWQcZHWXHOxiaRZYEDKEwdl129Zyg50+foYV2jCgtrqSA6qNuNSA==} + engines: {node: '>=6'} + dependencies: + defer-to-connect: 1.1.3 + dev: true + + /@tootallnate/once/1.1.2: + resolution: {integrity: sha512-RbzJvlNzmRq5c3O09UipeuXno4tA1FE6ikOjxZK0tuxVv3412l64l5t1W5pj4+rJq9vpkm/kwiR07aZXnsKPxw==} + engines: {node: '>= 6'} + dev: true + + /@tootallnate/once/2.0.0: + resolution: {integrity: sha512-XCuKFP5PS55gnMVu3dty8KPatLqUoy/ZYzDzAGCQ8JNFCkLXzmI7vNHCR+XpbZaMWQK/vQubr7PkYq8g470J/A==} + engines: {node: '>= 10'} + dev: true + + /@types/json-schema/7.0.11: + resolution: {integrity: sha512-wOuvG1SN4Us4rez+tylwwwCV1psiNVOkJeM3AUWUNWg/jDQY2+HE/444y5gc+jBmRqASOm2Oeh5c1axHobwRKQ==} + dev: true + + /@types/json5/0.0.29: + resolution: {integrity: sha512-dRLjCWHYg4oaA77cxO64oO+7JwCwnIzkZPdrrC71jQmQtlhM556pwKo5bUzqvZndkVbeFLIIi+9TC40JNF5hNQ==} + dev: true + + /@types/keyv/3.1.4: + resolution: {integrity: sha512-BQ5aZNSCpj7D6K2ksrRCTmKRLEpnPvWDiLPfoGyhZ++8YtiK9d/3DBKPJgry359X/P1PfruyYwvnvwFjuEiEIg==} + dependencies: + '@types/node': 18.11.0 + dev: true + + /@types/minimatch/3.0.5: + resolution: {integrity: sha512-Klz949h02Gz2uZCMGwDUSDS1YBlTdDDgbWHi+81l29tQALUtvz4rAYi5uoVhE5Lagoq6DeqAUlbrHvW/mXDgdQ==} + dev: true + + /@types/minimist/1.2.2: + resolution: {integrity: sha512-jhuKLIRrhvCPLqwPcx6INqmKeiA5EWrsCOPhrlFSrbrmU4ZMPjj5Ul/oLCMDO98XRUIwVm78xICz4EPCektzeQ==} + dev: true + + /@types/node/18.11.0: + resolution: {integrity: sha512-IOXCvVRToe7e0ny7HpT/X9Rb2RYtElG1a+VshjwT00HxrM2dWBApHQoqsI6WiY7Q03vdf2bCrIGzVrkF/5t10w==} + dev: true + + /@types/normalize-package-data/2.4.1: + resolution: {integrity: sha512-Gj7cI7z+98M282Tqmp2K5EIsoouUEzbBJhQQzDE3jSIRk6r9gsz0oUokqIUR4u1R3dMHo0pDHM7sNOHyhulypw==} + dev: true + + /@types/parse-json/4.0.0: + resolution: {integrity: sha512-//oorEZjL6sbPcKUaCdIGlIUeH26mgzimjBB77G6XRgnDl/L5wOnpyBGRe/Mmf5CVW3PwEBE1NjiMZ/ssFh4wA==} + dev: true + + /@types/responselike/1.0.0: + resolution: {integrity: sha512-85Y2BjiufFzaMIlvJDvTTB8Fxl2xfLo4HgmHzVBz08w4wDePCTjYw66PdrolO0kzli3yam/YCgRufyo1DdQVTA==} + dependencies: + '@types/node': 18.11.0 + dev: true + + /@typescript-eslint/eslint-plugin/5.40.0_25sstg4uu2sk4pm7xcyzuov7xq: + resolution: {integrity: sha512-FIBZgS3DVJgqPwJzvZTuH4HNsZhHMa9SjxTKAZTlMsPw/UzpEjcf9f4dfgDJEHjK+HboUJo123Eshl6niwEm/Q==} + engines: {node: ^12.22.0 || ^14.17.0 || >=16.0.0} + peerDependencies: + '@typescript-eslint/parser': ^5.0.0 + eslint: ^6.0.0 || ^7.0.0 || ^8.0.0 + typescript: '*' + peerDependenciesMeta: + typescript: + optional: true + dependencies: + '@typescript-eslint/parser': 5.40.0_z4bbprzjrhnsfa24uvmcbu7f5q + '@typescript-eslint/scope-manager': 5.40.0 + '@typescript-eslint/type-utils': 5.40.0_z4bbprzjrhnsfa24uvmcbu7f5q + '@typescript-eslint/utils': 5.40.0_z4bbprzjrhnsfa24uvmcbu7f5q + debug: 4.3.4 + eslint: 8.25.0 + ignore: 5.2.0 + regexpp: 3.2.0 + semver: 7.3.8 + tsutils: 3.21.0_typescript@4.8.4 + typescript: 4.8.4 + transitivePeerDependencies: + - supports-color + dev: true + + /@typescript-eslint/parser/5.40.0_z4bbprzjrhnsfa24uvmcbu7f5q: + resolution: {integrity: sha512-Ah5gqyX2ySkiuYeOIDg7ap51/b63QgWZA7w6AHtFrag7aH0lRQPbLzUjk0c9o5/KZ6JRkTTDKShL4AUrQa6/hw==} + engines: {node: ^12.22.0 || ^14.17.0 || >=16.0.0} + peerDependencies: + eslint: ^6.0.0 || ^7.0.0 || ^8.0.0 + typescript: '*' + peerDependenciesMeta: + typescript: + optional: true + dependencies: + '@typescript-eslint/scope-manager': 5.40.0 + '@typescript-eslint/types': 5.40.0 + '@typescript-eslint/typescript-estree': 5.40.0_typescript@4.8.4 + debug: 4.3.4 + eslint: 8.25.0 + typescript: 4.8.4 + transitivePeerDependencies: + - supports-color + dev: true + + /@typescript-eslint/scope-manager/5.40.0: + resolution: {integrity: sha512-d3nPmjUeZtEWRvyReMI4I1MwPGC63E8pDoHy0BnrYjnJgilBD3hv7XOiETKLY/zTwI7kCnBDf2vWTRUVpYw0Uw==} + engines: {node: ^12.22.0 || ^14.17.0 || >=16.0.0} + dependencies: + '@typescript-eslint/types': 5.40.0 + '@typescript-eslint/visitor-keys': 5.40.0 + dev: true + + /@typescript-eslint/type-utils/5.40.0_z4bbprzjrhnsfa24uvmcbu7f5q: + resolution: {integrity: sha512-nfuSdKEZY2TpnPz5covjJqav+g5qeBqwSHKBvz7Vm1SAfy93SwKk/JeSTymruDGItTwNijSsno5LhOHRS1pcfw==} + engines: {node: ^12.22.0 || ^14.17.0 || >=16.0.0} + peerDependencies: + eslint: '*' + typescript: '*' + peerDependenciesMeta: + typescript: + optional: true + dependencies: + '@typescript-eslint/typescript-estree': 5.40.0_typescript@4.8.4 + '@typescript-eslint/utils': 5.40.0_z4bbprzjrhnsfa24uvmcbu7f5q + debug: 4.3.4 + eslint: 8.25.0 + tsutils: 3.21.0_typescript@4.8.4 + typescript: 4.8.4 + transitivePeerDependencies: + - supports-color + dev: true + + /@typescript-eslint/types/5.40.0: + resolution: {integrity: sha512-V1KdQRTXsYpf1Y1fXCeZ+uhjW48Niiw0VGt4V8yzuaDTU8Z1Xl7yQDyQNqyAFcVhpYXIVCEuxSIWTsLDpHgTbw==} + engines: {node: ^12.22.0 || ^14.17.0 || >=16.0.0} + dev: true + + /@typescript-eslint/typescript-estree/5.40.0_typescript@4.8.4: + resolution: {integrity: sha512-b0GYlDj8TLTOqwX7EGbw2gL5EXS2CPEWhF9nGJiGmEcmlpNBjyHsTwbqpyIEPVpl6br4UcBOYlcI2FJVtJkYhg==} + engines: {node: ^12.22.0 || ^14.17.0 || >=16.0.0} + peerDependencies: + typescript: '*' + peerDependenciesMeta: + typescript: + optional: true + dependencies: + '@typescript-eslint/types': 5.40.0 + '@typescript-eslint/visitor-keys': 5.40.0 + debug: 4.3.4 + globby: 11.1.0 + is-glob: 4.0.3 + semver: 7.3.8 + tsutils: 3.21.0_typescript@4.8.4 + typescript: 4.8.4 + transitivePeerDependencies: + - supports-color + dev: true + + /@typescript-eslint/utils/5.40.0_z4bbprzjrhnsfa24uvmcbu7f5q: + resolution: {integrity: sha512-MO0y3T5BQ5+tkkuYZJBjePewsY+cQnfkYeRqS6tPh28niiIwPnQ1t59CSRcs1ZwJJNOdWw7rv9pF8aP58IMihA==} + engines: {node: ^12.22.0 || ^14.17.0 || >=16.0.0} + peerDependencies: + eslint: ^6.0.0 || ^7.0.0 || ^8.0.0 + dependencies: + '@types/json-schema': 7.0.11 + '@typescript-eslint/scope-manager': 5.40.0 + '@typescript-eslint/types': 5.40.0 + '@typescript-eslint/typescript-estree': 5.40.0_typescript@4.8.4 + eslint: 8.25.0 + eslint-scope: 5.1.1 + eslint-utils: 3.0.0_eslint@8.25.0 + semver: 7.3.8 + transitivePeerDependencies: + - supports-color + - typescript + dev: true + + /@typescript-eslint/visitor-keys/5.40.0: + resolution: {integrity: sha512-ijJ+6yig+x9XplEpG2K6FUdJeQGGj/15U3S56W9IqXKJqleuD7zJ2AX/miLezwxpd7ZxDAqO87zWufKg+RPZyQ==} + engines: {node: ^12.22.0 || ^14.17.0 || >=16.0.0} + dependencies: + '@typescript-eslint/types': 5.40.0 + eslint-visitor-keys: 3.3.0 + dev: true + + /JSONStream/1.3.5: + resolution: {integrity: sha512-E+iruNOY8VV9s4JEbe1aNEm6MiszPRr/UfcHMz0TQh1BXSxHK+ASV1R6W4HpjBhSeS+54PIsAMCBmwD06LLsqQ==} + hasBin: true + dependencies: + jsonparse: 1.3.1 + through: 2.3.8 + dev: true + + /abbrev/1.1.1: + resolution: {integrity: sha512-nne9/IiQ/hzIhY6pdDnbBtz7DjPTKrY00P/zvPSm5pOFkl6xuGrGnXn/VtTNNfNtAfZ9/1RtehkszU9qcTii0Q==} + dev: true + + /acorn-jsx/5.3.2_acorn@8.8.0: + resolution: {integrity: sha512-rq9s+JNhf0IChjtDXxllJ7g41oZk5SlXtp0LHwyA5cejwn7vKmKp4pPri6YEePv2PU65sAsegbXtIinmDFDXgQ==} + peerDependencies: + acorn: ^6.0.0 || ^7.0.0 || ^8.0.0 + dependencies: + acorn: 8.8.0 + dev: true + + /acorn/8.8.0: + resolution: {integrity: sha512-QOxyigPVrpZ2GXT+PFyZTl6TtOFc5egxHIP9IlQ+RbupQuX4RkT/Bee4/kQuC02Xkzg84JcT7oLYtDIQxp+v7w==} + engines: {node: '>=0.4.0'} + hasBin: true + dev: true + + /add-stream/1.0.0: + resolution: {integrity: sha512-qQLMr+8o0WC4FZGQTcJiKBVC59JylcPSrTtk6usvmIDFUOCKegapy1VHQwRbFMOFyb/inzUVqHs+eMYKDM1YeQ==} + dev: true + + /agent-base/6.0.2: + resolution: {integrity: sha512-RZNwNclF7+MS/8bDg70amg32dyeZGZxiDuQmZxKLAlQjr3jGyLx+4Kkk58UO7D2QdgFIQCovuSuZESne6RG6XQ==} + engines: {node: '>= 6.0.0'} + dependencies: + debug: 4.3.4 + transitivePeerDependencies: + - supports-color + dev: true + + /agentkeepalive/4.2.1: + resolution: {integrity: sha512-Zn4cw2NEqd+9fiSVWMscnjyQ1a8Yfoc5oBajLeo5w+YBHgDUcEBY2hS4YpTz6iN5f/2zQiktcuM6tS8x1p9dpA==} + engines: {node: '>= 8.0.0'} + dependencies: + debug: 4.3.4 + depd: 1.1.2 + humanize-ms: 1.2.1 + transitivePeerDependencies: + - supports-color + dev: true + + /aggregate-error/3.1.0: + resolution: {integrity: sha512-4I7Td01quW/RpocfNayFdFVk1qSuoh0E7JrbRJ16nH01HhKFQ88INq9Sd+nd72zqRySlr9BmDA8xlEJ6vJMrYA==} + engines: {node: '>=8'} + dependencies: + clean-stack: 2.2.0 + indent-string: 4.0.0 + dev: true + + /ajv/6.12.6: + resolution: {integrity: sha512-j3fVLgvTo527anyYyJOGTYJbG+vnnQYvE0m5mmkc1TK+nxAppkCLMIL0aZ4dblVCNoGShhm+kzE4ZUykBoMg4g==} + dependencies: + fast-deep-equal: 3.1.3 + fast-json-stable-stringify: 2.1.0 + json-schema-traverse: 0.4.1 + uri-js: 4.4.1 + dev: true + + /ansi-align/3.0.1: + resolution: {integrity: sha512-IOfwwBF5iczOjp/WeY4YxyjqAFMQoZufdQWDd19SEExbVLNXqvpzSJ/M7Za4/sCPmQ0+GRquoA7bGcINcxew6w==} + dependencies: + string-width: 4.2.3 + dev: true + + /ansi-escapes/4.3.2: + resolution: {integrity: sha512-gKXj5ALrKWQLsYG9jlTRmR/xKluxHV+Z9QEwNIgCfM1/uwPMCuzVVnh5mwTd+OuBZcwSIMbqssNWRm1lE51QaQ==} + engines: {node: '>=8'} + dependencies: + type-fest: 0.21.3 + dev: true + + /ansi-regex/2.1.1: + resolution: {integrity: sha512-TIGnTpdo+E3+pCyAluZvtED5p5wCqLdezCyhPZzKPcxvFplEt4i+W7OONCKgeZFT3+y5NZZfOOS/Bdcanm1MYA==} + engines: {node: '>=0.10.0'} + dev: true + + /ansi-regex/5.0.1: + resolution: {integrity: sha512-quJQXlTSUGL2LH9SUXo8VwsY4soanhgo6LNSm84E1LBcE8s3O0wpdiRzyR9z/ZZJMlMWv37qOOb9pdJlMUEKFQ==} + engines: {node: '>=8'} + dev: true + + /ansi-styles/3.2.1: + resolution: {integrity: sha512-VT0ZI6kZRdTh8YyJw3SMbYm/u+NqfsAxEpWO0Pf9sq8/e94WxxOpPKx9FR1FlyCtOVDNOQ+8ntlqFxiRc+r5qA==} + engines: {node: '>=4'} + dependencies: + color-convert: 1.9.3 + dev: true + + /ansi-styles/4.3.0: + resolution: {integrity: sha512-zbB9rCJAT1rbjiVDb2hqKFHNYLxgtk8NURxZ3IZwD3F6NtxbXZQCnnSi1Lkx+IDohdPlFp222wVALIheZJQSEg==} + engines: {node: '>=8'} + dependencies: + color-convert: 2.0.1 + dev: true + + /append-transform/2.0.0: + resolution: {integrity: sha512-7yeyCEurROLQJFv5Xj4lEGTy0borxepjFv1g22oAdqFu//SrAlDl1O1Nxx15SH1RoliUml6p8dwJW9jvZughhg==} + engines: {node: '>=8'} + dependencies: + default-require-extensions: 3.0.1 + dev: true + + /aproba/1.2.0: + resolution: {integrity: sha512-Y9J6ZjXtoYh8RnXVCMOU/ttDmk1aBjunq9vO0ta5x85WDQiQfUF9sIPBITdbiiIVcBo03Hi3jMxigBtsddlXRw==} + dev: true + + /aproba/2.0.0: + resolution: {integrity: sha512-lYe4Gx7QT+MKGbDsA+Z+he/Wtef0BiwDOlK/XkBrdfsh9J/jPPXbX0tE9x9cl27Tmu5gg3QUbUrQYa/y+KOHPQ==} + dev: true + + /archy/1.0.0: + resolution: {integrity: sha512-Xg+9RwCg/0p32teKdGMPTPnVXKD0w3DfHnFTficozsAgsvq2XenPJq/MYpzzQ/v8zrOyJn6Ds39VA4JIDwFfqw==} + dev: true + + /are-we-there-yet/1.1.7: + resolution: {integrity: sha512-nxwy40TuMiUGqMyRHgCSWZ9FM4VAoRP4xUYSTv5ImRog+h9yISPbVH7H8fASCIzYn9wlEv4zvFL7uKDMCFQm3g==} + dependencies: + delegates: 1.0.0 + readable-stream: 2.3.7 + dev: true + + /are-we-there-yet/3.0.1: + resolution: {integrity: sha512-QZW4EDmGwlYur0Yyf/b2uGucHQMa8aFUP7eu9ddR73vvhFyt4V0Vl3QHPcTNJ8l6qYOBdxgXdnBXQrHilfRQBg==} + engines: {node: ^12.13.0 || ^14.15.0 || >=16.0.0} + dependencies: + delegates: 1.0.0 + readable-stream: 3.6.0 + dev: true + + /argparse/1.0.10: + resolution: {integrity: sha512-o5Roy6tNG4SL/FOkCAN6RzjiakZS25RLYFrcMttJqbdd8BWrnA+fGz57iN5Pb06pvBGvl5gQ0B48dJlslXvoTg==} + dependencies: + sprintf-js: 1.0.3 + dev: true + + /argparse/2.0.1: + resolution: {integrity: sha512-8+9WqebbFzpX9OR+Wa6O29asIogeRMzcGtAINdpMHHyAg10f05aSFVBbcEqGf/PXw1EjAZ+q2/bEBg3DvurK3Q==} + dev: true + + /array-differ/3.0.0: + resolution: {integrity: sha512-THtfYS6KtME/yIAhKjZ2ul7XI96lQGHRputJQHO80LAWQnuGP4iCIN8vdMRboGbIEYBwU33q8Tch1os2+X0kMg==} + engines: {node: '>=8'} + dev: true + + /array-ify/1.0.0: + resolution: {integrity: sha512-c5AMf34bKdvPhQ7tBGhqkgKNUzMr4WUs+WDtC2ZUGOUncbxKMTvqxYctiseW3+L4bA8ec+GcZ6/A/FW4m8ukng==} + dev: true + + /array-includes/3.1.5: + resolution: {integrity: sha512-iSDYZMMyTPkiFasVqfuAQnWAYcvO/SeBSCGKePoEthjp4LEMTe4uLc7b025o4jAZpHhihh8xPo99TNWUWWkGDQ==} + engines: {node: '>= 0.4'} + 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 + dev: true + + /array-union/2.1.0: + resolution: {integrity: sha512-HGyxoOTYUyCM6stUe6EJgnd4EoewAI7zMdfqO+kGjnlZmBDz/cR5pf8r/cR4Wq60sL/p0IkcjUEEPwS3GFrIyw==} + engines: {node: '>=8'} + dev: true + + /array.prototype.flat/1.3.0: + resolution: {integrity: sha512-12IUEkHsAhA4DY5s0FPgNXIdc8VRSqD9Zp78a5au9abH/SOBrsp082JOWFNTjkMozh8mqcdiKuaLGhPeYztxSw==} + engines: {node: '>= 0.4'} + dependencies: + call-bind: 1.0.2 + define-properties: 1.1.4 + es-abstract: 1.20.4 + es-shim-unscopables: 1.0.0 + dev: true + + /array.prototype.reduce/1.0.4: + resolution: {integrity: sha512-WnM+AjG/DvLRLo4DDl+r+SvCzYtD2Jd9oeBYMcEaI7t3fFrHY9M53/wdLcTvmZNQ70IU6Htj0emFkZ5TS+lrdw==} + engines: {node: '>= 0.4'} + dependencies: + call-bind: 1.0.2 + define-properties: 1.1.4 + es-abstract: 1.20.4 + es-array-method-boxes-properly: 1.0.0 + is-string: 1.0.7 + dev: true + + /arrify/1.0.1: + resolution: {integrity: sha512-3CYzex9M9FGQjCGMGyi6/31c8GJbgb0qGyrx5HWxPd0aCwh4cB2YjMb2Xf9UuoogrMrlO9cTqnB5rI5GHZTcUA==} + engines: {node: '>=0.10.0'} + dev: true + + /arrify/2.0.1: + resolution: {integrity: sha512-3duEwti880xqi4eAMN8AyR4a0ByT90zoYdLlevfrvU43vb0YZwZVfxOgxWrLXXXpyugL0hNZc9G6BiB5B3nUug==} + engines: {node: '>=8'} + dev: true + + /asap/2.0.6: + resolution: {integrity: sha512-BSHWgDSAiKs50o2Re8ppvp3seVHXSRM44cdSsT9FfNEUUZLOGWVCsiWaRPWM1Znn+mqZ1OfVZ3z3DWEzSp7hRA==} + dev: true + + /asn1/0.2.6: + resolution: {integrity: sha512-ix/FxPn0MDjeyJ7i/yoHGFt/EX6LyNbxSEhPPXODPL+KB0VPk86UYfL0lMdy+KCnv+fmvIzySwaK5COwqVbWTQ==} + dependencies: + safer-buffer: 2.1.2 + dev: true + + /assert-plus/1.0.0: + resolution: {integrity: sha512-NfJ4UzBCcQGLDlQq7nHxH+tv3kyZ0hHQqF5BO6J7tNJeP5do1llPr8dZ8zHonfhAu0PHAdMkSo+8o0wxg9lZWw==} + engines: {node: '>=0.8'} + dev: true + + /asynckit/0.4.0: + resolution: {integrity: sha512-Oei9OH4tRh0YqU3GxhX79dM/mwVgvbZJaSNaRk+bshkj0S5cfHcgYakreBjrHwatXKbz+IoIdYLxrKim2MjW0Q==} + dev: true + + /at-least-node/1.0.0: + resolution: {integrity: sha512-+q/t7Ekv1EDY2l6Gda6LLiX14rU9TV20Wa3ofeQmwPFZbOMo9DXrLbOjFaaclkXKWidIaopwAObQDqwWtGUjqg==} + engines: {node: '>= 4.0.0'} + dev: true + + /aws-sign2/0.7.0: + resolution: {integrity: sha512-08kcGqnYf/YmjoRhfxyu+CLxBjUtHLXLXX/vUfx9l2LYzG3c1m61nrpyFUZI6zeS+Li/wWMMidD9KgrqtGq3mA==} + dev: true + + /aws4/1.11.0: + resolution: {integrity: sha512-xh1Rl34h6Fi1DC2WWKfxUTVqRsNnr6LsKz2+hfwDxQJWmrx8+c7ylaqBMcHfl1U1r2dsifOvKX3LQuLNZ+XSvA==} + dev: true + + /balanced-match/1.0.2: + resolution: {integrity: sha512-3oSeUO0TMV67hN1AmbXsK4yaqU7tjiHlbxRDZOpH0KW9+CeX4bRAaX0Anxt0tx2MrpRpWwQaPwIlISEJhYU5Pw==} + dev: true + + /bcrypt-pbkdf/1.0.2: + resolution: {integrity: sha512-qeFIXtP4MSoi6NLqO12WfqARWWuCKi2Rn/9hJLEmtB5yTNr9DqFWkJRCf2qShWzPeAMRnOgCrq0sg/KLv5ES9w==} + dependencies: + tweetnacl: 0.14.5 + dev: true + + /before-after-hook/2.2.3: + resolution: {integrity: sha512-NzUnlZexiaH/46WDhANlyR2bXRopNg4F/zuSA3OpZnllCUgRaOF2znDioDWrmbNVsuZk6l9pMquQB38cfBZwkQ==} + dev: true + + /boxen/5.1.2: + resolution: {integrity: sha512-9gYgQKXx+1nP8mP7CzFyaUARhg7D3n1dF/FnErWmu9l6JvGpNUN278h0aSb+QjoiKSWG+iZ3uHrcqk0qrY9RQQ==} + engines: {node: '>=10'} + dependencies: + ansi-align: 3.0.1 + camelcase: 6.3.0 + chalk: 4.1.2 + cli-boxes: 2.2.1 + string-width: 4.2.3 + type-fest: 0.20.2 + widest-line: 3.1.0 + wrap-ansi: 7.0.0 + dev: true + + /brace-expansion/1.1.11: + resolution: {integrity: sha512-iCuPHDFgrHX7H2vEI/5xpz07zSHB00TpugqhmYtVmMO6518mCuRMoOYFldEBl0g187ufozdaHgWKcYFb61qGiA==} + dependencies: + balanced-match: 1.0.2 + concat-map: 0.0.1 + dev: true + + /brace-expansion/2.0.1: + resolution: {integrity: sha512-XnAIvQ8eM+kC6aULx6wuQiwVsnzsi9d3WxzV3FpWTGA19F621kwdbsAcFKXgKUHZWsy+mY6iL1sHTxWEFCytDA==} + dependencies: + balanced-match: 1.0.2 + dev: true + + /braces/3.0.2: + resolution: {integrity: sha512-b8um+L1RzM3WDSzvhm6gIz1yfTbBt6YTlcEKAvsmqCZZFw46z626lVj9j1yEPW33H5H+lBQpZMP1k8l+78Ha0A==} + engines: {node: '>=8'} + dependencies: + fill-range: 7.0.1 + dev: true + + /browserslist/4.21.4: + resolution: {integrity: sha512-CBHJJdDmgjl3daYjN5Cp5kbTf1mUhZoS+beLklHIvkOWscs83YAhLlF3Wsh/lciQYAcbBJgTOD44VtG31ZM4Hw==} + engines: {node: ^6 || ^7 || ^8 || ^9 || ^10 || ^11 || ^12 || >=13.7} + hasBin: true + dependencies: + caniuse-lite: 1.0.30001419 + electron-to-chromium: 1.4.283 + node-releases: 2.0.6 + update-browserslist-db: 1.0.10_browserslist@4.21.4 + dev: true + + /buffer-from/1.1.2: + resolution: {integrity: sha512-E+XQCRwSbaaiChtv6k6Dwgc+bx+Bs6vuKJHHl5kox/BaKbhiXzqQOwK4cO22yElGp2OCmjwVhT3HmxgyPGnJfQ==} + dev: true + + /builtins/1.0.3: + resolution: {integrity: sha512-uYBjakWipfaO/bXI7E8rq6kpwHRZK5cNYrUv2OzZSI/FvmdMyXJ2tG9dKcjEC5YHmHpUAwsargWIZNWdxb/bnQ==} + dev: true + + /builtins/5.0.1: + resolution: {integrity: sha512-qwVpFEHNfhYJIzNRBvd2C1kyo6jz3ZSMPyyuR47OPdiKWlbYnZNyDWuyR175qDnAJLiCo5fBBqPb3RiXgWlkOQ==} + dependencies: + semver: 7.3.8 + dev: true + + /byline/5.0.0: + resolution: {integrity: sha512-s6webAy+R4SR8XVuJWt2V2rGvhnrhxN+9S15GNuTK3wKPOXFF6RNc+8ug2XhH+2s4f+uudG4kUVYmYOQWL2g0Q==} + engines: {node: '>=0.10.0'} + dev: true + + /byte-size/7.0.1: + resolution: {integrity: sha512-crQdqyCwhokxwV1UyDzLZanhkugAgft7vt0qbbdt60C6Zf3CAiGmtUCylbtYwrU6loOUw3euGrNtW1J651ot1A==} + engines: {node: '>=10'} + dev: true + + /cacache/15.3.0: + resolution: {integrity: sha512-VVdYzXEn+cnbXpFgWs5hTT7OScegHVmLhJIR8Ufqk3iFD6A6j5iSX1KuBTfNEv4tdJWE2PzA6IVFtcLC7fN9wQ==} + engines: {node: '>= 10'} + dependencies: + '@npmcli/fs': 1.1.1 + '@npmcli/move-file': 1.1.2 + chownr: 2.0.0 + fs-minipass: 2.1.0 + glob: 7.2.3 + infer-owner: 1.0.4 + lru-cache: 6.0.0 + minipass: 3.3.4 + minipass-collect: 1.0.2 + minipass-flush: 1.0.5 + minipass-pipeline: 1.2.4 + mkdirp: 1.0.4 + p-map: 4.0.0 + promise-inflight: 1.0.1 + rimraf: 3.0.2 + ssri: 8.0.1 + tar: 6.1.11 + unique-filename: 1.1.1 + transitivePeerDependencies: + - bluebird + dev: true + + /cacache/16.1.3: + resolution: {integrity: sha512-/+Emcj9DAXxX4cwlLmRI9c166RuL3w30zp4R7Joiv2cQTtTtA+jeuCAjH3ZlGnYS3tKENSrKhAzVVP9GVyzeYQ==} + engines: {node: ^12.13.0 || ^14.15.0 || >=16.0.0} + dependencies: + '@npmcli/fs': 2.1.2 + '@npmcli/move-file': 2.0.1 + chownr: 2.0.0 + fs-minipass: 2.1.0 + glob: 8.0.3 + infer-owner: 1.0.4 + lru-cache: 7.14.0 + minipass: 3.3.4 + minipass-collect: 1.0.2 + minipass-flush: 1.0.5 + minipass-pipeline: 1.2.4 + mkdirp: 1.0.4 + p-map: 4.0.0 + promise-inflight: 1.0.1 + rimraf: 3.0.2 + ssri: 9.0.1 + tar: 6.1.11 + unique-filename: 2.0.1 + transitivePeerDependencies: + - bluebird + dev: true + + /cacheable-request/6.1.0: + resolution: {integrity: sha512-Oj3cAGPCqOZX7Rz64Uny2GYAZNliQSqfbePrgAQ1wKAihYmCUnraBtJtKcGR4xz7wF+LoJC+ssFZvv5BgF9Igg==} + engines: {node: '>=8'} + dependencies: + clone-response: 1.0.3 + get-stream: 5.2.0 + http-cache-semantics: 4.1.0 + keyv: 3.1.0 + lowercase-keys: 2.0.0 + normalize-url: 4.5.1 + responselike: 1.0.2 + dev: true + + /caching-transform/4.0.0: + resolution: {integrity: sha512-kpqOvwXnjjN44D89K5ccQC+RUrsy7jB/XLlRrx0D7/2HNcTPqzsb6XgYoErwko6QsV184CA2YgS1fxDiiDZMWA==} + engines: {node: '>=8'} + dependencies: + hasha: 5.2.2 + make-dir: 3.1.0 + package-hash: 4.0.0 + write-file-atomic: 3.0.3 + dev: true + + /call-bind/1.0.2: + resolution: {integrity: sha512-7O+FbCihrB5WGbFYesctwmTKae6rOiIzmz1icreWJ+0aA7LJfuqhEso2T9ncpcFtzMQtzXf2QGGueWJGTYsqrA==} + dependencies: + function-bind: 1.1.1 + get-intrinsic: 1.1.3 + dev: true + + /callsites/3.1.0: + resolution: {integrity: sha512-P8BjAsXvZS+VIDUI11hHCQEv74YT67YUi5JJFNWIqL235sBmjX4+qx9Muvls5ivyNENctx46xQLQ3aTuE7ssaQ==} + engines: {node: '>=6'} + dev: true + + /camelcase-keys/6.2.2: + resolution: {integrity: sha512-YrwaA0vEKazPBkn0ipTiMpSajYDSe+KjQfrjhcBMxJt/znbvlHd8Pw/Vamaz5EB4Wfhs3SUR3Z9mwRu/P3s3Yg==} + engines: {node: '>=8'} + dependencies: + camelcase: 5.3.1 + map-obj: 4.3.0 + quick-lru: 4.0.1 + dev: true + + /camelcase/5.3.1: + resolution: {integrity: sha512-L28STB170nwWS63UjtlEOE3dldQApaJXZkOI1uMFfzf3rRuPegHaHesyee+YxQ+W6SvRDQV6UrdOdRiR153wJg==} + engines: {node: '>=6'} + dev: true + + /camelcase/6.3.0: + resolution: {integrity: sha512-Gmy6FhYlCY7uOElZUSbxo2UCDH8owEk996gkbrpsgGtrJLM3J7jGxl9Ic7Qwwj4ivOE5AWZWRMecDdF7hqGjFA==} + engines: {node: '>=10'} + dev: true + + /caniuse-lite/1.0.30001419: + resolution: {integrity: sha512-aFO1r+g6R7TW+PNQxKzjITwLOyDhVRLjW0LcwS/HCZGUUKTGNp9+IwLC4xyDSZBygVL/mxaFR3HIV6wEKQuSzw==} + dev: true + + /caseless/0.12.0: + resolution: {integrity: sha512-4tYFyifaFfGacoiObjJegolkwSU4xQNGbVgUiNYVUxbQ2x2lUsFvY4hVgVzGiIe6WLOPqycWXA40l+PWsxthUw==} + dev: true + + /chalk/2.4.2: + resolution: {integrity: sha512-Mti+f9lpJNcwF4tWV8/OrTTtF1gZi+f8FqlyAdouralcFWFQWF2+NgCHShjkCb+IFBLq9buZwE1xckQU4peSuQ==} + engines: {node: '>=4'} + dependencies: + ansi-styles: 3.2.1 + escape-string-regexp: 1.0.5 + supports-color: 5.5.0 + dev: true + + /chalk/4.1.2: + resolution: {integrity: sha512-oKnbhFyRIXpUuez8iBMmyEa4nbj4IOQyuhc/wy9kY7/WVPcwIO9VA668Pu8RkO7+0G76SLROeyw9CpQ061i4mA==} + engines: {node: '>=10'} + dependencies: + ansi-styles: 4.3.0 + supports-color: 7.2.0 + dev: true + + /chardet/0.7.0: + resolution: {integrity: sha512-mT8iDcrh03qDGRRmoA2hmBJnxpllMR+0/0qlzjqZES6NdiWDcZkCNAk4rPFZ9Q85r27unkiNNg8ZOiwZXBHwcA==} + dev: true + + /chownr/1.1.4: + resolution: {integrity: sha512-jJ0bqzaylmJtVnNgzTeSOs8DPavpbYgEr/b0YL8/2GO3xJEhInFmhKMUnEJQjZumK7KXGFhUy89PrsJWlakBVg==} + dev: true + + /chownr/2.0.0: + resolution: {integrity: sha512-bIomtDF5KGpdogkLd9VspvFzk9KfpyyGlS8YFVZl7TGPBHL5snIOnxeshwVgPteQ9b4Eydl+pVbIyE1DcvCWgQ==} + engines: {node: '>=10'} + dev: true + + /ci-info/2.0.0: + resolution: {integrity: sha512-5tK7EtrZ0N+OLFMthtqOj4fI2Jeb88C4CAZPu25LDVUgXJ0A3Js4PMGqrn0JU1W0Mh1/Z8wZzYPxqUrXeBboCQ==} + dev: true + + /cint/8.2.1: + resolution: {integrity: sha512-gyWqJHXgDFPNx7PEyFJotutav+al92TTC3dWlMFyTETlOyKBQMZb7Cetqmj3GlrnSILHwSJRwf4mIGzc7C5lXw==} + dev: true + + /clean-stack/2.2.0: + resolution: {integrity: sha512-4diC9HaTE+KRAMWhDhrGOECgWZxoevMc5TlkObMqNSsVU62PYzXZ/SMTjzyGAFF1YusgxGcSWTEXBhp0CPwQ1A==} + engines: {node: '>=6'} + dev: true + + /cli-boxes/2.2.1: + resolution: {integrity: sha512-y4coMcylgSCdVinjiDBuR8PCC2bLjyGTwEmPb9NHR/QaNU6EUOXcTY/s6VjGMD6ENSEaeQYHCY0GNGS5jfMwPw==} + engines: {node: '>=6'} + dev: true + + /cli-cursor/3.1.0: + resolution: {integrity: sha512-I/zHAwsKf9FqGoXM4WWRACob9+SNukZTd94DWF57E4toouRulbCxcUh6RKUEOQlYTHJnzkPMySvPNaaSLNfLZw==} + engines: {node: '>=8'} + dependencies: + restore-cursor: 3.1.0 + dev: true + + /cli-table/0.3.11: + resolution: {integrity: sha512-IqLQi4lO0nIB4tcdTpN4LCB9FI3uqrJZK7RC515EnhZ6qBaglkIgICb1wjeAqpdoOabm1+SuQtkXIPdYC93jhQ==} + engines: {node: '>= 0.2.0'} + dependencies: + colors: 1.0.3 + dev: true + + /cli-width/3.0.0: + resolution: {integrity: sha512-FxqpkPPwu1HjuN93Omfm4h8uIanXofW0RxVEW3k5RKx+mJJYSthzNhp32Kzxxy3YAEZ/Dc/EWN1vZRY0+kOhbw==} + engines: {node: '>= 10'} + dev: true + + /cliui/6.0.0: + resolution: {integrity: sha512-t6wbgtoCXvAzst7QgXxJYqPt0usEfbgQdftEPbLL/cvv6HPE5VgvqCuAIDR0NgU52ds6rFwqrgakNLrHEjCbrQ==} + dependencies: + string-width: 4.2.3 + strip-ansi: 6.0.1 + wrap-ansi: 6.2.0 + dev: true + + /cliui/7.0.4: + resolution: {integrity: sha512-OcRE68cOsVMXp1Yvonl/fzkQOyjLSu/8bhPDfQt0e0/Eb283TKP20Fs2MqoPsr9SwA595rRCA+QMzYc9nBP+JQ==} + dependencies: + string-width: 4.2.3 + strip-ansi: 6.0.1 + wrap-ansi: 7.0.0 + dev: true + + /clone-deep/4.0.1: + resolution: {integrity: sha512-neHB9xuzh/wk0dIHweyAXv2aPGZIVk3pLMe+/RNzINf17fe0OG96QroktYAUm7SM1PBnzTabaLboqqxDyMU+SQ==} + engines: {node: '>=6'} + dependencies: + is-plain-object: 2.0.4 + kind-of: 6.0.3 + shallow-clone: 3.0.1 + dev: true + + /clone-response/1.0.3: + resolution: {integrity: sha512-ROoL94jJH2dUVML2Y/5PEDNaSHgeOdSDicUyS7izcF63G6sTc/FTjLub4b8Il9S8S0beOfYt0TaA5qvFK+w0wA==} + dependencies: + mimic-response: 1.0.1 + dev: true + + /clone/1.0.4: + resolution: {integrity: sha512-JQHZ2QMW6l3aH/j6xCqQThY/9OH4D/9ls34cgkUBiEeocRTU04tHfKPBsUK1PqZCUQM7GiA0IIXJSuXHI64Kbg==} + engines: {node: '>=0.8'} + dev: true + + /cmd-shim/4.1.0: + resolution: {integrity: sha512-lb9L7EM4I/ZRVuljLPEtUJOP+xiQVknZ4ZMpMgEp4JzNldPb27HU03hi6K1/6CoIuit/Zm/LQXySErFeXxDprw==} + engines: {node: '>=10'} + dependencies: + mkdirp-infer-owner: 2.0.0 + dev: true + + /code-point-at/1.1.0: + resolution: {integrity: sha512-RpAVKQA5T63xEj6/giIbUEtZwJ4UFIc3ZtvEkiaUERylqe8xb5IvqcgOurZLahv93CLKfxcw5YI+DZcUBRyLXA==} + engines: {node: '>=0.10.0'} + dev: true + + /color-convert/1.9.3: + resolution: {integrity: sha512-QfAUtd+vFdAtFQcC8CCyYt1fYWxSqAiK2cSD6zDB8N3cpsEBAvRxp9zOGg6G/SHHJYAT88/az/IuDGALsNVbGg==} + dependencies: + color-name: 1.1.3 + dev: true + + /color-convert/2.0.1: + resolution: {integrity: sha512-RRECPsj7iu/xb5oKYcsFHSppFNnsj/52OVTRKb4zP5onXwVF3zVmmToNcOfGC+CRDpfK/U584fMg38ZHCaElKQ==} + engines: {node: '>=7.0.0'} + dependencies: + color-name: 1.1.4 + dev: true + + /color-name/1.1.3: + resolution: {integrity: sha512-72fSenhMw2HZMTVHeCA9KCmpEIbzWiQsjN+BHcBbS9vr1mtt+vJjPdksIBNUmKAW8TFUDPJK5SUU3QhE9NEXDw==} + dev: true + + /color-name/1.1.4: + resolution: {integrity: sha512-dOy+3AuW3a2wNbZHIuMZpTcgjGuLU/uBL/ubcZF9OXbDo8ff4O8yVp5Bf0efS8uEoYo5q4Fx7dY9OgQGXgAsQA==} + dev: true + + /color-support/1.1.3: + resolution: {integrity: sha512-qiBjkpbMLO/HL68y+lh4q0/O1MZFj2RX6X/KmMa3+gJD3z+WwI1ZzDHysvqHGS3mP6mznPckpXmw1nI9cJjyRg==} + hasBin: true + dev: true + + /colors/1.0.3: + resolution: {integrity: sha512-pFGrxThWcWQ2MsAz6RtgeWe4NK2kUE1WfsrvvlctdII745EW9I0yflqhe7++M5LEc7bV2c/9/5zc8sFcpL0Drw==} + engines: {node: '>=0.1.90'} + dev: true + + /columnify/1.6.0: + resolution: {integrity: sha512-lomjuFZKfM6MSAnV9aCZC9sc0qGbmZdfygNv+nCpqVkSKdCxCklLtd16O0EILGkImHw9ZpHkAnHaB+8Zxq5W6Q==} + engines: {node: '>=8.0.0'} + dependencies: + strip-ansi: 6.0.1 + wcwidth: 1.0.1 + dev: true + + /combined-stream/1.0.8: + resolution: {integrity: sha512-FQN4MRfuJeHf7cBbBMJFXhKSDq+2kAArBlmRBvcvFE5BB1HZKXtSFASDhdlz9zOYwxh8lDdnvmMOe/+5cdoEdg==} + engines: {node: '>= 0.8'} + dependencies: + delayed-stream: 1.0.0 + dev: true + + /commander/9.4.1: + resolution: {integrity: sha512-5EEkTNyHNGFPD2H+c/dXXfQZYa/scCKasxWcXJaWnNJ99pnQN9Vnmqow+p+PlFPE63Q6mThaZws1T+HxfpgtPw==} + engines: {node: ^12.20.0 || >=14} + dev: true + + /commondir/1.0.1: + resolution: {integrity: sha512-W9pAhw0ja1Edb5GVdIF1mjZw/ASI0AlShXM83UUGe2DVr5TdAPEA1OA8m/g8zWp9x6On7gqufY+FatDbC3MDQg==} + dev: true + + /compare-func/2.0.0: + resolution: {integrity: sha512-zHig5N+tPWARooBnb0Zx1MFcdfpyJrfTJ3Y5L+IFvUm8rM74hHz66z0gw0x4tijh5CorKkKUCnW82R2vmpeCRA==} + dependencies: + array-ify: 1.0.0 + dot-prop: 5.3.0 + dev: true + + /concat-map/0.0.1: + resolution: {integrity: sha512-/Srv4dswyQNBfohGpz9o6Yb3Gz3SrUDqBH5rTuhGR7ahtlbYKnVxw2bCFMRljaA7EXHaXZ8wsHdodFvbkhKmqg==} + dev: true + + /concat-stream/2.0.0: + resolution: {integrity: sha512-MWufYdFw53ccGjCA+Ol7XJYpAlW6/prSMzuPOTRnJGcGzuhLn4Scrz7qf6o8bROZ514ltazcIFJZevcfbo0x7A==} + engines: {'0': node >= 6.0} + dependencies: + buffer-from: 1.1.2 + inherits: 2.0.4 + readable-stream: 3.6.0 + typedarray: 0.0.6 + dev: true + + /config-chain/1.1.13: + resolution: {integrity: sha512-qj+f8APARXHrM0hraqXYb2/bOVSV4PvJQlNZ/DVj0QrmNM2q2euizkeuVckQ57J+W0mRH6Hvi+k50M4Jul2VRQ==} + dependencies: + ini: 1.3.8 + proto-list: 1.2.4 + dev: true + + /configstore/5.0.1: + resolution: {integrity: sha512-aMKprgk5YhBNyH25hj8wGt2+D52Sw1DRRIzqBwLp2Ya9mFmY8KPvvtvmna8SxVR9JMZ4kzMD68N22vlaRpkeFA==} + engines: {node: '>=8'} + dependencies: + dot-prop: 5.3.0 + graceful-fs: 4.2.10 + make-dir: 3.1.0 + unique-string: 2.0.0 + write-file-atomic: 3.0.3 + xdg-basedir: 4.0.0 + dev: true + + /console-control-strings/1.1.0: + resolution: {integrity: sha512-ty/fTekppD2fIwRvnZAVdeOiGd1c7YXEixbgJTNzqcxJWKQnjJ/V1bNEEE6hygpM3WjwHFUVK6HTjWSzV4a8sQ==} + dev: true + + /conventional-changelog-angular/5.0.13: + resolution: {integrity: sha512-i/gipMxs7s8L/QeuavPF2hLnJgH6pEZAttySB6aiQLWcX3puWDL3ACVmvBhJGxnAy52Qc15ua26BufY6KpmrVA==} + engines: {node: '>=10'} + dependencies: + compare-func: 2.0.0 + q: 1.5.1 + dev: true + + /conventional-changelog-core/4.2.4: + resolution: {integrity: sha512-gDVS+zVJHE2v4SLc6B0sLsPiloR0ygU7HaDW14aNJE1v4SlqJPILPl/aJC7YdtRE4CybBf8gDwObBvKha8Xlyg==} + engines: {node: '>=10'} + dependencies: + add-stream: 1.0.0 + conventional-changelog-writer: 5.0.1 + conventional-commits-parser: 3.2.4 + dateformat: 3.0.3 + get-pkg-repo: 4.2.1 + git-raw-commits: 2.0.11 + git-remote-origin-url: 2.0.0 + git-semver-tags: 4.1.1 + lodash: 4.17.21 + normalize-package-data: 3.0.3 + q: 1.5.1 + read-pkg: 3.0.0 + read-pkg-up: 3.0.0 + through2: 4.0.2 + dev: true + + /conventional-changelog-preset-loader/2.3.4: + resolution: {integrity: sha512-GEKRWkrSAZeTq5+YjUZOYxdHq+ci4dNwHvpaBC3+ENalzFWuCWa9EZXSuZBpkr72sMdKB+1fyDV4takK1Lf58g==} + engines: {node: '>=10'} + dev: true + + /conventional-changelog-writer/5.0.1: + resolution: {integrity: sha512-5WsuKUfxW7suLblAbFnxAcrvf6r+0b7GvNaWUwUIk0bXMnENP/PEieGKVUQrjPqwPT4o3EPAASBXiY6iHooLOQ==} + engines: {node: '>=10'} + hasBin: true + dependencies: + conventional-commits-filter: 2.0.7 + dateformat: 3.0.3 + handlebars: 4.7.7 + json-stringify-safe: 5.0.1 + lodash: 4.17.21 + meow: 8.1.2 + semver: 6.3.0 + split: 1.0.1 + through2: 4.0.2 + dev: true + + /conventional-commits-filter/2.0.7: + resolution: {integrity: sha512-ASS9SamOP4TbCClsRHxIHXRfcGCnIoQqkvAzCSbZzTFLfcTqJVugB0agRgsEELsqaeWgsXv513eS116wnlSSPA==} + engines: {node: '>=10'} + dependencies: + lodash.ismatch: 4.4.0 + modify-values: 1.0.1 + dev: true + + /conventional-commits-parser/3.2.4: + resolution: {integrity: sha512-nK7sAtfi+QXbxHCYfhpZsfRtaitZLIA6889kFIouLvz6repszQDgxBu7wf2WbU+Dco7sAnNCJYERCwt54WPC2Q==} + engines: {node: '>=10'} + hasBin: true + dependencies: + JSONStream: 1.3.5 + is-text-path: 1.0.1 + lodash: 4.17.21 + meow: 8.1.2 + split2: 3.2.2 + through2: 4.0.2 + dev: true + + /conventional-recommended-bump/6.1.0: + resolution: {integrity: sha512-uiApbSiNGM/kkdL9GTOLAqC4hbptObFo4wW2QRyHsKciGAfQuLU1ShZ1BIVI/+K2BE/W1AWYQMCXAsv4dyKPaw==} + engines: {node: '>=10'} + hasBin: true + dependencies: + concat-stream: 2.0.0 + conventional-changelog-preset-loader: 2.3.4 + conventional-commits-filter: 2.0.7 + conventional-commits-parser: 3.2.4 + git-raw-commits: 2.0.11 + git-semver-tags: 4.1.1 + meow: 8.1.2 + q: 1.5.1 + dev: true + + /convert-source-map/1.9.0: + resolution: {integrity: sha512-ASFBup0Mz1uyiIjANan1jzLQami9z1PoYSZCiiYW2FczPbenXc45FZdBZLzOT+r6+iciuEModtmCti+hjaAk0A==} + dev: true + + /core-util-is/1.0.2: + resolution: {integrity: sha512-3lqz5YjWTYnW6dlDa5TLaTCcShfar1e40rmcJVwCBJC6mWlFuj0eCHIElmG1g5kyuJ/GD+8Wn4FFCcz4gJPfaQ==} + dev: true + + /core-util-is/1.0.3: + resolution: {integrity: sha512-ZQBvi1DcpJ4GDqanjucZ2Hj3wEO5pZDS89BWbkcrvdxksJorwUDDZamX9ldFkp9aw2lmBDLgkObEA4DWNJ9FYQ==} + dev: true + + /cosmiconfig/7.0.1: + resolution: {integrity: sha512-a1YWNUV2HwGimB7dU2s1wUMurNKjpx60HxBB6xUM8Re+2s1g1IIfJvFR0/iCF+XHdE0GMTKTuLR32UQff4TEyQ==} + engines: {node: '>=10'} + dependencies: + '@types/parse-json': 4.0.0 + import-fresh: 3.3.0 + parse-json: 5.2.0 + path-type: 4.0.0 + yaml: 1.10.2 + dev: true + + /cross-spawn/7.0.3: + resolution: {integrity: sha512-iRDPJKUPVEND7dHPO8rkbOnPpyDygcDFtWjpeWNCgy8WP2rXcxXL8TskReQl6OrB2G7+UJrags1q15Fudc7G6w==} + engines: {node: '>= 8'} + dependencies: + path-key: 3.1.1 + shebang-command: 2.0.0 + which: 2.0.2 + dev: true + + /crypto-random-string/2.0.0: + resolution: {integrity: sha512-v1plID3y9r/lPhviJ1wrXpLeyUIGAZ2SHNYTEapm7/8A9nLPoyvVp3RK/EPFqn5kEznyWgYZNsRtYYIWbuG8KA==} + engines: {node: '>=8'} + dev: true + + /dargs/7.0.0: + resolution: {integrity: sha512-2iy1EkLdlBzQGvbweYRFxmFath8+K7+AKB0TlhHWkNuH+TmovaMH/Wp7V7R4u7f4SnX3OgLsU9t1NI9ioDnUpg==} + engines: {node: '>=8'} + dev: true + + /dashdash/1.14.1: + resolution: {integrity: sha512-jRFi8UDGo6j+odZiEpjazZaWqEal3w/basFjQHQEwVtZJGDpxbH1MeYluwCS8Xq5wmLJooDlMgvVarmWfGM44g==} + engines: {node: '>=0.10'} + dependencies: + assert-plus: 1.0.0 + dev: true + + /dateformat/3.0.3: + resolution: {integrity: sha512-jyCETtSl3VMZMWeRo7iY1FL19ges1t55hMo5yaam4Jrsm5EPL89UQkoQRyiI+Yf4k8r2ZpdngkV8hr1lIdjb3Q==} + dev: true + + /debug/2.6.9: + resolution: {integrity: sha512-bC7ElrdJaJnPbAP+1EotYvqZsb3ecl5wi6Bfi6BJTUcNowp6cvspg0jXznRTKDjm/E7AdgFBVeAPVMNcKGsHMA==} + peerDependencies: + supports-color: '*' + peerDependenciesMeta: + supports-color: + optional: true + dependencies: + ms: 2.0.0 + dev: true + + /debug/3.2.7: + resolution: {integrity: sha512-CFjzYYAi4ThfiQvizrFQevTTXHtnCqWfe7x1AhgEscTz6ZbLbfoLRLPugTQyBth6f8ZERVUSyWHFD/7Wu4t1XQ==} + peerDependencies: + supports-color: '*' + peerDependenciesMeta: + supports-color: + optional: true + dependencies: + ms: 2.1.3 + dev: true + + /debug/4.3.4: + resolution: {integrity: sha512-PRWFHuSU3eDtQJPvnNY7Jcket1j0t5OuOsFzPPzsekD52Zl8qUfFIPEiswXqIvHWGVHOgX+7G/vCNNhehwxfkQ==} + engines: {node: '>=6.0'} + peerDependencies: + supports-color: '*' + peerDependenciesMeta: + supports-color: + optional: true + dependencies: + ms: 2.1.2 + dev: true + + /debuglog/1.0.1: + resolution: {integrity: sha512-syBZ+rnAK3EgMsH2aYEOLUW7mZSY9Gb+0wUMCFsZvcmiz+HigA0LOcq/HoQqVuGG+EKykunc7QG2bzrponfaSw==} + dev: true + + /decamelize-keys/1.1.0: + resolution: {integrity: sha512-ocLWuYzRPoS9bfiSdDd3cxvrzovVMZnRDVEzAs+hWIVXGDbHxWMECij2OBuyB/An0FFW/nLuq6Kv1i/YC5Qfzg==} + engines: {node: '>=0.10.0'} + dependencies: + decamelize: 1.2.0 + map-obj: 1.0.1 + dev: true + + /decamelize/1.2.0: + resolution: {integrity: sha512-z2S+W9X73hAUUki+N+9Za2lBlun89zigOyGrsax+KUQ6wKW4ZoWpEYBkGhQjwAjjDCkWxhY0VKEhk8wzY7F5cA==} + engines: {node: '>=0.10.0'} + dev: true + + /decode-uri-component/0.2.0: + resolution: {integrity: sha512-hjf+xovcEn31w/EUYdTXQh/8smFL/dzYjohQGEIgjyNavaJfBY2p5F527Bo1VPATxv0VYTUC2bOcXvqFwk78Og==} + engines: {node: '>=0.10'} + dev: true + + /decompress-response/3.3.0: + resolution: {integrity: sha512-BzRPQuY1ip+qDonAOz42gRm/pg9F768C+npV/4JOsxRC2sq+Rlk+Q4ZCAsOhnIaMrgarILY+RMUIvMmmX1qAEA==} + engines: {node: '>=4'} + dependencies: + mimic-response: 1.0.1 + dev: true + + /dedent/0.7.0: + resolution: {integrity: sha512-Q6fKUPqnAHAyhiUgFU7BUzLiv0kd8saH9al7tnu5Q/okj6dnupxyTgFIBjVzJATdfIAm9NAsvXNzjaKa+bxVyA==} + dev: true + + /deep-extend/0.6.0: + resolution: {integrity: sha512-LOHxIOaPYdHlJRtCQfDIVZtfw/ufM8+rVj649RIHzcm/vGwQRXFt6OPqIFWsm2XEMrNIEtWR64sY1LEKD2vAOA==} + engines: {node: '>=4.0.0'} + dev: true + + /deep-is/0.1.4: + resolution: {integrity: sha512-oIPzksmTg4/MriiaYGO+okXDT7ztn/w3Eptv/+gSIdMdKsJo0u4CfYNFJPy+4SKMuCqGw2wxnA+URMg3t8a/bQ==} + dev: true + + /default-require-extensions/3.0.1: + resolution: {integrity: sha512-eXTJmRbm2TIt9MgWTsOH1wEuhew6XGZcMeGKCtLedIg/NCsg1iBePXkceTdK4Fii7pzmN9tGsZhKzZ4h7O/fxw==} + engines: {node: '>=8'} + dependencies: + strip-bom: 4.0.0 + dev: true + + /defaults/1.0.4: + resolution: {integrity: sha512-eFuaLoy/Rxalv2kr+lqMlUnrDWV+3j4pljOIJgLIhI058IQfWJ7vXhyEIHu+HtC738klGALYxOKDO0bQP3tg8A==} + dependencies: + clone: 1.0.4 + dev: true + + /defer-to-connect/1.1.3: + resolution: {integrity: sha512-0ISdNousHvZT2EiFlZeZAHBUvSxmKswVCEf8hW7KWgG4a8MVEu/3Vb6uWYozkjylyCxe0JBIiRB1jV45S70WVQ==} + dev: true + + /define-properties/1.1.4: + resolution: {integrity: sha512-uckOqKcfaVvtBdsVkdPv3XjveQJsNQqmhXgRi8uhvWWuPYZCNlzT8qAyblUgNoXdHdjMTzAqeGjAoli8f+bzPA==} + engines: {node: '>= 0.4'} + dependencies: + has-property-descriptors: 1.0.0 + object-keys: 1.1.1 + dev: true + + /delayed-stream/1.0.0: + resolution: {integrity: sha512-ZySD7Nf91aLB0RxL4KGrKHBXl7Eds1DAmEdcoVawXnLD7SDhpNgtuII2aAkg7a7QS41jxPSZ17p4VdGnMHk3MQ==} + engines: {node: '>=0.4.0'} + dev: true + + /delegates/1.0.0: + resolution: {integrity: sha512-bd2L678uiWATM6m5Z1VzNCErI3jiGzt6HGY8OVICs40JQq/HALfbyNJmp0UDakEY4pMMaN0Ly5om/B1VI/+xfQ==} + dev: true + + /depd/1.1.2: + resolution: {integrity: sha512-7emPTl6Dpo6JRXOXjLRxck+FlLRX5847cLKEn00PLAgc3g2hTZZgr+e4c2v6QpSmLeFP3n5yUo7ft6avBK/5jQ==} + engines: {node: '>= 0.6'} + dev: true + + /deprecation/2.3.1: + resolution: {integrity: sha512-xmHIy4F3scKVwMsQ4WnVaS8bHOx0DmVwRywosKhaILI0ywMDWPtBSku2HNxRvF7jtwDRsoEwYQSfbxj8b7RlJQ==} + dev: true + + /detect-indent/5.0.0: + resolution: {integrity: sha512-rlpvsxUtM0PQvy9iZe640/IWwWYyBsTApREbA1pHOpmOUIl9MkP/U4z7vTtg4Oaojvqhxt7sdufnT0EzGaR31g==} + engines: {node: '>=4'} + dev: true + + /detect-indent/6.1.0: + resolution: {integrity: sha512-reYkTUJAZb9gUuZ2RvVCNhVHdg62RHnJ7WJl8ftMi4diZ6NWlciOzQN88pUhSELEwflJht4oQDv0F0BMlwaYtA==} + engines: {node: '>=8'} + dev: true + + /dezalgo/1.0.4: + resolution: {integrity: sha512-rXSP0bf+5n0Qonsb+SVVfNfIsimO4HEtmnIpPHY8Q1UCzKlQrDMfdobr8nJOOsRgWCyMRqeSBQzmWUMq7zvVig==} + dependencies: + asap: 2.0.6 + wrappy: 1.0.2 + dev: true + + /dir-glob/3.0.1: + resolution: {integrity: sha512-WkrWp9GR4KXfKGYzOLmTuGVi1UWFfws377n9cc55/tb6DuqyF6pcQ5AbiHEshaDpY9v6oaSr2XCDidGmMwdzIA==} + engines: {node: '>=8'} + dependencies: + path-type: 4.0.0 + dev: true + + /doctrine/2.1.0: + resolution: {integrity: sha512-35mSku4ZXK0vfCuHEDAwt55dg2jNajHZ1odvF+8SSr82EsZY4QmXfuWso8oEd8zRhVObSN18aM0CjSdoBX7zIw==} + engines: {node: '>=0.10.0'} + dependencies: + esutils: 2.0.3 + dev: true + + /doctrine/3.0.0: + resolution: {integrity: sha512-yS+Q5i3hBf7GBkd4KG8a7eBNNWNGLTaEwwYWUijIYM7zrlYDM0BFXHjjPWlWZ1Rg7UaddZeIDmi9jF3HmqiQ2w==} + engines: {node: '>=6.0.0'} + dependencies: + esutils: 2.0.3 + dev: true + + /dot-prop/5.3.0: + resolution: {integrity: sha512-QM8q3zDe58hqUqjraQOmzZ1LIH9SWQJTlEKCH4kJ2oQvLZk7RbQXvtDM2XEq3fwkV9CCvvH4LA0AV+ogFsBM2Q==} + engines: {node: '>=8'} + dependencies: + is-obj: 2.0.0 + dev: true + + /dot-prop/6.0.1: + resolution: {integrity: sha512-tE7ztYzXHIeyvc7N+hR3oi7FIbf/NIjVP9hmAt3yMXzrQ072/fpjGLx2GxNxGxUl5V73MEqYzioOMoVhGMJ5cA==} + engines: {node: '>=10'} + dependencies: + is-obj: 2.0.0 + dev: true + + /duplexer/0.1.2: + resolution: {integrity: sha512-jtD6YG370ZCIi/9GTaJKQxWTZD045+4R4hTk/x1UyoqadyJ9x9CgSi1RlVDQF8U2sxLLSnFkCaMihqljHIWgMg==} + dev: true + + /duplexer3/0.1.5: + resolution: {integrity: sha512-1A8za6ws41LQgv9HrE/66jyC5yuSjQ3L/KOpFtoBilsAK2iA2wuS5rTt1OCzIvtS2V7nVmedsUU+DGRcjBmOYA==} + dev: true + + /ecc-jsbn/0.1.2: + resolution: {integrity: sha512-eh9O+hwRHNbG4BLTjEl3nw044CkGm5X6LoaCf7LPp7UU8Qrt47JYNi6nPX8xjW97TKGKm1ouctg0QSpZe9qrnw==} + dependencies: + jsbn: 0.1.1 + safer-buffer: 2.1.2 + dev: true + + /electron-to-chromium/1.4.283: + resolution: {integrity: sha512-g6RQ9zCOV+U5QVHW9OpFR7rdk/V7xfopNXnyAamdpFgCHgZ1sjI8VuR1+zG2YG/TZk+tQ8mpNkug4P8FU0fuOA==} + dev: true + + /emoji-regex/8.0.0: + resolution: {integrity: sha512-MSjYzcWNOA0ewAHpz0MxpYFvwg6yjy1NG3xteoqz644VCo/RPgnr1/GGt+ic3iJTzQ8Eu3TdM14SawnVUmGE6A==} + dev: true + + /encoding/0.1.13: + resolution: {integrity: sha512-ETBauow1T35Y/WZMkio9jiM0Z5xjHHmJ4XmjZOq1l/dXz3lr2sRn87nJy20RupqSh1F2m3HHPSp8ShIPQJrJ3A==} + requiresBuild: true + dependencies: + iconv-lite: 0.6.3 + dev: true + optional: true + + /end-of-stream/1.4.4: + resolution: {integrity: sha512-+uw1inIHVPQoaVuHzRyXd21icM+cnt4CzD5rW+NC1wjOUSTOs+Te7FOv7AhN7vS9x/oIyhLP5PR1H+phQAHu5Q==} + dependencies: + once: 1.4.0 + dev: true + + /env-paths/2.2.1: + resolution: {integrity: sha512-+h1lkLKhZMTYjog1VEpJNG7NZJWcuc2DDk/qsqSTRRCOXiLjeQ1d1/udrUGhqMxUgAlwKNZ0cf2uqan5GLuS2A==} + engines: {node: '>=6'} + dev: true + + /envinfo/7.8.1: + resolution: {integrity: sha512-/o+BXHmB7ocbHEAs6F2EnG0ogybVVUdkRunTT2glZU9XAaGmhqskrvKwqXuDfNjEO0LZKWdejEEpnq8aM0tOaw==} + engines: {node: '>=4'} + hasBin: true + dev: true + + /err-code/2.0.3: + resolution: {integrity: sha512-2bmlRpNKBxT/CRmPOlyISQpNj+qSeYvcym/uT0Jx2bMOlKLtSy1ZmLuVxSEKKyor/N5yhvp/ZiG1oE3DEYMSFA==} + dev: true + + /error-ex/1.3.2: + resolution: {integrity: sha512-7dFHNmqeFSEt2ZBsCriorKnn3Z2pj+fd9kmI6QoWw4//DL+icEBfc0U7qJCisqrTsKTjw4fNFy2pW9OqStD84g==} + dependencies: + is-arrayish: 0.2.1 + dev: true + + /es-abstract/1.20.4: + resolution: {integrity: sha512-0UtvRN79eMe2L+UNEF1BwRe364sj/DXhQ/k5FmivgoSdpM90b8Jc0mDzKMGo7QS0BVbOP/bTwBKNnDc9rNzaPA==} + engines: {node: '>= 0.4'} + dependencies: + call-bind: 1.0.2 + 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 + has: 1.0.3 + has-property-descriptors: 1.0.0 + has-symbols: 1.0.3 + internal-slot: 1.0.3 + 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-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.5 + string.prototype.trimstart: 1.0.5 + unbox-primitive: 1.0.2 + dev: true + + /es-array-method-boxes-properly/1.0.0: + resolution: {integrity: sha512-wd6JXUmyHmt8T5a2xreUwKcGPq6f1f+WwIJkijUqiGcJz1qqnZgP6XIK+QyIWU5lT7imeNxUll48bziG+TSYcA==} + dev: true + + /es-shim-unscopables/1.0.0: + resolution: {integrity: sha512-Jm6GPcCdC30eMLbZ2x8z2WuRwAws3zTBBKuusffYVUrNj/GVSUAZ+xKMaUpfNDR5IbyNA5LJbaecoUVbmUcB1w==} + dependencies: + has: 1.0.3 + dev: true + + /es-to-primitive/1.2.1: + resolution: {integrity: sha512-QCOllgZJtaUo9miYBcLChTUaHNjJF3PYs1VidD7AwiEj1kYxKeQTctLAezAOH5ZKRH0g2IgPn6KwB4IT8iRpvA==} + engines: {node: '>= 0.4'} + dependencies: + is-callable: 1.2.7 + is-date-object: 1.0.5 + is-symbol: 1.0.4 + dev: true + + /es6-error/4.1.1: + resolution: {integrity: sha512-Um/+FxMr9CISWh0bi5Zv0iOD+4cFh5qLeks1qhAopKVAJw3drgKbKySikp7wGhDL0HPeaja0P5ULZrxLkniUVg==} + dev: true + + /escalade/3.1.1: + resolution: {integrity: sha512-k0er2gUkLf8O0zKJiAhmkTnJlTvINGv7ygDNPbeIsX/TJjGJZHuh9B2UxbsaEkmlEo9MfhrSzmhIlhRlI2GXnw==} + engines: {node: '>=6'} + dev: true + + /escape-goat/2.1.1: + resolution: {integrity: sha512-8/uIhbG12Csjy2JEW7D9pHbreaVaS/OpN3ycnyvElTdwM5n6GY6W6e2IPemfvGZeUMqZ9A/3GqIZMgKnBhAw/Q==} + engines: {node: '>=8'} + dev: true + + /escape-string-regexp/1.0.5: + resolution: {integrity: sha512-vbRorB5FUQWvla16U8R/qgaFIya2qGzwDrNmCZuYKrbdSUMG6I1ZCGQRefkRVhuOkIGVne7BQ35DSfo1qvJqFg==} + engines: {node: '>=0.8.0'} + dev: true + + /escape-string-regexp/4.0.0: + resolution: {integrity: sha512-TtpcNJ3XAzx3Gq8sWRzJaVajRs0uVxA2YAkdb1jm2YkPz4G6egUFAyA3n5vtEIZefPk5Wa4UXbKuS5fKkJWdgA==} + engines: {node: '>=10'} + dev: true + + /eslint-import-resolver-node/0.3.6: + resolution: {integrity: sha512-0En0w03NRVMn9Uiyn8YRPDKvWjxCWkslUEhGNTdGx15RvPJYQ+lbOlqrlNI2vEAs4pDYK4f/HN2TbDmk5TP0iw==} + dependencies: + debug: 3.2.7 + resolve: 1.22.1 + transitivePeerDependencies: + - supports-color + dev: true + + /eslint-module-utils/2.7.4_c3hlus4v72tewog5wytziddckm: + resolution: {integrity: sha512-j4GT+rqzCoRKHwURX7pddtIPGySnX9Si/cgMI5ztrcqOPtk5dDEeZ34CQVPphnqkJytlc97Vuk05Um2mJ3gEQA==} + engines: {node: '>=4'} + peerDependencies: + '@typescript-eslint/parser': '*' + eslint: '*' + eslint-import-resolver-node: '*' + eslint-import-resolver-typescript: '*' + eslint-import-resolver-webpack: '*' + peerDependenciesMeta: + '@typescript-eslint/parser': + optional: true + eslint: + optional: true + eslint-import-resolver-node: + optional: true + eslint-import-resolver-typescript: + optional: true + eslint-import-resolver-webpack: + optional: true + dependencies: + '@typescript-eslint/parser': 5.40.0_z4bbprzjrhnsfa24uvmcbu7f5q + debug: 3.2.7 + eslint: 8.25.0 + eslint-import-resolver-node: 0.3.6 + transitivePeerDependencies: + - supports-color + dev: true + + /eslint-plugin-import/2.26.0_zb5prbqp7qzcgafjm73dfpyyvm: + resolution: {integrity: sha512-hYfi3FXaM8WPLf4S1cikh/r4IxnO6zrhZbEGz2b660EJRbuxgpDS5gkCuYgGWg2xxh2rBuIr4Pvhve/7c31koA==} + engines: {node: '>=4'} + peerDependencies: + '@typescript-eslint/parser': '*' + eslint: ^2 || ^3 || ^4 || ^5 || ^6 || ^7.2.0 || ^8 + peerDependenciesMeta: + '@typescript-eslint/parser': + optional: true + dependencies: + '@typescript-eslint/parser': 5.40.0_z4bbprzjrhnsfa24uvmcbu7f5q + array-includes: 3.1.5 + array.prototype.flat: 1.3.0 + debug: 2.6.9 + doctrine: 2.1.0 + eslint: 8.25.0 + eslint-import-resolver-node: 0.3.6 + eslint-module-utils: 2.7.4_c3hlus4v72tewog5wytziddckm + has: 1.0.3 + is-core-module: 2.10.0 + is-glob: 4.0.3 + minimatch: 3.1.2 + object.values: 1.1.5 + resolve: 1.22.1 + tsconfig-paths: 3.14.1 + transitivePeerDependencies: + - eslint-import-resolver-typescript + - eslint-import-resolver-webpack + - supports-color + dev: true + + /eslint-plugin-prefer-arrow/1.2.3_eslint@8.25.0: + resolution: {integrity: sha512-J9I5PKCOJretVuiZRGvPQxCbllxGAV/viI20JO3LYblAodofBxyMnZAJ+WGeClHgANnSJberTNoFWWjrWKBuXQ==} + peerDependencies: + eslint: '>=2.0.0' + dependencies: + eslint: 8.25.0 + dev: true + + /eslint-scope/5.1.1: + resolution: {integrity: sha512-2NxwbF/hZ0KpepYN0cNbo+FN6XoK7GaHlQhgx/hIZl6Va0bF45RQOOwhLIy8lQDbuCiadSLCBnH2CFYquit5bw==} + engines: {node: '>=8.0.0'} + dependencies: + esrecurse: 4.3.0 + estraverse: 4.3.0 + dev: true + + /eslint-scope/7.1.1: + resolution: {integrity: sha512-QKQM/UXpIiHcLqJ5AOyIW7XZmzjkzQXYE54n1++wb0u9V/abW3l9uQnxX8Z5Xd18xyKIMTUAyQ0k1e8pz6LUrw==} + engines: {node: ^12.22.0 || ^14.17.0 || >=16.0.0} + dependencies: + esrecurse: 4.3.0 + estraverse: 5.3.0 + dev: true + + /eslint-utils/3.0.0_eslint@8.25.0: + resolution: {integrity: sha512-uuQC43IGctw68pJA1RgbQS8/NP7rch6Cwd4j3ZBtgo4/8Flj4eGE7ZYSZRN3iq5pVUv6GPdW5Z1RFleo84uLDA==} + engines: {node: ^10.0.0 || ^12.0.0 || >= 14.0.0} + peerDependencies: + eslint: '>=5' + dependencies: + eslint: 8.25.0 + eslint-visitor-keys: 2.1.0 + dev: true + + /eslint-visitor-keys/2.1.0: + resolution: {integrity: sha512-0rSmRBzXgDzIsD6mGdJgevzgezI534Cer5L/vyMX0kHzT/jiB43jRhd9YUlMGYLQy2zprNmoT8qasCGtY+QaKw==} + engines: {node: '>=10'} + dev: true + + /eslint-visitor-keys/3.3.0: + resolution: {integrity: sha512-mQ+suqKJVyeuwGYHAdjMFqjCyfl8+Ldnxuyp3ldiMBFKkvytrXUZWaiPCEav8qDHKty44bD+qV1IP4T+w+xXRA==} + engines: {node: ^12.22.0 || ^14.17.0 || >=16.0.0} + dev: true + + /eslint/8.25.0: + resolution: {integrity: sha512-DVlJOZ4Pn50zcKW5bYH7GQK/9MsoQG2d5eDH0ebEkE8PbgzTTmtt/VTH9GGJ4BfeZCpBLqFfvsjX35UacUL83A==} + engines: {node: ^12.22.0 || ^14.17.0 || >=16.0.0} + hasBin: true + dependencies: + '@eslint/eslintrc': 1.3.3 + '@humanwhocodes/config-array': 0.10.7 + '@humanwhocodes/module-importer': 1.0.1 + ajv: 6.12.6 + chalk: 4.1.2 + cross-spawn: 7.0.3 + debug: 4.3.4 + doctrine: 3.0.0 + escape-string-regexp: 4.0.0 + eslint-scope: 7.1.1 + eslint-utils: 3.0.0_eslint@8.25.0 + eslint-visitor-keys: 3.3.0 + espree: 9.4.0 + esquery: 1.4.0 + esutils: 2.0.3 + fast-deep-equal: 3.1.3 + file-entry-cache: 6.0.1 + find-up: 5.0.0 + glob-parent: 6.0.2 + globals: 13.17.0 + globby: 11.1.0 + grapheme-splitter: 1.0.4 + ignore: 5.2.0 + import-fresh: 3.3.0 + imurmurhash: 0.1.4 + is-glob: 4.0.3 + js-sdsl: 4.1.5 + 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.1 + text-table: 0.2.0 + transitivePeerDependencies: + - supports-color + dev: true + + /espree/9.4.0: + resolution: {integrity: sha512-DQmnRpLj7f6TgN/NYb0MTzJXL+vJF9h3pHy4JhCIs3zwcgez8xmGg3sXHcEO97BrmO2OSvCwMdfdlyl+E9KjOw==} + engines: {node: ^12.22.0 || ^14.17.0 || >=16.0.0} + dependencies: + acorn: 8.8.0 + acorn-jsx: 5.3.2_acorn@8.8.0 + eslint-visitor-keys: 3.3.0 + dev: true + + /esprima/4.0.1: + resolution: {integrity: sha512-eGuFFw7Upda+g4p+QHvnW0RyTX/SVeJBDM/gCtMARO0cLuT2HcEKnTPvhjV6aGeqrCB/sbNop0Kszm0jsaWU4A==} + engines: {node: '>=4'} + hasBin: true + dev: true + + /esquery/1.4.0: + resolution: {integrity: sha512-cCDispWt5vHHtwMY2YrAQ4ibFkAL8RbH5YGBnZBc90MolvvfkkQcJro/aZiAQUlQ3qgrYS6D6v8Gc5G5CQsc9w==} + engines: {node: '>=0.10'} + dependencies: + estraverse: 5.3.0 + dev: true + + /esrecurse/4.3.0: + resolution: {integrity: sha512-KmfKL3b6G+RXvP8N1vr3Tq1kL/oCFgn2NYXEtqP8/L3pKapUA4G8cFVaoF3SU323CD4XypR/ffioHmkti6/Tag==} + engines: {node: '>=4.0'} + dependencies: + estraverse: 5.3.0 + dev: true + + /estraverse/4.3.0: + resolution: {integrity: sha512-39nnKffWz8xN1BU/2c79n9nB9HDzo0niYUqx6xyqUnyoAnQyyWpOTdZEeiCch8BBu515t4wp9ZmgVfVhn9EBpw==} + engines: {node: '>=4.0'} + dev: true + + /estraverse/5.3.0: + resolution: {integrity: sha512-MMdARuVEQziNTeJD8DgMqmhwR11BRQ/cBP+pLtYdSTnf3MIO8fFeiINEbX36ZdNlfU/7A9f3gUw49B3oQsvwBA==} + engines: {node: '>=4.0'} + dev: true + + /esutils/2.0.3: + resolution: {integrity: sha512-kVscqXk4OCp68SZ0dkgEKVi6/8ij300KBWTJq32P/dYeWTSwK41WyTxalN1eRmA5Z9UU/LX9D7FWSmV9SAYx6g==} + engines: {node: '>=0.10.0'} + dev: true + + /eventemitter3/4.0.7: + resolution: {integrity: sha512-8guHBZCwKnFhYdHr2ysuRWErTwhoN2X8XELRlrRwpmfeY2jjuUN4taQMsULKUVo1K4DvZl+0pgfyoysHxvmvEw==} + dev: true + + /execa/5.1.1: + resolution: {integrity: sha512-8uSpZZocAZRBAPIEINJj3Lo9HyGitllczc27Eh5YYojjMFMn8yHMDMaUHE2Jqfq05D/wucwI4JGURyXt1vchyg==} + engines: {node: '>=10'} + dependencies: + cross-spawn: 7.0.3 + get-stream: 6.0.1 + human-signals: 2.1.0 + is-stream: 2.0.1 + merge-stream: 2.0.0 + npm-run-path: 4.0.1 + onetime: 5.1.2 + signal-exit: 3.0.7 + strip-final-newline: 2.0.0 + dev: true + + /extend/3.0.2: + resolution: {integrity: sha512-fjquC59cD7CyW6urNXK0FBufkZcoiGG80wTuPujX590cB5Ttln20E2UB4S/WARVqhXffZl2LNgS+gQdPIIim/g==} + dev: true + + /external-editor/3.1.0: + resolution: {integrity: sha512-hMQ4CX1p1izmuLYyZqLMO/qGNw10wSv9QDCPfzXfyFrOaCSSoRfqE1Kf1s5an66J5JZC62NewG+mK49jOCtQew==} + engines: {node: '>=4'} + dependencies: + chardet: 0.7.0 + iconv-lite: 0.4.24 + tmp: 0.0.33 + dev: true + + /extsprintf/1.3.0: + resolution: {integrity: sha512-11Ndz7Nv+mvAC1j0ktTa7fAb0vLyGGX+rMHNBYQviQDGU0Hw7lhctJANqbPhu9nV9/izT/IntTgZ7Im/9LJs9g==} + engines: {'0': node >=0.6.0} + dev: true + + /fast-deep-equal/3.1.3: + resolution: {integrity: sha512-f3qQ9oQy9j2AhBe/H9VC91wLmKBCCU/gDOnKNAYG5hswO7BLKj09Hc5HYNz9cGI++xlpDCIgDaitVs03ATR84Q==} + dev: true + + /fast-glob/3.2.12: + resolution: {integrity: sha512-DVj4CQIYYow0BlaelwK1pHl5n5cRSJfM60UA0zK891sVInoPri2Ekj7+e1CT3/3qxXenpI+nBBmQAcJPJgaj4w==} + engines: {node: '>=8.6.0'} + dependencies: + '@nodelib/fs.stat': 2.0.5 + '@nodelib/fs.walk': 1.2.8 + glob-parent: 5.1.2 + merge2: 1.4.1 + micromatch: 4.0.5 + dev: true + + /fast-json-stable-stringify/2.1.0: + resolution: {integrity: sha512-lhd/wF+Lk98HZoTCtlVraHtfh5XYijIjalXck7saUtuanSDyLMxnHhSXEDJqHxD7msR8D0uCmqlkwjCV8xvwHw==} + dev: true + + /fast-levenshtein/2.0.6: + resolution: {integrity: sha512-DCXu6Ifhqcks7TZKY3Hxp3y6qphY5SJZmrWMDrKcERSOXWQdMhU9Ig/PYrzyw/ul9jOIyh0N4M0tbC5hodg8dw==} + dev: true + + /fast-memoize/2.5.2: + resolution: {integrity: sha512-Ue0LwpDYErFbmNnZSF0UH6eImUwDmogUO1jyE+JbN2gsQz/jICm1Ve7t9QT0rNSsfJt+Hs4/S3GnsDVjL4HVrw==} + dev: true + + /fastq/1.13.0: + resolution: {integrity: sha512-YpkpUnK8od0o1hmeSc7UUs/eB/vIPWJYjKck2QKIzAf71Vm1AAQ3EbuZB3g2JIy+pg+ERD0vqI79KyZiB2e2Nw==} + dependencies: + reusify: 1.0.4 + dev: true + + /figgy-pudding/3.5.2: + resolution: {integrity: sha512-0btnI/H8f2pavGMN8w40mlSKOfTK2SVJmBfBeVIj3kNw0swwgzyRq0d5TJVOwodFmtvpPeWPN/MCcfuWF0Ezbw==} + dev: true + + /figures/3.2.0: + resolution: {integrity: sha512-yaduQFRKLXYOGgEn6AZau90j3ggSOyiqXU0F9JZfeXYhNa+Jk4X+s45A2zg5jns87GAFa34BBm2kXw4XpNcbdg==} + engines: {node: '>=8'} + dependencies: + escape-string-regexp: 1.0.5 + dev: true + + /file-entry-cache/6.0.1: + resolution: {integrity: sha512-7Gps/XWymbLk2QLYK4NzpMOrYjMhdIxXuIvy2QBsLE6ljuodKvdkWs/cpyJJ3CVIVpH0Oi1Hvg1ovbMzLdFBBg==} + engines: {node: ^10.12.0 || >=12.0.0} + dependencies: + flat-cache: 3.0.4 + dev: true + + /fill-range/7.0.1: + resolution: {integrity: sha512-qOo9F+dMUmC2Lcb4BbVvnKJxTPjCm+RRpe4gDuGrzkL7mEVl/djYSu2OdQ2Pa302N4oqkSg9ir6jaLWJ2USVpQ==} + engines: {node: '>=8'} + dependencies: + to-regex-range: 5.0.1 + dev: true + + /filter-obj/1.1.0: + resolution: {integrity: sha512-8rXg1ZnX7xzy2NGDVkBVaAy+lSlPNwad13BtgSlLuxfIslyt5Vg64U7tFcCt4WS1R0hvtnQybT/IyCkGZ3DpXQ==} + engines: {node: '>=0.10.0'} + dev: true + + /find-cache-dir/3.3.2: + resolution: {integrity: sha512-wXZV5emFEjrridIgED11OoUKLxiYjAcqot/NJdAkOhlJ+vGzwhOAfcG5OX1jP+S0PcjEn8bdMJv+g2jwQ3Onig==} + engines: {node: '>=8'} + dependencies: + commondir: 1.0.1 + make-dir: 3.1.0 + pkg-dir: 4.2.0 + dev: true + + /find-up/2.1.0: + resolution: {integrity: sha512-NWzkk0jSJtTt08+FBFMvXoeZnOJD+jTtsRmBYbAIzJdX6l7dLgR7CTubCM5/eDdPUBvLCeVasP1brfVR/9/EZQ==} + engines: {node: '>=4'} + dependencies: + locate-path: 2.0.0 + dev: true + + /find-up/3.0.0: + resolution: {integrity: sha512-1yD6RmLI1XBfxugvORwlck6f75tYL+iR0jqwsOrOxMZyGYqUuDhJ0l4AXdO1iX/FTs9cBAMEk1gWSEx1kSbylg==} + engines: {node: '>=6'} + dependencies: + locate-path: 3.0.0 + dev: true + + /find-up/4.1.0: + resolution: {integrity: sha512-PpOwAdQ/YlXQ2vj8a3h8IipDuYRi3wceVQQGYWxNINccq40Anw7BlsEXCMbt1Zt+OLA6Fq9suIpIWD0OsnISlw==} + engines: {node: '>=8'} + dependencies: + locate-path: 5.0.0 + path-exists: 4.0.0 + dev: true + + /find-up/5.0.0: + resolution: {integrity: sha512-78/PXT1wlLLDgTzDs7sjq9hzz0vXD+zn+7wypEe4fXQxCmdmqfGsEPQxmiCSQI3ajFV91bVSsvNtrJRiW6nGng==} + engines: {node: '>=10'} + dependencies: + locate-path: 6.0.0 + path-exists: 4.0.0 + dev: true + + /flat-cache/3.0.4: + resolution: {integrity: sha512-dm9s5Pw7Jc0GvMYbshN6zchCA9RgQlzzEZX3vylR9IqFfS8XciblUXOKfW6SiuJ0e13eDYZoZV5wdrev7P3Nwg==} + engines: {node: ^10.12.0 || >=12.0.0} + dependencies: + flatted: 3.2.7 + rimraf: 3.0.2 + dev: true + + /flatted/3.2.7: + resolution: {integrity: sha512-5nqDSxl8nn5BSNxyR3n4I6eDmbolI6WT+QqR547RwxQapgjQBmtktdP+HTBb/a/zLsbzERTONyUB5pefh5TtjQ==} + dev: true + + /foreground-child/2.0.0: + resolution: {integrity: sha512-dCIq9FpEcyQyXKCkyzmlPTFNgrCzPudOe+mhvJU5zAtlBnGVy2yKxtfsxK2tQBThwq225jcvBjpw1Gr40uzZCA==} + engines: {node: '>=8.0.0'} + dependencies: + cross-spawn: 7.0.3 + signal-exit: 3.0.7 + dev: true + + /forever-agent/0.6.1: + resolution: {integrity: sha512-j0KLYPhm6zeac4lz3oJ3o65qvgQCcPubiyotZrXqEaG4hNagNYO8qdlUrX5vwqv9ohqeT/Z3j6+yW067yWWdUw==} + dev: true + + /form-data/2.3.3: + resolution: {integrity: sha512-1lLKB2Mu3aGP1Q/2eCOx0fNbRMe7XdwktwOruhfqqd0rIJWwN4Dh+E3hrPSlDCXnSR7UtZ1N38rVXm+6+MEhJQ==} + engines: {node: '>= 0.12'} + dependencies: + asynckit: 0.4.0 + combined-stream: 1.0.8 + mime-types: 2.1.35 + dev: true + + /fp-and-or/0.1.3: + resolution: {integrity: sha512-wJaE62fLaB3jCYvY2ZHjZvmKK2iiLiiehX38rz5QZxtdN8fVPJDeZUiVvJrHStdTc+23LHlyZuSEKgFc0pxi2g==} + engines: {node: '>=10'} + dev: true + + /fromentries/1.3.2: + resolution: {integrity: sha512-cHEpEQHUg0f8XdtZCc2ZAhrHzKzT0MrFUTcvx+hfxYu7rGMDc5SKoXFh+n4YigxsHXRzc6OrCshdR1bWH6HHyg==} + dev: true + + /fs-extra/9.1.0: + resolution: {integrity: sha512-hcg3ZmepS30/7BSFqRvoo3DOMQu7IjqxO5nCDt+zM9XWjb33Wg7ziNT+Qvqbuc3+gWpzO02JubVyk2G4Zvo1OQ==} + engines: {node: '>=10'} + dependencies: + at-least-node: 1.0.0 + graceful-fs: 4.2.10 + jsonfile: 6.1.0 + universalify: 2.0.0 + dev: true + + /fs-minipass/1.2.7: + resolution: {integrity: sha512-GWSSJGFy4e9GUeCcbIkED+bgAoFyj7XF1mV8rma3QW4NIqX9Kyx79N/PF61H5udOV3aY1IaMLs6pGbH71nlCTA==} + dependencies: + minipass: 2.9.0 + dev: true + + /fs-minipass/2.1.0: + resolution: {integrity: sha512-V/JgOLFCS+R6Vcq0slCuaeWEdNC3ouDlJMNIsacH2VtALiu9mV4LPrHc5cDl8k5aw6J8jwgWWpiTo5RYhmIzvg==} + engines: {node: '>= 8'} + dependencies: + minipass: 3.3.4 + dev: true + + /fs.realpath/1.0.0: + resolution: {integrity: sha512-OO0pH2lK6a0hZnAdau5ItzHPI6pUlvI7jMVnxUQRtw4owF2wk8lOSabtGDCTP4Ggrg2MbGnWO9X8K1t4+fGMDw==} + dev: true + + /function-bind/1.1.1: + resolution: {integrity: sha512-yIovAzMX49sF8Yl58fSCWJ5svSLuaibPxXQJFLmBObTuCr0Mf1KiPopGM9NiFjiYBCbfaa2Fh6breQ6ANVTI0A==} + dev: true + + /function.prototype.name/1.1.5: + resolution: {integrity: sha512-uN7m/BzVKQnCUF/iW8jYea67v++2u7m5UgENbHRtdDVclOUP+FMPlCNdmk0h/ysGyo2tavMJEDqJAkJdRa1vMA==} + engines: {node: '>= 0.4'} + dependencies: + call-bind: 1.0.2 + define-properties: 1.1.4 + es-abstract: 1.20.4 + functions-have-names: 1.2.3 + dev: true + + /functions-have-names/1.2.3: + resolution: {integrity: sha512-xckBUXyTIqT97tq2x2AMb+g163b5JFysYk0x4qxNFwbfQkmNZoiRHb6sPzI9/QV33WeuvVYBUIiD4NzNIyqaRQ==} + dev: true + + /gauge/2.7.4: + resolution: {integrity: sha512-14x4kjc6lkD3ltw589k0NrPD6cCNTD6CWoVUNpB85+DrtONoZn+Rug6xZU5RvSC4+TZPxA5AnBibQYAvZn41Hg==} + dependencies: + aproba: 1.2.0 + console-control-strings: 1.1.0 + has-unicode: 2.0.1 + object-assign: 4.1.1 + signal-exit: 3.0.7 + string-width: 1.0.2 + strip-ansi: 3.0.1 + wide-align: 1.1.5 + dev: true + + /gauge/4.0.4: + resolution: {integrity: sha512-f9m+BEN5jkg6a0fZjleidjN51VE1X+mPFQ2DJ0uv1V39oCLCbsGe6yjbBnp7eK7z/+GAon99a3nHuqbuuthyPg==} + engines: {node: ^12.13.0 || ^14.15.0 || >=16.0.0} + dependencies: + aproba: 2.0.0 + color-support: 1.1.3 + console-control-strings: 1.1.0 + has-unicode: 2.0.1 + signal-exit: 3.0.7 + string-width: 4.2.3 + strip-ansi: 6.0.1 + wide-align: 1.1.5 + dev: true + + /gensync/1.0.0-beta.2: + resolution: {integrity: sha512-3hN7NaskYvMDLQY55gnW3NQ+mesEAepTqlg+VEbj7zzqEMBVNhzcGYYeqFo/TlYz6eQiFcp1HcsCZO+nGgS8zg==} + engines: {node: '>=6.9.0'} + dev: true + + /get-caller-file/2.0.5: + resolution: {integrity: sha512-DyFP3BM/3YHTQOCUL/w0OZHR0lpKeGrxotcHWcqNEdnltqFwXVfhEBQ94eIo34AfQpo0rGki4cyIiftY06h2Fg==} + engines: {node: 6.* || 8.* || >= 10.*} + dev: true + + /get-intrinsic/1.1.3: + resolution: {integrity: sha512-QJVz1Tj7MS099PevUG5jvnt9tSkXN8K14dxQlikJuPt4uD9hHAHjLyLBiLR5zELelBdD9QNRAXZzsJx0WaDL9A==} + dependencies: + function-bind: 1.1.1 + has: 1.0.3 + has-symbols: 1.0.3 + dev: true + + /get-package-type/0.1.0: + resolution: {integrity: sha512-pjzuKtY64GYfWizNAJ0fr9VqttZkNiK2iS430LtIHzjBEr6bX8Am2zm4sW4Ro5wjWW5cAlRL1qAMTcXbjNAO2Q==} + engines: {node: '>=8.0.0'} + dev: true + + /get-pkg-repo/4.2.1: + resolution: {integrity: sha512-2+QbHjFRfGB74v/pYWjd5OhU3TDIC2Gv/YKUTk/tCvAz0pkn/Mz6P3uByuBimLOcPvN2jYdScl3xGFSrx0jEcA==} + engines: {node: '>=6.9.0'} + hasBin: true + dependencies: + '@hutson/parse-repository-url': 3.0.2 + hosted-git-info: 4.1.0 + through2: 2.0.5 + yargs: 16.2.0 + dev: true + + /get-port/5.1.1: + resolution: {integrity: sha512-g/Q1aTSDOxFpchXC4i8ZWvxA1lnPqx/JHqcpIw0/LX9T8x/GBbi6YnlN5nhaKIFkT8oFsscUKgDJYxfwfS6QsQ==} + engines: {node: '>=8'} + dev: true + + /get-stdin/8.0.0: + resolution: {integrity: sha512-sY22aA6xchAzprjyqmSEQv4UbAAzRN0L2dQB0NlN5acTTK9Don6nhoc3eAbUnpZiCANAMfd/+40kVdKfFygohg==} + engines: {node: '>=10'} + dev: true + + /get-stream/4.1.0: + resolution: {integrity: sha512-GMat4EJ5161kIy2HevLlr4luNjBgvmj413KaQA7jt4V8B4RDsfpHk7WQ9GVqfYyyx8OS/L66Kox+rJRNklLK7w==} + engines: {node: '>=6'} + dependencies: + pump: 3.0.0 + dev: true + + /get-stream/5.2.0: + resolution: {integrity: sha512-nBF+F1rAZVCu/p7rjzgA+Yb4lfYXrpl7a6VmJrU8wF9I1CKvP/QwPNZHnOlwbTkY6dvtFIzFMSyQXbLoTQPRpA==} + engines: {node: '>=8'} + dependencies: + pump: 3.0.0 + dev: true + + /get-stream/6.0.1: + resolution: {integrity: sha512-ts6Wi+2j3jQjqi70w5AlN8DFnkSwC+MqmxEzdEALB2qXZYV3X/b1CTfgPLGJNMeAWxdPfU8FO1ms3NUfaHCPYg==} + engines: {node: '>=10'} + dev: true + + /get-symbol-description/1.0.0: + resolution: {integrity: sha512-2EmdH1YvIQiZpltCNgkuiUnyukzxM/R6NDJX31Ke3BG1Nq5b0S2PhX59UKi9vZpPDQVdqn+1IcaAwnzTT5vCjw==} + engines: {node: '>= 0.4'} + dependencies: + call-bind: 1.0.2 + get-intrinsic: 1.1.3 + dev: true + + /getpass/0.1.7: + resolution: {integrity: sha512-0fzj9JxOLfJ+XGLhR8ze3unN0KZCgZwiSSDz168VERjK8Wl8kVSdcu2kspd4s4wtAa1y/qrVRiAA0WclVsu0ng==} + dependencies: + assert-plus: 1.0.0 + dev: true + + /git-raw-commits/2.0.11: + resolution: {integrity: sha512-VnctFhw+xfj8Va1xtfEqCUD2XDrbAPSJx+hSrE5K7fGdjZruW7XV+QOrN7LF/RJyvspRiD2I0asWsxFp0ya26A==} + engines: {node: '>=10'} + hasBin: true + dependencies: + dargs: 7.0.0 + lodash: 4.17.21 + meow: 8.1.2 + split2: 3.2.2 + through2: 4.0.2 + dev: true + + /git-remote-origin-url/2.0.0: + resolution: {integrity: sha512-eU+GGrZgccNJcsDH5LkXR3PB9M958hxc7sbA8DFJjrv9j4L2P/eZfKhM+QD6wyzpiv+b1BpK0XrYCxkovtjSLw==} + engines: {node: '>=4'} + dependencies: + gitconfiglocal: 1.0.0 + pify: 2.3.0 + dev: true + + /git-semver-tags/4.1.1: + resolution: {integrity: sha512-OWyMt5zBe7xFs8vglMmhM9lRQzCWL3WjHtxNNfJTMngGym7pC1kh8sP6jevfydJ6LP3ZvGxfb6ABYgPUM0mtsA==} + engines: {node: '>=10'} + hasBin: true + dependencies: + meow: 8.1.2 + semver: 6.3.0 + dev: true + + /git-up/4.0.5: + resolution: {integrity: sha512-YUvVDg/vX3d0syBsk/CKUTib0srcQME0JyHkL5BaYdwLsiCslPWmDSi8PUMo9pXYjrryMcmsCoCgsTpSCJEQaA==} + dependencies: + is-ssh: 1.4.0 + parse-url: 6.0.5 + dev: true + + /git-url-parse/11.6.0: + resolution: {integrity: sha512-WWUxvJs5HsyHL6L08wOusa/IXYtMuCAhrMmnTjQPpBU0TTHyDhnOATNH3xNQz7YOQUsqIIPTGr4xiVti1Hsk5g==} + dependencies: + git-up: 4.0.5 + dev: true + + /gitconfiglocal/1.0.0: + resolution: {integrity: sha512-spLUXeTAVHxDtKsJc8FkFVgFtMdEN9qPGpL23VfSHx4fP4+Ds097IXLvymbnDH8FnmxX5Nr9bPw3A+AQ6mWEaQ==} + dependencies: + ini: 1.3.8 + dev: true + + /glob-parent/5.1.2: + resolution: {integrity: sha512-AOIgSQCepiJYwP3ARnGx+5VnTu2HBYdzbGP45eLw1vr3zB3vZLeyed1sC9hnbcOc9/SrMyM5RPQrkGz4aS9Zow==} + engines: {node: '>= 6'} + dependencies: + is-glob: 4.0.3 + dev: true + + /glob-parent/6.0.2: + resolution: {integrity: sha512-XxwI8EOhVQgWp6iDL+3b0r86f4d6AX6zSU55HfB4ydCEuXLXc5FcYeOu+nnGftS4TEju/11rt4KJPTMgbfmv4A==} + engines: {node: '>=10.13.0'} + dependencies: + is-glob: 4.0.3 + dev: true + + /glob/7.2.3: + resolution: {integrity: sha512-nFR0zLpU2YCaRxwoCJvL6UvCH2JFyFVIvwTLsIf21AuHlMskA1hhTdk+LlYJtOlYt9v6dvszD2BGRqBL+iQK9Q==} + dependencies: + fs.realpath: 1.0.0 + inflight: 1.0.6 + inherits: 2.0.4 + minimatch: 3.1.2 + once: 1.4.0 + path-is-absolute: 1.0.1 + dev: true + + /glob/8.0.3: + resolution: {integrity: sha512-ull455NHSHI/Y1FqGaaYFaLGkNMMJbavMrEGFXG/PGrg6y7sutWHUHrz6gy6WEBH6akM1M414dWKCNs+IhKdiQ==} + engines: {node: '>=12'} + dependencies: + fs.realpath: 1.0.0 + inflight: 1.0.6 + inherits: 2.0.4 + minimatch: 5.1.0 + once: 1.4.0 + dev: true + + /global-dirs/3.0.0: + resolution: {integrity: sha512-v8ho2DS5RiCjftj1nD9NmnfaOzTdud7RRnVd9kFNOjqZbISlx5DQ+OrTkywgd0dIt7oFCvKetZSHoHcP3sDdiA==} + engines: {node: '>=10'} + dependencies: + ini: 2.0.0 + dev: true + + /globals/11.12.0: + resolution: {integrity: sha512-WOBp/EEGUiIsJSp7wcv/y6MO+lV9UoncWqxuFfm8eBwzWNgyfBd6Gz+IeKQ9jCmyhoH99g15M3T+QaVHFjizVA==} + engines: {node: '>=4'} + dev: true + + /globals/13.17.0: + resolution: {integrity: sha512-1C+6nQRb1GwGMKm2dH/E7enFAMxGTmGI7/dEdhy/DNelv85w9B72t3uc5frtMNXIbzrarJJ/lTCjcaZwbLJmyw==} + engines: {node: '>=8'} + dependencies: + type-fest: 0.20.2 + dev: true + + /globby/11.1.0: + resolution: {integrity: sha512-jhIXaOzy1sb8IyocaruWSn1TjmnBVs8Ayhcy83rmxNJ8q2uWKCAj3CnJY+KpGSXCueAPc0i05kVvVKtP1t9S3g==} + engines: {node: '>=10'} + dependencies: + array-union: 2.1.0 + dir-glob: 3.0.1 + fast-glob: 3.2.12 + ignore: 5.2.0 + merge2: 1.4.1 + slash: 3.0.0 + dev: true + + /got/9.6.0: + resolution: {integrity: sha512-R7eWptXuGYxwijs0eV+v3o6+XH1IqVK8dJOEecQfTmkncw9AV4dcw/Dhxi8MdlqPthxxpZyizMzyg8RTmEsG+Q==} + engines: {node: '>=8.6'} + dependencies: + '@sindresorhus/is': 0.14.0 + '@szmarczak/http-timer': 1.1.2 + '@types/keyv': 3.1.4 + '@types/responselike': 1.0.0 + cacheable-request: 6.1.0 + decompress-response: 3.3.0 + duplexer3: 0.1.5 + get-stream: 4.1.0 + lowercase-keys: 1.0.1 + mimic-response: 1.0.1 + p-cancelable: 1.1.0 + to-readable-stream: 1.0.0 + url-parse-lax: 3.0.0 + dev: true + + /graceful-fs/4.2.10: + resolution: {integrity: sha512-9ByhssR2fPVsNZj478qUUbKfmL0+t5BDVyjShtyZZLiK7ZDAArFFfopyOTj0M05wE2tJPisA4iTnnXl2YoPvOA==} + dev: true + + /grapheme-splitter/1.0.4: + resolution: {integrity: sha512-bzh50DW9kTPM00T8y4o8vQg89Di9oLJVLW/KaOGIXJWP/iqCN6WKYkbNOF04vFLJhwcpYUh9ydh/+5vpOqV4YQ==} + dev: true + + /handlebars/4.7.7: + resolution: {integrity: sha512-aAcXm5OAfE/8IXkcZvCepKU3VzW1/39Fb5ZuqMtgI/hT8X2YgoMvBY5dLhq/cpOvw7Lk1nK/UF71aLG/ZnVYRA==} + engines: {node: '>=0.4.7'} + hasBin: true + dependencies: + minimist: 1.2.7 + neo-async: 2.6.2 + source-map: 0.6.1 + wordwrap: 1.0.0 + optionalDependencies: + uglify-js: 3.17.3 + dev: true + + /har-schema/2.0.0: + resolution: {integrity: sha512-Oqluz6zhGX8cyRaTQlFMPw80bSJVG2x/cFb8ZPhUILGgHka9SsokCCOQgpveePerqidZOrT14ipqfJb7ILcW5Q==} + engines: {node: '>=4'} + dev: true + + /har-validator/5.1.5: + resolution: {integrity: sha512-nmT2T0lljbxdQZfspsno9hgrG3Uir6Ks5afism62poxqBM6sDnMEuPmzTq8XN0OEwqKLLdh1jQI3qyE66Nzb3w==} + engines: {node: '>=6'} + deprecated: this library is no longer supported + dependencies: + ajv: 6.12.6 + har-schema: 2.0.0 + dev: true + + /hard-rejection/2.1.0: + resolution: {integrity: sha512-VIZB+ibDhx7ObhAe7OVtoEbuP4h/MuOTHJ+J8h/eBXotJYl0fBgR72xDFCKgIh22OJZIOVNxBMWuhAr10r8HdA==} + engines: {node: '>=6'} + dev: true + + /has-bigints/1.0.2: + resolution: {integrity: sha512-tSvCKtBr9lkF0Ex0aQiP9N+OpV4zi2r/Nee5VkRDbaqv35RLYMzbwQfFSZZH0kR+Rd6302UJZ2p/bJCEoR3VoQ==} + dev: true + + /has-flag/3.0.0: + resolution: {integrity: sha512-sKJf1+ceQBr4SMkvQnBDNDtf4TXpVhVGateu0t918bl30FnbE2m4vNLX+VWe/dpjlb+HugGYzW7uQXH98HPEYw==} + engines: {node: '>=4'} + dev: true + + /has-flag/4.0.0: + resolution: {integrity: sha512-EykJT/Q1KjTWctppgIAgfSO0tKVuZUjhgMr17kqTumMl6Afv3EISleU7qZUzoXDFTAHTDC4NOoG/ZxU3EvlMPQ==} + engines: {node: '>=8'} + dev: true + + /has-property-descriptors/1.0.0: + resolution: {integrity: sha512-62DVLZGoiEBDHQyqG4w9xCuZ7eJEwNmJRWw2VY84Oedb7WFcA27fiEVe8oUQx9hAUJ4ekurquucTGwsyO1XGdQ==} + dependencies: + get-intrinsic: 1.1.3 + dev: true + + /has-symbols/1.0.3: + resolution: {integrity: sha512-l3LCuF6MgDNwTDKkdYGEihYjt5pRPbEg46rtlmnSPlUbgmB8LOIrKJbYYFBSbnPaJexMKtiPO8hmeRjRz2Td+A==} + engines: {node: '>= 0.4'} + dev: true + + /has-tostringtag/1.0.0: + resolution: {integrity: sha512-kFjcSNhnlGV1kyoGk7OXKSawH5JOb/LzUc5w9B02hOTO0dfFRjbHQKvg1d6cf3HbeUmtU9VbbV3qzZ2Teh97WQ==} + engines: {node: '>= 0.4'} + dependencies: + has-symbols: 1.0.3 + dev: true + + /has-unicode/2.0.1: + resolution: {integrity: sha512-8Rf9Y83NBReMnx0gFzA8JImQACstCYWUplepDa9xprwwtmgEZUF0h/i5xSA625zB/I37EtrswSST6OXxwaaIJQ==} + dev: true + + /has-yarn/2.1.0: + resolution: {integrity: sha512-UqBRqi4ju7T+TqGNdqAO0PaSVGsDGJUBQvk9eUWNGRY1CFGDzYhLWoM7JQEemnlvVcv/YEmc2wNW8BC24EnUsw==} + engines: {node: '>=8'} + dev: true + + /has/1.0.3: + resolution: {integrity: sha512-f2dvO0VU6Oej7RkWJGrehjbzMAjFp5/VKPp5tTpWIV4JHHZK1/BxbFRtf/siA2SWTe09caDmVtYYzWEIbBS4zw==} + engines: {node: '>= 0.4.0'} + dependencies: + function-bind: 1.1.1 + dev: true + + /hasha/5.2.2: + resolution: {integrity: sha512-Hrp5vIK/xr5SkeN2onO32H0MgNZ0f17HRNH39WfL0SYUNOTZ5Lz1TJ8Pajo/87dYGEFlLMm7mIc/k/s6Bvz9HQ==} + engines: {node: '>=8'} + dependencies: + is-stream: 2.0.1 + type-fest: 0.8.1 + dev: true + + /hosted-git-info/2.8.9: + resolution: {integrity: sha512-mxIDAb9Lsm6DoOJ7xH+5+X4y1LU/4Hi50L9C5sIswK3JzULS4bwk1FvjdBgvYR4bzT4tuUQiC15FE2f5HbLvYw==} + dev: true + + /hosted-git-info/4.1.0: + resolution: {integrity: sha512-kyCuEOWjJqZuDbRHzL8V93NzQhwIB71oFWSyzVo+KPZI+pnQPPxucdkrOZvkLRnrf5URsQM+IJ09Dw29cRALIA==} + engines: {node: '>=10'} + dependencies: + lru-cache: 6.0.0 + dev: true + + /hosted-git-info/5.1.0: + resolution: {integrity: sha512-Ek+QmMEqZF8XrbFdwoDjSbm7rT23pCgEMOJmz6GPk/s4yH//RQfNPArhIxbguNxROq/+5lNBwCDHMhA903Kx1Q==} + engines: {node: ^12.13.0 || ^14.15.0 || >=16.0.0} + dependencies: + lru-cache: 7.14.0 + dev: true + + /html-escaper/2.0.2: + resolution: {integrity: sha512-H2iMtd0I4Mt5eYiapRdIDjp+XzelXQ0tFE4JS7YFwFevXXMmOp9myNrUvCg0D6ws8iqkRPBfKHgbwig1SmlLfg==} + dev: true + + /http-cache-semantics/4.1.0: + resolution: {integrity: sha512-carPklcUh7ROWRK7Cv27RPtdhYhUsela/ue5/jKzjegVvXDqM2ILE9Q2BGn9JZJh1g87cp56su/FgQSzcWS8cQ==} + dev: true + + /http-proxy-agent/4.0.1: + resolution: {integrity: sha512-k0zdNgqWTGA6aeIRVpvfVob4fL52dTfaehylg0Y4UvSySvOq/Y+BOyPrgpUrA7HylqvU8vIZGsRuXmspskV0Tg==} + engines: {node: '>= 6'} + dependencies: + '@tootallnate/once': 1.1.2 + agent-base: 6.0.2 + debug: 4.3.4 + transitivePeerDependencies: + - supports-color + dev: true + + /http-proxy-agent/5.0.0: + resolution: {integrity: sha512-n2hY8YdoRE1i7r6M0w9DIw5GgZN0G25P8zLCRQ8rjXtTU3vsNFBI/vWK/UIeE6g5MUUz6avwAPXmL6Fy9D/90w==} + engines: {node: '>= 6'} + dependencies: + '@tootallnate/once': 2.0.0 + agent-base: 6.0.2 + debug: 4.3.4 + transitivePeerDependencies: + - supports-color + dev: true + + /http-signature/1.2.0: + resolution: {integrity: sha512-CAbnr6Rz4CYQkLYUtSNXxQPUH2gK8f3iWexVlsnMeD+GjlsQ0Xsy1cOX+mN3dtxYomRy21CiOzU8Uhw6OwncEQ==} + engines: {node: '>=0.8', npm: '>=1.3.7'} + dependencies: + assert-plus: 1.0.0 + jsprim: 1.4.2 + sshpk: 1.17.0 + dev: true + + /https-proxy-agent/5.0.1: + resolution: {integrity: sha512-dFcAjpTQFgoLMzC2VwU+C/CbS7uRL0lWmxDITmqm7C+7F0Odmj6s9l6alZc6AELXhrnggM2CeWSXHGOdX2YtwA==} + engines: {node: '>= 6'} + dependencies: + agent-base: 6.0.2 + debug: 4.3.4 + transitivePeerDependencies: + - supports-color + dev: true + + /human-signals/2.1.0: + resolution: {integrity: sha512-B4FFZ6q/T2jhhksgkbEW3HBvWIfDW85snkQgawt07S7J5QXTk6BkNV+0yAeZrM5QpMAdYlocGoljn0sJ/WQkFw==} + engines: {node: '>=10.17.0'} + dev: true + + /humanize-ms/1.2.1: + resolution: {integrity: sha512-Fl70vYtsAFb/C06PTS9dZBo7ihau+Tu/DNCk/OyHhea07S+aeMWpFFkUaXRa8fI+ScZbEI8dfSxwY7gxZ9SAVQ==} + dependencies: + ms: 2.1.3 + dev: true + + /iconv-lite/0.4.24: + resolution: {integrity: sha512-v3MXnZAcvnywkTUEZomIActle7RXXeedOR31wwl7VlyoXO4Qi9arvSenNQWne1TcRwhCL1HwLI21bEqdpj8/rA==} + engines: {node: '>=0.10.0'} + dependencies: + safer-buffer: 2.1.2 + dev: true + + /iconv-lite/0.6.3: + resolution: {integrity: sha512-4fCk79wshMdzMp2rH06qWrJE4iolqLhCUH+OiuIgU++RB0+94NlDL81atO7GX55uUKueo0txHNtvEyI6D7WdMw==} + engines: {node: '>=0.10.0'} + dependencies: + safer-buffer: 2.1.2 + dev: true + optional: true + + /ignore-walk/3.0.4: + resolution: {integrity: sha512-PY6Ii8o1jMRA1z4F2hRkH/xN59ox43DavKvD3oDpfurRlOJyAHpifIwpbdv1n4jt4ov0jSpw3kQ4GhJnpBL6WQ==} + dependencies: + minimatch: 3.1.2 + dev: true + + /ignore-walk/5.0.1: + resolution: {integrity: sha512-yemi4pMf51WKT7khInJqAvsIGzoqYXblnsz0ql8tM+yi1EKYTY1evX4NAbJrLL/Aanr2HyZeluqU+Oi7MGHokw==} + engines: {node: ^12.13.0 || ^14.15.0 || >=16.0.0} + dependencies: + minimatch: 5.1.0 + dev: true + + /ignore/5.2.0: + resolution: {integrity: sha512-CmxgYGiEPCLhfLnpPp1MoRmifwEIOgjcHXxOBjv7mY96c+eWScsOP9c112ZyLdWHi0FxHjI+4uVhKYp/gcdRmQ==} + engines: {node: '>= 4'} + dev: true + + /import-fresh/3.3.0: + resolution: {integrity: sha512-veYYhQa+D1QBKznvhUHxb8faxlrwUnxseDAbAp457E0wLNio2bOSKnjYDhMj+YiAq61xrMGhQk9iXVk5FzgQMw==} + engines: {node: '>=6'} + dependencies: + parent-module: 1.0.1 + resolve-from: 4.0.0 + dev: true + + /import-lazy/2.1.0: + resolution: {integrity: sha512-m7ZEHgtw69qOGw+jwxXkHlrlIPdTGkyh66zXZ1ajZbxkDBNjSY/LGbmjc7h0s2ELsUDTAhFr55TrPSSqJGPG0A==} + engines: {node: '>=4'} + dev: true + + /import-local/3.1.0: + resolution: {integrity: sha512-ASB07uLtnDs1o6EHjKpX34BKYDSqnFerfTOJL2HvMqF70LnxpjkzDB8J44oT9pu4AMPkQwf8jl6szgvNd2tRIg==} + engines: {node: '>=8'} + hasBin: true + dependencies: + pkg-dir: 4.2.0 + resolve-cwd: 3.0.0 + dev: true + + /imurmurhash/0.1.4: + resolution: {integrity: sha512-JmXMZ6wuvDmLiHEml9ykzqO6lwFbof0GG4IkcGaENdCRDDmMVnny7s5HsIgHCbaq0w2MyPhDqkhTUgS2LU2PHA==} + engines: {node: '>=0.8.19'} + dev: true + + /indent-string/4.0.0: + resolution: {integrity: sha512-EdDDZu4A2OyIK7Lr/2zG+w5jmbuk1DVBnEwREQvBzspBJkCEbRa8GxU1lghYcaGJCnRWibjDXlq779X1/y5xwg==} + engines: {node: '>=8'} + dev: true + + /infer-owner/1.0.4: + resolution: {integrity: sha512-IClj+Xz94+d7irH5qRyfJonOdfTzuDaifE6ZPWfx0N0+/ATZCbuTPq2prFl526urkQd90WyUKIh1DfBQ2hMz9A==} + dev: true + + /inflight/1.0.6: + resolution: {integrity: sha512-k92I/b08q4wvFscXCLvqfsHCrjrF7yiXsQuIVvVE7N82W3+aqpzuUdBbfhWcy/FZR3/4IgflMgKLOsvPDrGCJA==} + dependencies: + once: 1.4.0 + wrappy: 1.0.2 + dev: true + + /inherits/2.0.4: + resolution: {integrity: sha512-k/vGaX4/Yla3WzyMCvTQOXYeIHvqOKtnqBduzTHpzpQZzAskKMhZ2K+EnBiSM9zGSoIFeMpXKxa4dYeZIQqewQ==} + dev: true + + /ini/1.3.8: + resolution: {integrity: sha512-JV/yugV2uzW5iMRSiZAyDtQd+nxtUnjeLt0acNdw98kKLrvuRVyB80tsREOE7yvGVgalhZ6RNXCmEHkUKBKxew==} + dev: true + + /ini/2.0.0: + resolution: {integrity: sha512-7PnF4oN3CvZF23ADhA5wRaYEQpJ8qygSkbtTXWBeXWXmEVRXK+1ITciHWwHhsjv1TmW0MgacIv6hEi5pX5NQdA==} + engines: {node: '>=10'} + dev: true + + /init-package-json/2.0.5: + resolution: {integrity: sha512-u1uGAtEFu3VA6HNl/yUWw57jmKEMx8SKOxHhxjGnOFUiIlFnohKDFg4ZrPpv9wWqk44nDxGJAtqjdQFm+9XXQA==} + engines: {node: '>=10'} + dependencies: + npm-package-arg: 8.1.5 + promzard: 0.3.0 + read: 1.0.7 + read-package-json: 4.1.2 + semver: 7.3.8 + validate-npm-package-license: 3.0.4 + validate-npm-package-name: 3.0.0 + dev: true + + /inquirer/7.3.3: + resolution: {integrity: sha512-JG3eIAj5V9CwcGvuOmoo6LB9kbAYT8HXffUl6memuszlwDC/qvFAJw49XJ5NROSFNPxp3iQg1GqkFhaY/CR0IA==} + engines: {node: '>=8.0.0'} + dependencies: + ansi-escapes: 4.3.2 + chalk: 4.1.2 + cli-cursor: 3.1.0 + cli-width: 3.0.0 + external-editor: 3.1.0 + figures: 3.2.0 + lodash: 4.17.21 + mute-stream: 0.0.8 + run-async: 2.4.1 + rxjs: 6.6.7 + string-width: 4.2.3 + strip-ansi: 6.0.1 + through: 2.3.8 + dev: true + + /internal-slot/1.0.3: + resolution: {integrity: sha512-O0DB1JC/sPyZl7cIo78n5dR7eUSwwpYPiXRhTzNxZVAMUuB8vlnRFyLxdrVToks6XPLVnFfbzaVd5WLjhgg+vA==} + engines: {node: '>= 0.4'} + dependencies: + get-intrinsic: 1.1.3 + has: 1.0.3 + side-channel: 1.0.4 + dev: true + + /ip/2.0.0: + resolution: {integrity: sha512-WKa+XuLG1A1R0UWhl2+1XQSi+fZWMsYKffMZTTYsiZaUD8k2yDAj5atimTUD2TZkyCkNEeYE5NhFZmupOGtjYQ==} + dev: true + + /is-arrayish/0.2.1: + resolution: {integrity: sha512-zz06S8t0ozoDXMG+ube26zeCTNXcKIPJZJi8hBrF4idCLms4CG9QtK7qBl1boi5ODzFpjswb5JPmHCbMpjaYzg==} + dev: true + + /is-bigint/1.0.4: + resolution: {integrity: sha512-zB9CruMamjym81i2JZ3UMn54PKGsQzsJeo6xvN3HJJ4CAsQNB6iRutp2To77OfCNuoxspsIhzaPoO1zyCEhFOg==} + dependencies: + has-bigints: 1.0.2 + dev: true + + /is-boolean-object/1.1.2: + resolution: {integrity: sha512-gDYaKHJmnj4aWxyj6YHyXVpdQawtVLHU5cb+eztPGczf6cjuTdwve5ZIEfgXqH4e57An1D1AKf8CZ3kYrQRqYA==} + engines: {node: '>= 0.4'} + dependencies: + call-bind: 1.0.2 + has-tostringtag: 1.0.0 + dev: true + + /is-callable/1.2.7: + resolution: {integrity: sha512-1BC0BVFhS/p0qtw6enp8e+8OD0UrK0oFLztSjNzhcKA3WDuJxxAPXzPuPtKkjEY9UUoEWlX/8fgKeu2S8i9JTA==} + engines: {node: '>= 0.4'} + dev: true + + /is-ci/2.0.0: + resolution: {integrity: sha512-YfJT7rkpQB0updsdHLGWrvhBJfcfzNNawYDNIyQXJz0IViGf75O8EBPKSdvw2rF+LGCsX4FZ8tcr3b19LcZq4w==} + hasBin: true + dependencies: + ci-info: 2.0.0 + dev: true + + /is-core-module/2.10.0: + resolution: {integrity: sha512-Erxj2n/LDAZ7H8WNJXd9tw38GYM3dv8rk8Zcs+jJuxYTW7sozH+SS8NtrSjVL1/vpLvWi1hxy96IzjJ3EHTJJg==} + dependencies: + has: 1.0.3 + dev: true + + /is-date-object/1.0.5: + resolution: {integrity: sha512-9YQaSxsAiSwcvS33MBk3wTCVnWK+HhF8VZR2jRxehM16QcVOdHqPn4VPHmRK4lSr38n9JriurInLcP90xsYNfQ==} + engines: {node: '>= 0.4'} + dependencies: + has-tostringtag: 1.0.0 + dev: true + + /is-extglob/2.1.1: + resolution: {integrity: sha512-SbKbANkN603Vi4jEZv49LeVJMn4yGwsbzZworEoyEiutsN3nJYdbO36zfhGJ6QEDpOZIFkDtnq5JRxmvl3jsoQ==} + engines: {node: '>=0.10.0'} + dev: true + + /is-fullwidth-code-point/1.0.0: + resolution: {integrity: sha512-1pqUqRjkhPJ9miNq9SwMfdvi6lBJcd6eFxvfaivQhaH3SgisfiuudvFntdKOmxuee/77l+FPjKrQjWvmPjWrRw==} + engines: {node: '>=0.10.0'} + dependencies: + number-is-nan: 1.0.1 + dev: true + + /is-fullwidth-code-point/3.0.0: + resolution: {integrity: sha512-zymm5+u+sCsSWyD9qNaejV3DFvhCKclKdizYaJUuHA83RLjb7nSuGnddCHGv0hk+KY7BMAlsWeK4Ueg6EV6XQg==} + engines: {node: '>=8'} + dev: true + + /is-glob/4.0.3: + resolution: {integrity: sha512-xelSayHH36ZgE7ZWhli7pW34hNbNl8Ojv5KVmkJD4hBdD3th8Tfk9vYasLM+mXWOZhFkgZfxhLSnrwRr4elSSg==} + engines: {node: '>=0.10.0'} + dependencies: + is-extglob: 2.1.1 + dev: true + + /is-installed-globally/0.4.0: + resolution: {integrity: sha512-iwGqO3J21aaSkC7jWnHP/difazwS7SFeIqxv6wEtLU8Y5KlzFTjyqcSIT0d8s4+dDhKytsk9PJZ2BkS5eZwQRQ==} + engines: {node: '>=10'} + dependencies: + global-dirs: 3.0.0 + is-path-inside: 3.0.3 + dev: true + + /is-lambda/1.0.1: + resolution: {integrity: sha512-z7CMFGNrENq5iFB9Bqo64Xk6Y9sg+epq1myIcdHaGnbMTYOxvzsEtdYqQUylB7LxfkvgrrjP32T6Ywciio9UIQ==} + dev: true + + /is-negative-zero/2.0.2: + resolution: {integrity: sha512-dqJvarLawXsFbNDeJW7zAz8ItJ9cd28YufuuFzh0G8pNHjJMnY08Dv7sYX2uF5UpQOwieAeOExEYAWWfu7ZZUA==} + engines: {node: '>= 0.4'} + dev: true + + /is-npm/5.0.0: + resolution: {integrity: sha512-WW/rQLOazUq+ST/bCAVBp/2oMERWLsR7OrKyt052dNDk4DHcDE0/7QSXITlmi+VBcV13DfIbysG3tZJm5RfdBA==} + engines: {node: '>=10'} + dev: true + + /is-number-object/1.0.7: + resolution: {integrity: sha512-k1U0IRzLMo7ZlYIfzRu23Oh6MiIFasgpb9X76eqfFZAqwH44UI4KTBvBYIZ1dSL9ZzChTB9ShHfLkR4pdW5krQ==} + engines: {node: '>= 0.4'} + dependencies: + has-tostringtag: 1.0.0 + dev: true + + /is-number/7.0.0: + resolution: {integrity: sha512-41Cifkg6e8TylSpdtTpeLVMqvSBEVzTttHvERD741+pnZ8ANv0004MRL43QKPDlK9cGvNp6NZWZUBlbGXYxxng==} + engines: {node: '>=0.12.0'} + dev: true + + /is-obj/2.0.0: + resolution: {integrity: sha512-drqDG3cbczxxEJRoOXcOjtdp1J/lyp1mNn0xaznRs8+muBhgQcrnbspox5X5fOw0HnMnbfDzvnEMEtqDEJEo8w==} + engines: {node: '>=8'} + dev: true + + /is-path-inside/3.0.3: + resolution: {integrity: sha512-Fd4gABb+ycGAmKou8eMftCupSir5lRxqf4aD/vd0cD2qc4HL07OjCeuHMr8Ro4CoMaeCKDB0/ECBOVWjTwUvPQ==} + engines: {node: '>=8'} + dev: true + + /is-plain-obj/1.1.0: + resolution: {integrity: sha512-yvkRyxmFKEOQ4pNXCmJG5AEQNlXJS5LaONXo5/cLdTZdWvsZ1ioJEonLGAosKlMWE8lwUy/bJzMjcw8az73+Fg==} + engines: {node: '>=0.10.0'} + dev: true + + /is-plain-obj/2.1.0: + resolution: {integrity: sha512-YWnfyRwxL/+SsrWYfOpUtz5b3YD+nyfkHvjbcanzk8zgyO4ASD67uVMRt8k5bM4lLMDnXfriRhOpemw+NfT1eA==} + engines: {node: '>=8'} + dev: true + + /is-plain-object/2.0.4: + resolution: {integrity: sha512-h5PpgXkWitc38BBMYawTYMWJHFZJVnBquFE57xFpjB8pJFiF6gZ+bU+WyI/yqXiFR5mdLsgYNaPe8uao6Uv9Og==} + engines: {node: '>=0.10.0'} + dependencies: + isobject: 3.0.1 + dev: true + + /is-plain-object/5.0.0: + resolution: {integrity: sha512-VRSzKkbMm5jMDoKLbltAkFQ5Qr7VDiTFGXxYFXXowVj387GeGNOCsOH6Msy00SGZ3Fp84b1Naa1psqgcCIEP5Q==} + engines: {node: '>=0.10.0'} + dev: true + + /is-regex/1.1.4: + resolution: {integrity: sha512-kvRdxDsxZjhzUX07ZnLydzS1TU/TJlTUHHY4YLL87e37oUA49DfkLqgy+VjFocowy29cKvcSiu+kIv728jTTVg==} + engines: {node: '>= 0.4'} + dependencies: + call-bind: 1.0.2 + has-tostringtag: 1.0.0 + dev: true + + /is-shared-array-buffer/1.0.2: + resolution: {integrity: sha512-sqN2UDu1/0y6uvXyStCOzyhAjCSlHceFoMKJW8W9EU9cvic/QdsZ0kEU93HEy3IUEFZIiH/3w+AH/UQbPHNdhA==} + dependencies: + call-bind: 1.0.2 + dev: true + + /is-ssh/1.4.0: + resolution: {integrity: sha512-x7+VxdxOdlV3CYpjvRLBv5Lo9OJerlYanjwFrPR9fuGPjCiNiCzFgAWpiLAohSbsnH4ZAys3SBh+hq5rJosxUQ==} + dependencies: + protocols: 2.0.1 + dev: true + + /is-stream/2.0.1: + resolution: {integrity: sha512-hFoiJiTl63nn+kstHGBtewWSKnQLpyb155KHheA1l39uvtO9nWIop1p3udqPcUd/xbF1VLMO4n7OI6p7RbngDg==} + engines: {node: '>=8'} + dev: true + + /is-string/1.0.7: + resolution: {integrity: sha512-tE2UXzivje6ofPW7l23cjDOMa09gb7xlAqG6jG5ej6uPV32TlWP3NKPigtaGeHNu9fohccRYvIiZMfOOnOYUtg==} + engines: {node: '>= 0.4'} + dependencies: + has-tostringtag: 1.0.0 + dev: true + + /is-symbol/1.0.4: + resolution: {integrity: sha512-C/CPBqKWnvdcxqIARxyOh4v1UUEOCHpgDa0WYgpKDFMszcrPcffg5uhwSgPCLD2WWxmq6isisz87tzT01tuGhg==} + engines: {node: '>= 0.4'} + dependencies: + has-symbols: 1.0.3 + dev: true + + /is-text-path/1.0.1: + resolution: {integrity: sha512-xFuJpne9oFz5qDaodwmmG08e3CawH/2ZV8Qqza1Ko7Sk8POWbkRdwIoAWVhqvq0XeUzANEhKo2n0IXUGBm7A/w==} + engines: {node: '>=0.10.0'} + dependencies: + text-extensions: 1.9.0 + dev: true + + /is-typedarray/1.0.0: + resolution: {integrity: sha512-cyA56iCMHAh5CdzjJIa4aohJyeO1YbwLi3Jc35MmRU6poroFjIGZzUzupGiRPOjgHg9TLu43xbpwXk523fMxKA==} + dev: true + + /is-weakref/1.0.2: + resolution: {integrity: sha512-qctsuLZmIQ0+vSSMfoVvyFe2+GSEvnmZ2ezTup1SBse9+twCCeial6EEi3Nc2KFcf6+qz2FBPnjXsk8xhKSaPQ==} + dependencies: + call-bind: 1.0.2 + dev: true + + /is-windows/1.0.2: + resolution: {integrity: sha512-eXK1UInq2bPmjyX6e3VHIzMLobc4J94i4AWn+Hpq3OU5KkrRC96OAcR3PRJ/pGu6m8TRnBHP9dkXQVsT/COVIA==} + engines: {node: '>=0.10.0'} + dev: true + + /is-yarn-global/0.3.0: + resolution: {integrity: sha512-VjSeb/lHmkoyd8ryPVIKvOCn4D1koMqY+vqyjjUfc3xyKtP4dYOxM44sZrnqQSzSds3xyOrUTLTC9LVCVgLngw==} + dev: true + + /isarray/1.0.0: + resolution: {integrity: sha512-VLghIWNM6ELQzo7zwmcg0NmTVyWKYjvIeM83yjp0wRDTmUnrM678fQbcKBo6n2CJEF0szoG//ytg+TKla89ALQ==} + dev: true + + /isexe/2.0.0: + resolution: {integrity: sha512-RHxMLp9lnKHGHRng9QFhRCMbYAcVpn69smSGcq3f36xjgVVWThj4qqLbTLlq7Ssj8B+fIQ1EuCEGI2lKsyQeIw==} + dev: true + + /isobject/3.0.1: + resolution: {integrity: sha512-WhB9zCku7EGTj/HQQRz5aUQEUeoQZH2bWcltRErOpymJ4boYE6wL9Tbr23krRPSZ+C5zqNSrSw+Cc7sZZ4b7vg==} + engines: {node: '>=0.10.0'} + dev: true + + /isstream/0.1.2: + resolution: {integrity: sha512-Yljz7ffyPbrLpLngrMtZ7NduUgVvi6wG9RJ9IUcyCd59YQ911PBJphODUcbOVbqYfxe1wuYf/LJ8PauMRwsM/g==} + dev: true + + /istanbul-lib-coverage/3.2.0: + resolution: {integrity: sha512-eOeJ5BHCmHYvQK7xt9GkdHuzuCGS1Y6g9Gvnx3Ym33fz/HpLRYxiS0wHNr+m/MBC8B647Xt608vCDEvhl9c6Mw==} + engines: {node: '>=8'} + dev: true + + /istanbul-lib-hook/3.0.0: + resolution: {integrity: sha512-Pt/uge1Q9s+5VAZ+pCo16TYMWPBIl+oaNIjgLQxcX0itS6ueeaA+pEfThZpH8WxhFgCiEb8sAJY6MdUKgiIWaQ==} + engines: {node: '>=8'} + dependencies: + append-transform: 2.0.0 + dev: true + + /istanbul-lib-instrument/4.0.3: + resolution: {integrity: sha512-BXgQl9kf4WTCPCCpmFGoJkz/+uhvm7h7PFKUYxh7qarQd3ER33vHG//qaE8eN25l07YqZPpHXU9I09l/RD5aGQ==} + engines: {node: '>=8'} + dependencies: + '@babel/core': 7.19.3 + '@istanbuljs/schema': 0.1.3 + istanbul-lib-coverage: 3.2.0 + semver: 6.3.0 + transitivePeerDependencies: + - supports-color + dev: true + + /istanbul-lib-processinfo/2.0.3: + resolution: {integrity: sha512-NkwHbo3E00oybX6NGJi6ar0B29vxyvNwoC7eJ4G4Yq28UfY758Hgn/heV8VRFhevPED4LXfFz0DQ8z/0kw9zMg==} + engines: {node: '>=8'} + dependencies: + archy: 1.0.0 + cross-spawn: 7.0.3 + istanbul-lib-coverage: 3.2.0 + p-map: 3.0.0 + rimraf: 3.0.2 + uuid: 8.3.2 + dev: true + + /istanbul-lib-report/3.0.0: + resolution: {integrity: sha512-wcdi+uAKzfiGT2abPpKZ0hSU1rGQjUQnLvtY5MpQ7QCTahD3VODhcu4wcfY1YtkGaDD5yuydOLINXsfbus9ROw==} + engines: {node: '>=8'} + dependencies: + istanbul-lib-coverage: 3.2.0 + make-dir: 3.1.0 + supports-color: 7.2.0 + dev: true + + /istanbul-lib-source-maps/4.0.1: + resolution: {integrity: sha512-n3s8EwkdFIJCG3BPKBYvskgXGoy88ARzvegkitk60NxRdwltLOTaH7CUiMRXvwYorl0Q712iEjcWB+fK/MrWVw==} + engines: {node: '>=10'} + dependencies: + debug: 4.3.4 + istanbul-lib-coverage: 3.2.0 + source-map: 0.6.1 + transitivePeerDependencies: + - supports-color + dev: true + + /istanbul-reports/3.1.5: + resolution: {integrity: sha512-nUsEMa9pBt/NOHqbcbeJEgqIlY/K7rVWUX6Lql2orY5e9roQOthbR3vtY4zzf2orPELg80fnxxk9zUyPlgwD1w==} + engines: {node: '>=8'} + dependencies: + html-escaper: 2.0.2 + istanbul-lib-report: 3.0.0 + dev: true + + /jju/1.4.0: + resolution: {integrity: sha512-8wb9Yw966OSxApiCt0K3yNJL8pnNeIv+OEq2YMidz4FKP6nonSRoOXc80iXY4JaN2FC11B9qsNmDsm+ZOfMROA==} + dev: true + + /js-sdsl/4.1.5: + resolution: {integrity: sha512-08bOAKweV2NUC1wqTtf3qZlnpOX/R2DU9ikpjOHs0H+ibQv3zpncVQg6um4uYtRtrwIX8M4Nh3ytK4HGlYAq7Q==} + dev: true + + /js-tokens/4.0.0: + resolution: {integrity: sha512-RdJUflcE3cUzKiMqQgsCu06FPu9UdIJO0beYbPhHN4k6apgJtifcoCtT9bcxOpYBtpD2kCM6Sbzg4CausW/PKQ==} + dev: true + + /js-yaml/3.14.1: + resolution: {integrity: sha512-okMH7OXXJ7YrN9Ok3/SXrnu4iX9yOk+25nqX4imS2npuvTYDmo/QEZoqwZkYaIDk3jVvBOTOIEgEhaLOynBS9g==} + hasBin: true + dependencies: + argparse: 1.0.10 + esprima: 4.0.1 + dev: true + + /js-yaml/4.1.0: + resolution: {integrity: sha512-wpxZs9NoxZaJESJGIZTyDEaYpl0FKSA+FB9aJiyemKhMwkxQg63h4T1KJgUGHpTqPDNRcmmYLugrRjJlBtWvRA==} + hasBin: true + dependencies: + argparse: 2.0.1 + dev: true + + /jsbn/0.1.1: + resolution: {integrity: sha512-UVU9dibq2JcFWxQPA6KCqj5O42VOmAY3zQUfEKxU0KpTGXwNoCjkX1e13eHNvw/xPynt6pU0rZ1htjWTNTSXsg==} + dev: true + + /jsesc/2.5.2: + resolution: {integrity: sha512-OYu7XEzjkCQ3C5Ps3QIZsQfNpqoJyZZA99wd9aWd05NCtC5pWOkShK2mkL6HXQR6/Cy2lbNdPlZBpuQHXE63gA==} + engines: {node: '>=4'} + hasBin: true + dev: true + + /json-buffer/3.0.0: + resolution: {integrity: sha512-CuUqjv0FUZIdXkHPI8MezCnFCdaTAacej1TZYulLoAg1h/PhwkdXFN4V/gzY4g+fMBCOV2xF+rp7t2XD2ns/NQ==} + dev: true + + /json-parse-better-errors/1.0.2: + resolution: {integrity: sha512-mrqyZKfX5EhL7hvqcV6WG1yYjnjeuYDzDhhcAAUrq8Po85NBQBJP+ZDUT75qZQ98IkUoBqdkExkukOU7Ts2wrw==} + dev: true + + /json-parse-even-better-errors/2.3.1: + resolution: {integrity: sha512-xyFwyhro/JEof6Ghe2iz2NcXoj2sloNsWr/XsERDK/oiPCfaNhl5ONfp+jQdAZRQQ0IJWNzH9zIZF7li91kh2w==} + dev: true + + /json-parse-helpfulerror/1.0.3: + resolution: {integrity: sha512-XgP0FGR77+QhUxjXkwOMkC94k3WtqEBfcnjWqhRd82qTat4SWKRE+9kUnynz/shm3I4ea2+qISvTIeGTNU7kJg==} + dependencies: + jju: 1.4.0 + dev: true + + /json-schema-traverse/0.4.1: + resolution: {integrity: sha512-xbbCH5dCYU5T8LcEhhuh7HJ88HXuW3qsI3Y0zOZFKfZEHcpWiHU/Jxzk629Brsab/mMiHQti9wMP+845RPe3Vg==} + dev: true + + /json-schema/0.4.0: + resolution: {integrity: sha512-es94M3nTIfsEPisRafak+HDLfHXnKBhV3vU5eqPcS3flIWqcxJWgXHXiey3YrpaNsanY5ei1VoYEbOzijuq9BA==} + dev: true + + /json-stable-stringify-without-jsonify/1.0.1: + resolution: {integrity: sha512-Bdboy+l7tA3OGW6FjyFHWkP5LuByj1Tk33Ljyq0axyzdk9//JSi2u3fP1QSmd1KNwq6VOKYGlAu87CisVir6Pw==} + dev: true + + /json-stringify-safe/5.0.1: + resolution: {integrity: sha512-ZClg6AaYvamvYEE82d3Iyd3vSSIjQ+odgjaTzRuO3s7toCdFKczob2i0zCh7JE8kWn17yvAWhUVxvqGwUalsRA==} + dev: true + + /json5/1.0.1: + resolution: {integrity: sha512-aKS4WQjPenRxiQsC93MNfjx+nbF4PAdYzmd/1JIj8HYzqfbu86beTuNgXDzPknWk0n0uARlyewZo4s++ES36Ow==} + hasBin: true + dependencies: + minimist: 1.2.7 + dev: true + + /json5/2.2.1: + resolution: {integrity: sha512-1hqLFMSrGHRHxav9q9gNjJ5EXznIxGVO09xQRrwplcS8qs28pZ8s8hupZAmqDwZUmVZ2Qb2jnyPOWcDH8m8dlA==} + engines: {node: '>=6'} + hasBin: true + dev: true + + /jsonfile/6.1.0: + resolution: {integrity: sha512-5dgndWOriYSm5cnYaJNhalLNDKOqFwyDB/rr1E9ZsGciGvKPs8R2xYGCacuf3z6K1YKDz182fd+fY3cn3pMqXQ==} + dependencies: + universalify: 2.0.0 + optionalDependencies: + graceful-fs: 4.2.10 + dev: true + + /jsonlines/0.1.1: + resolution: {integrity: sha512-ekDrAGso79Cvf+dtm+mL8OBI2bmAOt3gssYs833De/C9NmIpWDWyUO4zPgB5x2/OhY366dkhgfPMYfwZF7yOZA==} + dev: true + + /jsonparse/1.3.1: + resolution: {integrity: sha512-POQXvpdL69+CluYsillJ7SUhKvytYjW9vG/GKpnf+xP8UWgYEM/RaMzHHofbALDiKbbP1W8UEYmgGl39WkPZsg==} + engines: {'0': node >= 0.2.0} + dev: true + + /jsprim/1.4.2: + resolution: {integrity: sha512-P2bSOMAc/ciLz6DzgjVlGJP9+BrJWu5UDGK70C2iweC5QBIeFf0ZXRvGjEj2uYgrY2MkAAhsSWHDWlFtEroZWw==} + engines: {node: '>=0.6.0'} + dependencies: + assert-plus: 1.0.0 + extsprintf: 1.3.0 + json-schema: 0.4.0 + verror: 1.10.0 + dev: true + + /keyv/3.1.0: + resolution: {integrity: sha512-9ykJ/46SN/9KPM/sichzQ7OvXyGDYKGTaDlKMGCAlg2UK8KRy4jb0d8sFc+0Tt0YYnThq8X2RZgCg74RPxgcVA==} + dependencies: + json-buffer: 3.0.0 + dev: true + + /kind-of/6.0.3: + resolution: {integrity: sha512-dcS1ul+9tmeD95T+x28/ehLgd9mENa3LsvDTtzm3vyBEO7RPptvAD+t44WVXaUjTBRcrpFeFlC8WCruUR456hw==} + engines: {node: '>=0.10.0'} + dev: true + + /kleur/3.0.3: + resolution: {integrity: sha512-eTIzlVOSUR+JxdDFepEYcBMtZ9Qqdef+rnzWdRZuMbOywu5tO2w2N7rqjoANZ5k9vywhL6Br1VRjUIgTQx4E8w==} + engines: {node: '>=6'} + dev: true + + /latest-version/5.1.0: + resolution: {integrity: sha512-weT+r0kTkRQdCdYCNtkMwWXQTMEswKrFBkm4ckQOMVhhqhIMI1UT2hMj+1iigIhgSZm5gTmrRXBNoGUgaTY1xA==} + engines: {node: '>=8'} + dependencies: + package-json: 6.5.0 + dev: true + + /lerna/4.0.0: + resolution: {integrity: sha512-DD/i1znurfOmNJb0OBw66NmNqiM8kF6uIrzrJ0wGE3VNdzeOhz9ziWLYiRaZDGGwgbcjOo6eIfcx9O5Qynz+kg==} + engines: {node: '>= 10.18.0'} + hasBin: true + dependencies: + '@lerna/add': 4.0.0 + '@lerna/bootstrap': 4.0.0 + '@lerna/changed': 4.0.0 + '@lerna/clean': 4.0.0 + '@lerna/cli': 4.0.0 + '@lerna/create': 4.0.0 + '@lerna/diff': 4.0.0 + '@lerna/exec': 4.0.0 + '@lerna/import': 4.0.0 + '@lerna/info': 4.0.0 + '@lerna/init': 4.0.0 + '@lerna/link': 4.0.0 + '@lerna/list': 4.0.0 + '@lerna/publish': 4.0.0 + '@lerna/run': 4.0.0 + '@lerna/version': 4.0.0 + import-local: 3.1.0 + npmlog: 4.1.2 + transitivePeerDependencies: + - bluebird + - encoding + - supports-color + dev: true + + /levn/0.4.1: + resolution: {integrity: sha512-+bT2uH4E5LGE7h/n3evcS/sQlJXCpIp6ym8OWJ5eV6+67Dsql/LaaT7qJBAt2rzfoa/5QBGBhxDix1dMt2kQKQ==} + engines: {node: '>= 0.8.0'} + dependencies: + prelude-ls: 1.2.1 + type-check: 0.4.0 + dev: true + + /libnpmaccess/4.0.3: + resolution: {integrity: sha512-sPeTSNImksm8O2b6/pf3ikv4N567ERYEpeKRPSmqlNt1dTZbvgpJIzg5vAhXHpw2ISBsELFRelk0jEahj1c6nQ==} + engines: {node: '>=10'} + dependencies: + aproba: 2.0.0 + minipass: 3.3.4 + npm-package-arg: 8.1.5 + npm-registry-fetch: 11.0.0 + transitivePeerDependencies: + - bluebird + - supports-color + dev: true + + /libnpmconfig/1.2.1: + resolution: {integrity: sha512-9esX8rTQAHqarx6qeZqmGQKBNZR5OIbl/Ayr0qQDy3oXja2iFVQQI81R6GZ2a02bSNZ9p3YOGX1O6HHCb1X7kA==} + deprecated: This module is not used anymore. npm config is parsed by npm itself and by @npmcli/config + dependencies: + figgy-pudding: 3.5.2 + find-up: 3.0.0 + ini: 1.3.8 + dev: true + + /libnpmpublish/4.0.2: + resolution: {integrity: sha512-+AD7A2zbVeGRCFI2aO//oUmapCwy7GHqPXFJh3qpToSRNU+tXKJ2YFUgjt04LPPAf2dlEH95s6EhIHM1J7bmOw==} + engines: {node: '>=10'} + dependencies: + normalize-package-data: 3.0.3 + npm-package-arg: 8.1.5 + npm-registry-fetch: 11.0.0 + semver: 7.3.8 + ssri: 8.0.1 + transitivePeerDependencies: + - bluebird + - supports-color + dev: true + + /lines-and-columns/1.2.4: + resolution: {integrity: sha512-7ylylesZQ/PV29jhEDl3Ufjo6ZX7gCqJr5F7PKrqc93v7fzSymt1BpwEU8nAUXs8qzzvqhbjhK5QZg6Mt/HkBg==} + dev: true + + /load-json-file/4.0.0: + resolution: {integrity: sha512-Kx8hMakjX03tiGTLAIdJ+lL0htKnXjEZN6hk/tozf/WOuYGdZBJrZ+rCJRbVCugsjB3jMLn9746NsQIf5VjBMw==} + engines: {node: '>=4'} + dependencies: + graceful-fs: 4.2.10 + parse-json: 4.0.0 + pify: 3.0.0 + strip-bom: 3.0.0 + dev: true + + /load-json-file/6.2.0: + resolution: {integrity: sha512-gUD/epcRms75Cw8RT1pUdHugZYM5ce64ucs2GEISABwkRsOQr0q2wm/MV2TKThycIe5e0ytRweW2RZxclogCdQ==} + engines: {node: '>=8'} + dependencies: + graceful-fs: 4.2.10 + parse-json: 5.2.0 + strip-bom: 4.0.0 + type-fest: 0.6.0 + dev: true + + /locate-path/2.0.0: + resolution: {integrity: sha512-NCI2kiDkyR7VeEKm27Kda/iQHyKJe1Bu0FlTbYp3CqJu+9IFe9bLyAjMxf5ZDDbEg+iMPzB5zYyUTSm8wVTKmA==} + engines: {node: '>=4'} + dependencies: + p-locate: 2.0.0 + path-exists: 3.0.0 + dev: true + + /locate-path/3.0.0: + resolution: {integrity: sha512-7AO748wWnIhNqAuaty2ZWHkQHRSNfPVIsPIfwEOWO22AmaoVrWavlOcMR5nzTLNYvp36X220/maaRsrec1G65A==} + engines: {node: '>=6'} + dependencies: + p-locate: 3.0.0 + path-exists: 3.0.0 + dev: true + + /locate-path/5.0.0: + resolution: {integrity: sha512-t7hw9pI+WvuwNJXwk5zVHpyhIqzg2qTlklJOf0mVxGSbe3Fp2VieZcduNYjaLDoy6p9uGpQEGWG87WpMKlNq8g==} + engines: {node: '>=8'} + dependencies: + p-locate: 4.1.0 + dev: true + + /locate-path/6.0.0: + resolution: {integrity: sha512-iPZK6eYjbxRu3uB4/WZ3EsEIMJFMqAoopl3R+zuq0UjcAm/MO6KCweDgPfP3elTztoKP3KtnVHxTn2NHBSDVUw==} + engines: {node: '>=10'} + dependencies: + p-locate: 5.0.0 + dev: true + + /lodash._reinterpolate/3.0.0: + resolution: {integrity: sha512-xYHt68QRoYGjeeM/XOE1uJtvXQAgvszfBhjV4yvsQH0u2i9I6cI6c6/eG4Hh3UAOVn0y/xAXwmTzEay49Q//HA==} + dev: true + + /lodash.flattendeep/4.4.0: + resolution: {integrity: sha512-uHaJFihxmJcEX3kT4I23ABqKKalJ/zDrDg0lsFtc1h+3uw49SIJ5beyhx5ExVRti3AvKoOJngIj7xz3oylPdWQ==} + dev: true + + /lodash.ismatch/4.4.0: + resolution: {integrity: sha512-fPMfXjGQEV9Xsq/8MTSgUf255gawYRbjwMyDbcvDhXgV7enSZA0hynz6vMPnpAb5iONEzBHBPsT+0zes5Z301g==} + dev: true + + /lodash.merge/4.6.2: + resolution: {integrity: sha512-0KpjqXRVvrYyCsX1swR/XTK0va6VQkQM6MNo7PqW77ByjAhoARA8EfrP1N4+KlKj8YS0ZUCtRT/YUuhyYDujIQ==} + dev: true + + /lodash.template/4.5.0: + resolution: {integrity: sha512-84vYFxIkmidUiFxidA/KjjH9pAycqW+h980j7Fuz5qxRtO9pgB7MDFTdys1N7A5mcucRiDyEq4fusljItR1T/A==} + dependencies: + lodash._reinterpolate: 3.0.0 + lodash.templatesettings: 4.2.0 + dev: true + + /lodash.templatesettings/4.2.0: + resolution: {integrity: sha512-stgLz+i3Aa9mZgnjr/O+v9ruKZsPsndy7qPZOchbqk2cnTU1ZaldKK+v7m54WoKIyxiuMZTKT2H81F8BeAc3ZQ==} + dependencies: + lodash._reinterpolate: 3.0.0 + dev: true + + /lodash/4.17.21: + resolution: {integrity: sha512-v2kDEe57lecTulaDIuNTPy3Ry4gLGJ6Z1O3vE1krgXZNrsQ+LFTGHVxVjcXPs17LhbZVGedAJv8XZ1tvj5FvSg==} + dev: true + + /lowercase-keys/1.0.1: + resolution: {integrity: sha512-G2Lj61tXDnVFFOi8VZds+SoQjtQC3dgokKdDG2mTm1tx4m50NUHBOZSBwQQHyy0V12A0JTG4icfZQH+xPyh8VA==} + engines: {node: '>=0.10.0'} + dev: true + + /lowercase-keys/2.0.0: + resolution: {integrity: sha512-tqNXrS78oMOE73NMxK4EMLQsQowWf8jKooH9g7xPavRT706R6bkQJ6DY2Te7QukaZsulxa30wQ7bk0pm4XiHmA==} + engines: {node: '>=8'} + dev: true + + /lru-cache/6.0.0: + resolution: {integrity: sha512-Jo6dJ04CmSjuznwJSS3pUeWmd/H0ffTlkXXgwZi+eq1UCmqQwCh+eLsYOYCwY991i2Fah4h1BEMCx4qThGbsiA==} + engines: {node: '>=10'} + dependencies: + yallist: 4.0.0 + dev: true + + /lru-cache/7.14.0: + resolution: {integrity: sha512-EIRtP1GrSJny0dqb50QXRUNBxHJhcpxHC++M5tD7RYbvLLn5KVWKsbyswSSqDuU15UFi3bgTQIY8nhDMeF6aDQ==} + engines: {node: '>=12'} + dev: true + + /make-dir/2.1.0: + resolution: {integrity: sha512-LS9X+dc8KLxXCb8dni79fLIIUA5VyZoyjSMCwTluaXA0o27cCK0bhXkpgw+sTXVpPy/lSO57ilRixqk0vDmtRA==} + engines: {node: '>=6'} + dependencies: + pify: 4.0.1 + semver: 5.7.1 + dev: true + + /make-dir/3.1.0: + resolution: {integrity: sha512-g3FeP20LNwhALb/6Cz6Dd4F2ngze0jz7tbzrD2wAV+o9FeNHe4rL+yK2md0J/fiSf1sa1ADhXqi5+oVwOM/eGw==} + engines: {node: '>=8'} + dependencies: + semver: 6.3.0 + dev: true + + /make-fetch-happen/10.2.1: + resolution: {integrity: sha512-NgOPbRiaQM10DYXvN3/hhGVI2M5MtITFryzBGxHM5p4wnFxsVCbxkrBrDsk+EZ5OB4jEOT7AjDxtdF+KVEFT7w==} + engines: {node: ^12.13.0 || ^14.15.0 || >=16.0.0} + dependencies: + agentkeepalive: 4.2.1 + cacache: 16.1.3 + http-cache-semantics: 4.1.0 + http-proxy-agent: 5.0.0 + https-proxy-agent: 5.0.1 + is-lambda: 1.0.1 + lru-cache: 7.14.0 + minipass: 3.3.4 + minipass-collect: 1.0.2 + minipass-fetch: 2.1.2 + minipass-flush: 1.0.5 + minipass-pipeline: 1.2.4 + negotiator: 0.6.3 + promise-retry: 2.0.1 + socks-proxy-agent: 7.0.0 + ssri: 9.0.1 + transitivePeerDependencies: + - bluebird + - supports-color + dev: true + + /make-fetch-happen/8.0.14: + resolution: {integrity: sha512-EsS89h6l4vbfJEtBZnENTOFk8mCRpY5ru36Xe5bcX1KYIli2mkSHqoFsp5O1wMDvTJJzxe/4THpCTtygjeeGWQ==} + engines: {node: '>= 10'} + dependencies: + agentkeepalive: 4.2.1 + cacache: 15.3.0 + http-cache-semantics: 4.1.0 + http-proxy-agent: 4.0.1 + https-proxy-agent: 5.0.1 + is-lambda: 1.0.1 + lru-cache: 6.0.0 + minipass: 3.3.4 + minipass-collect: 1.0.2 + minipass-fetch: 1.4.1 + minipass-flush: 1.0.5 + minipass-pipeline: 1.2.4 + promise-retry: 2.0.1 + socks-proxy-agent: 5.0.1 + ssri: 8.0.1 + transitivePeerDependencies: + - bluebird + - supports-color + dev: true + + /make-fetch-happen/9.1.0: + resolution: {integrity: sha512-+zopwDy7DNknmwPQplem5lAZX/eCOzSvSNNcSKm5eVwTkOBzoktEfXsa9L23J/GIRhxRsaxzkPEhrJEpE2F4Gg==} + engines: {node: '>= 10'} + dependencies: + agentkeepalive: 4.2.1 + cacache: 15.3.0 + http-cache-semantics: 4.1.0 + http-proxy-agent: 4.0.1 + https-proxy-agent: 5.0.1 + is-lambda: 1.0.1 + lru-cache: 6.0.0 + minipass: 3.3.4 + minipass-collect: 1.0.2 + minipass-fetch: 1.4.1 + minipass-flush: 1.0.5 + minipass-pipeline: 1.2.4 + negotiator: 0.6.3 + promise-retry: 2.0.1 + socks-proxy-agent: 6.2.1 + ssri: 8.0.1 + transitivePeerDependencies: + - bluebird + - supports-color + dev: true + + /map-obj/1.0.1: + resolution: {integrity: sha512-7N/q3lyZ+LVCp7PzuxrJr4KMbBE2hW7BT7YNia330OFxIf4d3r5zVpicP2650l7CPN6RM9zOJRl3NGpqSiw3Eg==} + engines: {node: '>=0.10.0'} + dev: true + + /map-obj/4.3.0: + resolution: {integrity: sha512-hdN1wVrZbb29eBGiGjJbeP8JbKjq1urkHJ/LIP/NY48MZ1QVXUsQBV1G1zvYFHn1XE06cwjBsOI2K3Ulnj1YXQ==} + engines: {node: '>=8'} + dev: true + + /meow/8.1.2: + resolution: {integrity: sha512-r85E3NdZ+mpYk1C6RjPFEMSE+s1iZMuHtsHAqY0DT3jZczl0diWUZ8g6oU7h0M9cD2EL+PzaYghhCLzR0ZNn5Q==} + engines: {node: '>=10'} + dependencies: + '@types/minimist': 1.2.2 + camelcase-keys: 6.2.2 + decamelize-keys: 1.1.0 + hard-rejection: 2.1.0 + minimist-options: 4.1.0 + normalize-package-data: 3.0.3 + read-pkg-up: 7.0.1 + redent: 3.0.0 + trim-newlines: 3.0.1 + type-fest: 0.18.1 + yargs-parser: 20.2.9 + dev: true + + /merge-stream/2.0.0: + resolution: {integrity: sha512-abv/qOcuPfk3URPfDzmZU1LKmuw8kT+0nIHvKrKgFrwifol/doWcdA4ZqsWQ8ENrFKkd67Mfpo/LovbIUsbt3w==} + dev: true + + /merge2/1.4.1: + resolution: {integrity: sha512-8q7VEgMJW4J8tcfVPy8g09NcQwZdbwFEqhe/WZkoIzjn/3TGDwtOCYtXGxA3O8tPzpczCCDgv+P2P5y00ZJOOg==} + engines: {node: '>= 8'} + dev: true + + /micromatch/4.0.5: + resolution: {integrity: sha512-DMy+ERcEW2q8Z2Po+WNXuw3c5YaUSFjAO5GsJqfEl7UjvtIuFKO6ZrKvcItdy98dwFI2N1tg3zNIdKaQT+aNdA==} + engines: {node: '>=8.6'} + dependencies: + braces: 3.0.2 + picomatch: 2.3.1 + dev: true + + /mime-db/1.52.0: + resolution: {integrity: sha512-sPU4uV7dYlvtWJxwwxHD0PuihVNiE7TyAbQ5SWxDCB9mUYvOgroQOwYQQOKPJ8CIbE+1ETVlOoK1UC2nU3gYvg==} + engines: {node: '>= 0.6'} + dev: true + + /mime-types/2.1.35: + resolution: {integrity: sha512-ZDY+bPm5zTTF+YpCrAU9nK0UgICYPT0QtT1NZWFv4s++TNkcgVaT0g6+4R2uI4MjQjzysHB1zxuWL50hzaeXiw==} + engines: {node: '>= 0.6'} + dependencies: + mime-db: 1.52.0 + dev: true + + /mimic-fn/2.1.0: + resolution: {integrity: sha512-OqbOk5oEQeAZ8WXWydlu9HJjz9WVdEIvamMCcXmuqUYjTknH/sqsWvhQ3vgwKFRR1HpjvNBKQ37nbJgYzGqGcg==} + engines: {node: '>=6'} + dev: true + + /mimic-response/1.0.1: + resolution: {integrity: sha512-j5EctnkH7amfV/q5Hgmoal1g2QHFJRraOtmx0JpIqkxhBhI/lJSl1nMpQ45hVarwNETOoWEimndZ4QK0RHxuxQ==} + engines: {node: '>=4'} + dev: true + + /min-indent/1.0.1: + resolution: {integrity: sha512-I9jwMn07Sy/IwOj3zVkVik2JTvgpaykDZEigL6Rx6N9LbMywwUSMtxET+7lVoDLLd3O3IXwJwvuuns8UB/HeAg==} + engines: {node: '>=4'} + dev: true + + /minimatch/3.1.2: + resolution: {integrity: sha512-J7p63hRiAjw1NDEww1W7i37+ByIrOWO5XQQAzZ3VOcL0PNybwpfmV/N05zFAzwQ9USyEcX6t3UO+K5aqBQOIHw==} + dependencies: + brace-expansion: 1.1.11 + dev: true + + /minimatch/5.1.0: + resolution: {integrity: sha512-9TPBGGak4nHfGZsPBohm9AWg6NoT7QTCehS3BIJABslyZbzxfV78QM2Y6+i741OPZIafFAaiiEMh5OyIrJPgtg==} + engines: {node: '>=10'} + dependencies: + brace-expansion: 2.0.1 + dev: true + + /minimist-options/4.1.0: + resolution: {integrity: sha512-Q4r8ghd80yhO/0j1O3B2BjweX3fiHg9cdOwjJd2J76Q135c+NDxGCqdYKQ1SKBuFfgWbAUzBfvYjPUEeNgqN1A==} + engines: {node: '>= 6'} + dependencies: + arrify: 1.0.1 + is-plain-obj: 1.1.0 + kind-of: 6.0.3 + dev: true + + /minimist/1.2.7: + resolution: {integrity: sha512-bzfL1YUZsP41gmu/qjrEk0Q6i2ix/cVeAhbCbqH9u3zYutS1cLg00qhrD0M2MVdCcx4Sc0UpP2eBWo9rotpq6g==} + dev: true + + /minipass-collect/1.0.2: + resolution: {integrity: sha512-6T6lH0H8OG9kITm/Jm6tdooIbogG9e0tLgpY6mphXSm/A9u8Nq1ryBG+Qspiub9LjWlBPsPS3tWQ/Botq4FdxA==} + engines: {node: '>= 8'} + dependencies: + minipass: 3.3.4 + dev: true + + /minipass-fetch/1.4.1: + resolution: {integrity: sha512-CGH1eblLq26Y15+Azk7ey4xh0J/XfJfrCox5LDJiKqI2Q2iwOLOKrlmIaODiSQS8d18jalF6y2K2ePUm0CmShw==} + engines: {node: '>=8'} + dependencies: + minipass: 3.3.4 + minipass-sized: 1.0.3 + minizlib: 2.1.2 + optionalDependencies: + encoding: 0.1.13 + dev: true + + /minipass-fetch/2.1.2: + resolution: {integrity: sha512-LT49Zi2/WMROHYoqGgdlQIZh8mLPZmOrN2NdJjMXxYe4nkN6FUyuPuOAOedNJDrx0IRGg9+4guZewtp8hE6TxA==} + engines: {node: ^12.13.0 || ^14.15.0 || >=16.0.0} + dependencies: + minipass: 3.3.4 + minipass-sized: 1.0.3 + minizlib: 2.1.2 + optionalDependencies: + encoding: 0.1.13 + dev: true + + /minipass-flush/1.0.5: + resolution: {integrity: sha512-JmQSYYpPUqX5Jyn1mXaRwOda1uQ8HP5KAT/oDSLCzt1BYRhQU0/hDtsB1ufZfEEzMZ9aAVmsBw8+FWsIXlClWw==} + engines: {node: '>= 8'} + dependencies: + minipass: 3.3.4 + dev: true + + /minipass-json-stream/1.0.1: + resolution: {integrity: sha512-ODqY18UZt/I8k+b7rl2AENgbWE8IDYam+undIJONvigAz8KR5GWblsFTEfQs0WODsjbSXWlm+JHEv8Gr6Tfdbg==} + dependencies: + jsonparse: 1.3.1 + minipass: 3.3.4 + dev: true + + /minipass-pipeline/1.2.4: + resolution: {integrity: sha512-xuIq7cIOt09RPRJ19gdi4b+RiNvDFYe5JH+ggNvBqGqpQXcru3PcRmOZuHBKWK1Txf9+cQ+HMVN4d6z46LZP7A==} + engines: {node: '>=8'} + dependencies: + minipass: 3.3.4 + dev: true + + /minipass-sized/1.0.3: + resolution: {integrity: sha512-MbkQQ2CTiBMlA2Dm/5cY+9SWFEN8pzzOXi6rlM5Xxq0Yqbda5ZQy9sU75a673FE9ZK0Zsbr6Y5iP6u9nktfg2g==} + engines: {node: '>=8'} + dependencies: + minipass: 3.3.4 + dev: true + + /minipass/2.9.0: + resolution: {integrity: sha512-wxfUjg9WebH+CUDX/CdbRlh5SmfZiy/hpkxaRI16Y9W56Pa75sWgd/rvFilSgrauD9NyFymP/+JFV3KwzIsJeg==} + dependencies: + safe-buffer: 5.2.1 + yallist: 3.1.1 + dev: true + + /minipass/3.3.4: + resolution: {integrity: sha512-I9WPbWHCGu8W+6k1ZiGpPu0GkoKBeorkfKNuAFBNS1HNFJvke82sxvI5bzcCNpWPorkOO5QQ+zomzzwRxejXiw==} + engines: {node: '>=8'} + dependencies: + yallist: 4.0.0 + dev: true + + /minizlib/1.3.3: + resolution: {integrity: sha512-6ZYMOEnmVsdCeTJVE0W9ZD+pVnE8h9Hma/iOwwRDsdQoePpoX56/8B6z3P9VNwppJuBKNRuFDRNRqRWexT9G9Q==} + dependencies: + minipass: 2.9.0 + dev: true + + /minizlib/2.1.2: + resolution: {integrity: sha512-bAxsR8BVfj60DWXHE3u30oHzfl4G7khkSuPW+qvpd7jFRHm7dLxOjUk1EHACJ/hxLY8phGJ0YhYHZo7jil7Qdg==} + engines: {node: '>= 8'} + dependencies: + minipass: 3.3.4 + yallist: 4.0.0 + dev: true + + /mkdirp-infer-owner/2.0.0: + resolution: {integrity: sha512-sdqtiFt3lkOaYvTXSRIUjkIdPTcxgv5+fgqYE/5qgwdw12cOrAuzzgzvVExIkH/ul1oeHN3bCLOWSG3XOqbKKw==} + engines: {node: '>=10'} + dependencies: + chownr: 2.0.0 + infer-owner: 1.0.4 + mkdirp: 1.0.4 + dev: true + + /mkdirp/0.5.6: + resolution: {integrity: sha512-FP+p8RB8OWpF3YZBCrP5gtADmtXApB5AMLn+vdyA+PyxCjrCs00mjyUozssO33cwDeT3wNGdLxJ5M//YqtHAJw==} + hasBin: true + dependencies: + minimist: 1.2.7 + dev: true + + /mkdirp/1.0.4: + resolution: {integrity: sha512-vVqVZQyf3WLx2Shd0qJ9xuvqgAyKPLAiqITEtqW0oIUjzo3PePDd6fW9iFz30ef7Ysp/oiWqbhszeGWW2T6Gzw==} + engines: {node: '>=10'} + hasBin: true + dev: true + + /modify-values/1.0.1: + resolution: {integrity: sha512-xV2bxeN6F7oYjZWTe/YPAy6MN2M+sL4u/Rlm2AHCIVGfo2p1yGmBHQ6vHehl4bRTZBdHu3TSkWdYgkwpYzAGSw==} + engines: {node: '>=0.10.0'} + dev: true + + /ms/2.0.0: + resolution: {integrity: sha512-Tpp60P6IUJDTuOq/5Z8cdskzJujfwqfOTkrwIwj7IRISpnkJnT6SyJ4PCPnGMoFjC9ddhal5KVIYtAt97ix05A==} + dev: true + + /ms/2.1.2: + resolution: {integrity: sha512-sGkPx+VjMtmA6MX27oA4FBFELFCZZ4S4XqeGOXCv68tT+jb3vk/RyaKWP0PTKyWtmLSM0b+adUTEvbs1PEaH2w==} + dev: true + + /ms/2.1.3: + resolution: {integrity: sha512-6FlzubTLZG3J2a/NVCAleEhjzq5oxgHyaCU9yYXvcLsvoVaHJq/s5xXI6/XXP6tz7R9xAOtHnSO/tXtF3WRTlA==} + dev: true + + /multimatch/5.0.0: + resolution: {integrity: sha512-ypMKuglUrZUD99Tk2bUQ+xNQj43lPEfAeX2o9cTteAmShXy2VHDJpuwu1o0xqoKCt9jLVAvwyFKdLTPXKAfJyA==} + engines: {node: '>=10'} + dependencies: + '@types/minimatch': 3.0.5 + array-differ: 3.0.0 + array-union: 2.1.0 + arrify: 2.0.1 + minimatch: 3.1.2 + dev: true + + /mute-stream/0.0.8: + resolution: {integrity: sha512-nnbWWOkoWyUsTjKrhgD0dcz22mdkSnpYqbEjIm2nhwhuxlSkpywJmBo8h0ZqJdkp73mb90SssHkN4rsRaBAfAA==} + dev: true + + /natural-compare/1.4.0: + resolution: {integrity: sha512-OWND8ei3VtNC9h7V60qff3SVobHr996CTwgxubgyQYEpg290h9J0buyECNNJexkFm5sOajh5G116RYA1c8ZMSw==} + dev: true + + /negotiator/0.6.3: + resolution: {integrity: sha512-+EUsqGPLsM+j/zdChZjsnX51g4XrHFOIXwfnCVPGlQk/k5giakcKsuxCObBRu6DSm9opw/O6slWbJdghQM4bBg==} + engines: {node: '>= 0.6'} + dev: true + + /neo-async/2.6.2: + resolution: {integrity: sha512-Yd3UES5mWCSqR+qNT93S3UoYUkqAZ9lLg8a7g9rimsWmYGK8cVToA4/sF3RrshdyV3sAGMXVUmpMYOw+dLpOuw==} + dev: true + + /node-fetch/2.6.7: + resolution: {integrity: sha512-ZjMPFEfVx5j+y2yF35Kzx5sF7kDzxuDj6ziH4FFbOp87zKDZNx8yExJIb05OGF4Nlt9IHFIMBkRl41VdvcNdbQ==} + engines: {node: 4.x || >=6.0.0} + peerDependencies: + encoding: ^0.1.0 + peerDependenciesMeta: + encoding: + optional: true + dependencies: + whatwg-url: 5.0.0 + dev: true + + /node-gyp/5.1.1: + resolution: {integrity: sha512-WH0WKGi+a4i4DUt2mHnvocex/xPLp9pYt5R6M2JdFB7pJ7Z34hveZ4nDTGTiLXCkitA9T8HFZjhinBCiVHYcWw==} + engines: {node: '>= 6.0.0'} + hasBin: true + dependencies: + env-paths: 2.2.1 + glob: 7.2.3 + graceful-fs: 4.2.10 + mkdirp: 0.5.6 + nopt: 4.0.3 + npmlog: 4.1.2 + request: 2.88.2 + rimraf: 2.7.1 + semver: 5.7.1 + tar: 4.4.19 + which: 1.3.1 + dev: true + + /node-gyp/7.1.2: + resolution: {integrity: sha512-CbpcIo7C3eMu3dL1c3d0xw449fHIGALIJsRP4DDPHpyiW8vcriNY7ubh9TE4zEKfSxscY7PjeFnshE7h75ynjQ==} + engines: {node: '>= 10.12.0'} + hasBin: true + dependencies: + env-paths: 2.2.1 + glob: 7.2.3 + graceful-fs: 4.2.10 + nopt: 5.0.0 + npmlog: 4.1.2 + request: 2.88.2 + rimraf: 3.0.2 + semver: 7.3.8 + tar: 6.1.11 + which: 2.0.2 + dev: true + + /node-gyp/9.3.0: + resolution: {integrity: sha512-A6rJWfXFz7TQNjpldJ915WFb1LnhO4lIve3ANPbWreuEoLoKlFT3sxIepPBkLhM27crW8YmN+pjlgbasH6cH/Q==} + engines: {node: ^12.22 || ^14.13 || >=16} + hasBin: true + dependencies: + env-paths: 2.2.1 + glob: 7.2.3 + graceful-fs: 4.2.10 + make-fetch-happen: 10.2.1 + nopt: 6.0.0 + npmlog: 6.0.2 + rimraf: 3.0.2 + semver: 7.3.8 + tar: 6.1.11 + which: 2.0.2 + transitivePeerDependencies: + - bluebird + - supports-color + dev: true + + /node-preload/0.2.1: + resolution: {integrity: sha512-RM5oyBy45cLEoHqCeh+MNuFAxO0vTFBLskvQbOKnEE7YTTSN4tbN8QWDIPQ6L+WvKsB/qLEGpYe2ZZ9d4W9OIQ==} + engines: {node: '>=8'} + dependencies: + process-on-spawn: 1.0.0 + dev: true + + /node-releases/2.0.6: + resolution: {integrity: sha512-PiVXnNuFm5+iYkLBNeq5211hvO38y63T0i2KKh2KnUs3RpzJ+JtODFjkD8yjLwnDkTYF1eKXheUwdssR+NRZdg==} + dev: true + + /nopt/4.0.3: + resolution: {integrity: sha512-CvaGwVMztSMJLOeXPrez7fyfObdZqNUK1cPAEzLHrTybIua9pMdmmPR5YwtfNftIOMv3DPUhFaxsZMNTQO20Kg==} + hasBin: true + dependencies: + abbrev: 1.1.1 + osenv: 0.1.5 + dev: true + + /nopt/5.0.0: + resolution: {integrity: sha512-Tbj67rffqceeLpcRXrT7vKAN8CwfPeIBgM7E6iBkmKLV7bEMwpGgYLGv0jACUsECaa/vuxP0IjEont6umdMgtQ==} + engines: {node: '>=6'} + hasBin: true + dependencies: + abbrev: 1.1.1 + dev: true + + /nopt/6.0.0: + resolution: {integrity: sha512-ZwLpbTgdhuZUnZzjd7nb1ZV+4DoiC6/sfiVKok72ym/4Tlf+DFdlHYmT2JPmcNNWV6Pi3SDf1kT+A4r9RTuT9g==} + engines: {node: ^12.13.0 || ^14.15.0 || >=16.0.0} + hasBin: true + dependencies: + abbrev: 1.1.1 + dev: true + + /normalize-package-data/2.5.0: + resolution: {integrity: sha512-/5CMN3T0R4XTj4DcGaexo+roZSdSFW/0AOOTROrjxzCG1wrWXEsGbRKevjlIL+ZDE4sZlJr5ED4YW0yqmkK+eA==} + dependencies: + hosted-git-info: 2.8.9 + resolve: 1.22.1 + semver: 5.7.1 + validate-npm-package-license: 3.0.4 + dev: true + + /normalize-package-data/3.0.3: + resolution: {integrity: sha512-p2W1sgqij3zMMyRC067Dg16bfzVH+w7hyegmpIvZ4JNjqtGOVAIvLmjBx3yP7YTe9vKJgkoNOPjwQGogDoMXFA==} + engines: {node: '>=10'} + dependencies: + hosted-git-info: 4.1.0 + is-core-module: 2.10.0 + semver: 7.3.8 + validate-npm-package-license: 3.0.4 + dev: true + + /normalize-package-data/4.0.1: + resolution: {integrity: sha512-EBk5QKKuocMJhB3BILuKhmaPjI8vNRSpIfO9woLC6NyHVkKKdVEdAO1mrT0ZfxNR1lKwCcTkuZfmGIFdizZ8Pg==} + engines: {node: ^12.13.0 || ^14.15.0 || >=16.0.0} + dependencies: + hosted-git-info: 5.1.0 + is-core-module: 2.10.0 + semver: 7.3.8 + validate-npm-package-license: 3.0.4 + dev: true + + /normalize-url/4.5.1: + resolution: {integrity: sha512-9UZCFRHQdNrfTpGg8+1INIg93B6zE0aXMVFkw1WFwvO4SlZywU6aLg5Of0Ap/PgcbSw4LNxvMWXMeugwMCX0AA==} + engines: {node: '>=8'} + dev: true + + /normalize-url/6.1.0: + resolution: {integrity: sha512-DlL+XwOy3NxAQ8xuC0okPgK46iuVNAK01YN7RueYBqqFeGsBjV9XmCAzAdgt+667bCl5kPh9EqKKDwnaPG1I7A==} + engines: {node: '>=10'} + dev: true + + /npm-bundled/1.1.2: + resolution: {integrity: sha512-x5DHup0SuyQcmL3s7Rx/YQ8sbw/Hzg0rj48eN0dV7hf5cmQq5PXIeioroH3raV1QC1yh3uTYuMThvEQF3iKgGQ==} + dependencies: + npm-normalize-package-bin: 1.0.1 + dev: true + + /npm-bundled/2.0.1: + resolution: {integrity: sha512-gZLxXdjEzE/+mOstGDqR6b0EkhJ+kM6fxM6vUuckuctuVPh80Q6pw/rSZj9s4Gex9GxWtIicO1pc8DB9KZWudw==} + engines: {node: ^12.13.0 || ^14.15.0 || >=16.0.0} + dependencies: + npm-normalize-package-bin: 2.0.0 + dev: true + + /npm-check-updates/12.5.12: + resolution: {integrity: sha512-JAFs+kKokZmYPRzhSHgIpKashX6vSGGXYo0VJXNaKV/nLnq3ZKI0nTVou9OwTix+PFfLAWTEJ6T/byGxkDlhWA==} + engines: {node: '>=12'} + hasBin: true + dependencies: + chalk: 4.1.2 + cint: 8.2.1 + cli-table: 0.3.11 + commander: 9.4.1 + fast-memoize: 2.5.2 + find-up: 5.0.0 + fp-and-or: 0.1.3 + get-stdin: 8.0.0 + globby: 11.1.0 + hosted-git-info: 5.1.0 + json-parse-helpfulerror: 1.0.3 + jsonlines: 0.1.1 + libnpmconfig: 1.2.1 + lodash: 4.17.21 + minimatch: 5.1.0 + p-map: 4.0.0 + pacote: 13.6.2 + parse-github-url: 1.0.2 + progress: 2.0.3 + prompts: 2.4.2 + rc-config-loader: 4.1.0 + remote-git-tags: 3.0.0 + rimraf: 3.0.2 + semver: 7.3.8 + semver-utils: 1.1.4 + source-map-support: 0.5.21 + spawn-please: 1.0.0 + update-notifier: 5.1.0 + yaml: 1.10.2 + transitivePeerDependencies: + - bluebird + - supports-color + dev: true + + /npm-install-checks/4.0.0: + resolution: {integrity: sha512-09OmyDkNLYwqKPOnbI8exiOZU2GVVmQp7tgez2BPi5OZC8M82elDAps7sxC4l//uSUtotWqoEIDwjRvWH4qz8w==} + engines: {node: '>=10'} + dependencies: + semver: 7.3.8 + dev: true + + /npm-install-checks/5.0.0: + resolution: {integrity: sha512-65lUsMI8ztHCxFz5ckCEC44DRvEGdZX5usQFriauxHEwt7upv1FKaQEmAtU0YnOAdwuNWCmk64xYiQABNrEyLA==} + engines: {node: ^12.13.0 || ^14.15.0 || >=16.0.0} + dependencies: + semver: 7.3.8 + dev: true + + /npm-lifecycle/3.1.5: + resolution: {integrity: sha512-lDLVkjfZmvmfvpvBzA4vzee9cn+Me4orq0QF8glbswJVEbIcSNWib7qGOffolysc3teCqbbPZZkzbr3GQZTL1g==} + dependencies: + byline: 5.0.0 + graceful-fs: 4.2.10 + node-gyp: 5.1.1 + resolve-from: 4.0.0 + slide: 1.1.6 + uid-number: 0.0.6 + umask: 1.1.0 + which: 1.3.1 + dev: true + + /npm-normalize-package-bin/1.0.1: + resolution: {integrity: sha512-EPfafl6JL5/rU+ot6P3gRSCpPDW5VmIzX959Ob1+ySFUuuYHWHekXpwdUZcKP5C+DS4GEtdJluwBjnsNDl+fSA==} + dev: true + + /npm-normalize-package-bin/2.0.0: + resolution: {integrity: sha512-awzfKUO7v0FscrSpRoogyNm0sajikhBWpU0QMrW09AMi9n1PoKU6WaIqUzuJSQnpciZZmJ/jMZ2Egfmb/9LiWQ==} + engines: {node: ^12.13.0 || ^14.15.0 || >=16.0.0} + dev: true + + /npm-package-arg/8.1.5: + resolution: {integrity: sha512-LhgZrg0n0VgvzVdSm1oiZworPbTxYHUJCgtsJW8mGvlDpxTM1vSJc3m5QZeUkhAHIzbz3VCHd/R4osi1L1Tg/Q==} + engines: {node: '>=10'} + dependencies: + hosted-git-info: 4.1.0 + semver: 7.3.8 + validate-npm-package-name: 3.0.0 + dev: true + + /npm-package-arg/9.1.2: + resolution: {integrity: sha512-pzd9rLEx4TfNJkovvlBSLGhq31gGu2QDexFPWT19yCDh0JgnRhlBLNo5759N0AJmBk+kQ9Y/hXoLnlgFD+ukmg==} + engines: {node: ^12.13.0 || ^14.15.0 || >=16.0.0} + dependencies: + hosted-git-info: 5.1.0 + proc-log: 2.0.1 + semver: 7.3.8 + validate-npm-package-name: 4.0.0 + dev: true + + /npm-packlist/2.2.2: + resolution: {integrity: sha512-Jt01acDvJRhJGthnUJVF/w6gumWOZxO7IkpY/lsX9//zqQgnF7OJaxgQXcerd4uQOLu7W5bkb4mChL9mdfm+Zg==} + engines: {node: '>=10'} + hasBin: true + dependencies: + glob: 7.2.3 + ignore-walk: 3.0.4 + npm-bundled: 1.1.2 + npm-normalize-package-bin: 1.0.1 + dev: true + + /npm-packlist/5.1.3: + resolution: {integrity: sha512-263/0NGrn32YFYi4J533qzrQ/krmmrWwhKkzwTuM4f/07ug51odoaNjUexxO4vxlzURHcmYMH1QjvHjsNDKLVg==} + engines: {node: ^12.13.0 || ^14.15.0 || >=16.0.0} + hasBin: true + dependencies: + glob: 8.0.3 + ignore-walk: 5.0.1 + npm-bundled: 2.0.1 + npm-normalize-package-bin: 2.0.0 + dev: true + + /npm-pick-manifest/6.1.1: + resolution: {integrity: sha512-dBsdBtORT84S8V8UTad1WlUyKIY9iMsAmqxHbLdeEeBNMLQDlDWWra3wYUx9EBEIiG/YwAy0XyNHDd2goAsfuA==} + dependencies: + npm-install-checks: 4.0.0 + npm-normalize-package-bin: 1.0.1 + npm-package-arg: 8.1.5 + semver: 7.3.8 + dev: true + + /npm-pick-manifest/7.0.2: + resolution: {integrity: sha512-gk37SyRmlIjvTfcYl6RzDbSmS9Y4TOBXfsPnoYqTHARNgWbyDiCSMLUpmALDj4jjcTZpURiEfsSHJj9k7EV4Rw==} + engines: {node: ^12.13.0 || ^14.15.0 || >=16.0.0} + dependencies: + npm-install-checks: 5.0.0 + npm-normalize-package-bin: 2.0.0 + npm-package-arg: 9.1.2 + semver: 7.3.8 + dev: true + + /npm-registry-fetch/11.0.0: + resolution: {integrity: sha512-jmlgSxoDNuhAtxUIG6pVwwtz840i994dL14FoNVZisrmZW5kWd63IUTNv1m/hyRSGSqWjCUp/YZlS1BJyNp9XA==} + engines: {node: '>=10'} + dependencies: + make-fetch-happen: 9.1.0 + minipass: 3.3.4 + minipass-fetch: 1.4.1 + minipass-json-stream: 1.0.1 + minizlib: 2.1.2 + npm-package-arg: 8.1.5 + transitivePeerDependencies: + - bluebird + - supports-color + dev: true + + /npm-registry-fetch/13.3.1: + resolution: {integrity: sha512-eukJPi++DKRTjSBRcDZSDDsGqRK3ehbxfFUcgaRd0Yp6kRwOwh2WVn0r+8rMB4nnuzvAk6rQVzl6K5CkYOmnvw==} + engines: {node: ^12.13.0 || ^14.15.0 || >=16.0.0} + dependencies: + make-fetch-happen: 10.2.1 + minipass: 3.3.4 + minipass-fetch: 2.1.2 + minipass-json-stream: 1.0.1 + minizlib: 2.1.2 + npm-package-arg: 9.1.2 + proc-log: 2.0.1 + transitivePeerDependencies: + - bluebird + - supports-color + dev: true + + /npm-registry-fetch/9.0.0: + resolution: {integrity: sha512-PuFYYtnQ8IyVl6ib9d3PepeehcUeHN9IO5N/iCRhyg9tStQcqGQBRVHmfmMWPDERU3KwZoHFvbJ4FPXPspvzbA==} + engines: {node: '>=10'} + dependencies: + '@npmcli/ci-detect': 1.4.0 + lru-cache: 6.0.0 + make-fetch-happen: 8.0.14 + minipass: 3.3.4 + minipass-fetch: 1.4.1 + minipass-json-stream: 1.0.1 + minizlib: 2.1.2 + npm-package-arg: 8.1.5 + transitivePeerDependencies: + - bluebird + - supports-color + dev: true + + /npm-run-path/4.0.1: + resolution: {integrity: sha512-S48WzZW777zhNIrn7gxOlISNAqi9ZC/uQFnRdbeIHhZhCA6UqpkOT8T1G7BvfdgP4Er8gF4sUbaS0i7QvIfCWw==} + engines: {node: '>=8'} + dependencies: + path-key: 3.1.1 + dev: true + + /npmlog/4.1.2: + resolution: {integrity: sha512-2uUqazuKlTaSI/dC8AzicUck7+IrEaOnN/e0jd3Xtt1KcGpwx30v50mL7oPyr/h9bL3E4aZccVwpwP+5W9Vjkg==} + dependencies: + are-we-there-yet: 1.1.7 + console-control-strings: 1.1.0 + gauge: 2.7.4 + set-blocking: 2.0.0 + dev: true + + /npmlog/6.0.2: + resolution: {integrity: sha512-/vBvz5Jfr9dT/aFWd0FIRf+T/Q2WBsLENygUaFUqstqsycmZAP/t5BvFJTK0viFmSUxiUKTUplWy5vt+rvKIxg==} + engines: {node: ^12.13.0 || ^14.15.0 || >=16.0.0} + dependencies: + are-we-there-yet: 3.0.1 + console-control-strings: 1.1.0 + gauge: 4.0.4 + set-blocking: 2.0.0 + dev: true + + /number-is-nan/1.0.1: + resolution: {integrity: sha512-4jbtZXNAsfZbAHiiqjLPBiCl16dES1zI4Hpzzxw61Tk+loF+sBDBKx1ICKKKwIqQ7M0mFn1TmkN7euSncWgHiQ==} + engines: {node: '>=0.10.0'} + dev: true + + /nyc/15.1.0: + resolution: {integrity: sha512-jMW04n9SxKdKi1ZMGhvUTHBN0EICCRkHemEoE5jm6mTYcqcdas0ATzgUgejlQUHMvpnOZqGB5Xxsv9KxJW1j8A==} + engines: {node: '>=8.9'} + hasBin: true + dependencies: + '@istanbuljs/load-nyc-config': 1.1.0 + '@istanbuljs/schema': 0.1.3 + caching-transform: 4.0.0 + convert-source-map: 1.9.0 + decamelize: 1.2.0 + find-cache-dir: 3.3.2 + find-up: 4.1.0 + foreground-child: 2.0.0 + get-package-type: 0.1.0 + glob: 7.2.3 + istanbul-lib-coverage: 3.2.0 + istanbul-lib-hook: 3.0.0 + istanbul-lib-instrument: 4.0.3 + istanbul-lib-processinfo: 2.0.3 + istanbul-lib-report: 3.0.0 + istanbul-lib-source-maps: 4.0.1 + istanbul-reports: 3.1.5 + make-dir: 3.1.0 + node-preload: 0.2.1 + p-map: 3.0.0 + process-on-spawn: 1.0.0 + resolve-from: 5.0.0 + rimraf: 3.0.2 + signal-exit: 3.0.7 + spawn-wrap: 2.0.0 + test-exclude: 6.0.0 + yargs: 15.4.1 + transitivePeerDependencies: + - supports-color + dev: true + + /oauth-sign/0.9.0: + resolution: {integrity: sha512-fexhUFFPTGV8ybAtSIGbV6gOkSv8UtRbDBnAyLQw4QPKkgNlsH2ByPGtMUqdWkos6YCRmAqViwgZrJc/mRDzZQ==} + dev: true + + /object-assign/4.1.1: + resolution: {integrity: sha512-rJgTQnkUnH1sFw8yT6VSU3zD3sWmu6sZhIseY8VX+GRu3P6F7Fu+JNDoXfklElbLJSnc3FUQHVe4cU5hj+BcUg==} + engines: {node: '>=0.10.0'} + dev: true + + /object-inspect/1.12.2: + resolution: {integrity: sha512-z+cPxW0QGUp0mcqcsgQyLVRDoXFQbXOwBaqyF7VIgI4TWNQsDHrBpUQslRmIfAoYWdYzs6UlKJtB2XJpTaNSpQ==} + dev: true + + /object-keys/1.1.1: + resolution: {integrity: sha512-NuAESUOUMrlIXOfHKzD6bpPu3tYt3xvjNdRIQ+FeT0lNb4K8WR70CaDxhuNguS2XG+GjkyMwOzsN5ZktImfhLA==} + engines: {node: '>= 0.4'} + dev: true + + /object.assign/4.1.4: + resolution: {integrity: sha512-1mxKf0e58bvyjSCtKYY4sRe9itRk3PJpquJOjeIkz885CczcI4IvJJDLPS72oowuSh+pBxUFROpX+TU++hxhZQ==} + engines: {node: '>= 0.4'} + dependencies: + call-bind: 1.0.2 + define-properties: 1.1.4 + has-symbols: 1.0.3 + object-keys: 1.1.1 + dev: true + + /object.getownpropertydescriptors/2.1.4: + resolution: {integrity: sha512-sccv3L/pMModT6dJAYF3fzGMVcb38ysQ0tEE6ixv2yXJDtEIPph268OlAdJj5/qZMZDq2g/jqvwppt36uS/uQQ==} + engines: {node: '>= 0.8'} + dependencies: + array.prototype.reduce: 1.0.4 + call-bind: 1.0.2 + define-properties: 1.1.4 + es-abstract: 1.20.4 + dev: true + + /object.values/1.1.5: + resolution: {integrity: sha512-QUZRW0ilQ3PnPpbNtgdNV1PDbEqLIiSFB3l+EnGtBQ/8SUTLj1PZwtQHABZtLgwpJZTSZhuGLOGk57Drx2IvYg==} + engines: {node: '>= 0.4'} + dependencies: + call-bind: 1.0.2 + define-properties: 1.1.4 + es-abstract: 1.20.4 + dev: true + + /once/1.4.0: + resolution: {integrity: sha512-lNaJgI+2Q5URQBkccEKHTQOPaXdUxnZZElQTZY0MFUAuaEqe1E+Nyvgdz/aIyNi6Z9MzO5dv1H8n58/GELp3+w==} + dependencies: + wrappy: 1.0.2 + dev: true + + /onetime/5.1.2: + resolution: {integrity: sha512-kbpaSSGJTWdAY5KPVeMOKXSrPtr8C8C7wodJbcsd51jRnmD+GZu8Y0VoU6Dm5Z4vWr0Ig/1NKuWRKf7j5aaYSg==} + engines: {node: '>=6'} + dependencies: + mimic-fn: 2.1.0 + dev: true + + /optionator/0.9.1: + resolution: {integrity: sha512-74RlY5FCnhq4jRxVUPKDaRwrVNXMqsGsiW6AJw4XK8hmtm10wC0ypZBLw5IIp85NZMr91+qd1RvvENwg7jjRFw==} + engines: {node: '>= 0.8.0'} + dependencies: + deep-is: 0.1.4 + fast-levenshtein: 2.0.6 + levn: 0.4.1 + prelude-ls: 1.2.1 + type-check: 0.4.0 + word-wrap: 1.2.3 + dev: true + + /os-homedir/1.0.2: + resolution: {integrity: sha512-B5JU3cabzk8c67mRRd3ECmROafjYMXbuzlwtqdM8IbS8ktlTix8aFGb2bAGKrSRIlnfKwovGUUr72JUPyOb6kQ==} + engines: {node: '>=0.10.0'} + dev: true + + /os-tmpdir/1.0.2: + resolution: {integrity: sha512-D2FR03Vir7FIu45XBY20mTb+/ZSWB00sjU9jdQXt83gDrI4Ztz5Fs7/yy74g2N5SVQY4xY1qDr4rNddwYRVX0g==} + engines: {node: '>=0.10.0'} + dev: true + + /osenv/0.1.5: + resolution: {integrity: sha512-0CWcCECdMVc2Rw3U5w9ZjqX6ga6ubk1xDVKxtBQPK7wis/0F2r9T6k4ydGYhecl7YUBxBVxhL5oisPsNxAPe2g==} + dependencies: + os-homedir: 1.0.2 + os-tmpdir: 1.0.2 + dev: true + + /p-cancelable/1.1.0: + resolution: {integrity: sha512-s73XxOZ4zpt1edZYZzvhqFa6uvQc1vwUa0K0BdtIZgQMAJj9IbebH+JkgKZc9h+B05PKHLOTl4ajG1BmNrVZlw==} + engines: {node: '>=6'} + dev: true + + /p-finally/1.0.0: + resolution: {integrity: sha512-LICb2p9CB7FS+0eR1oqWnHhp0FljGLZCWBE9aix0Uye9W8LTQPwMTYVGWQWIw9RdQiDg4+epXQODwIYJtSJaow==} + engines: {node: '>=4'} + dev: true + + /p-limit/1.3.0: + resolution: {integrity: sha512-vvcXsLAJ9Dr5rQOPk7toZQZJApBl2K4J6dANSsEuh6QI41JYcsS/qhTGa9ErIUUgK3WNQoJYvylxvjqmiqEA9Q==} + engines: {node: '>=4'} + dependencies: + p-try: 1.0.0 + dev: true + + /p-limit/2.3.0: + resolution: {integrity: sha512-//88mFWSJx8lxCzwdAABTJL2MyWB12+eIY7MDL2SqLmAkeKU9qxRvWuSyTjm3FUmpBEMuFfckAIqEaVGUDxb6w==} + engines: {node: '>=6'} + dependencies: + p-try: 2.2.0 + dev: true + + /p-limit/3.1.0: + resolution: {integrity: sha512-TYOanM3wGwNGsZN2cVTYPArw454xnXj5qmWF1bEoAc4+cU/ol7GVh7odevjp1FNHduHc3KZMcFduxU5Xc6uJRQ==} + engines: {node: '>=10'} + dependencies: + yocto-queue: 0.1.0 + dev: true + + /p-locate/2.0.0: + resolution: {integrity: sha512-nQja7m7gSKuewoVRen45CtVfODR3crN3goVQ0DDZ9N3yHxgpkuBhZqsaiotSQRrADUrne346peY7kT3TSACykg==} + engines: {node: '>=4'} + dependencies: + p-limit: 1.3.0 + dev: true + + /p-locate/3.0.0: + resolution: {integrity: sha512-x+12w/To+4GFfgJhBEpiDcLozRJGegY+Ei7/z0tSLkMmxGZNybVMSfWj9aJn8Z5Fc7dBUNJOOVgPv2H7IwulSQ==} + engines: {node: '>=6'} + dependencies: + p-limit: 2.3.0 + dev: true + + /p-locate/4.1.0: + resolution: {integrity: sha512-R79ZZ/0wAxKGu3oYMlz8jy/kbhsNrS7SKZ7PxEHBgJ5+F2mtFW2fK2cOtBh1cHYkQsbzFV7I+EoRKe6Yt0oK7A==} + engines: {node: '>=8'} + dependencies: + p-limit: 2.3.0 + dev: true + + /p-locate/5.0.0: + resolution: {integrity: sha512-LaNjtRWUBY++zB5nE/NwcaoMylSPk+S+ZHNB1TzdbMJMny6dynpAGt7X/tl/QYq3TIeE6nxHppbo2LGymrG5Pw==} + engines: {node: '>=10'} + dependencies: + p-limit: 3.1.0 + dev: true + + /p-map-series/2.1.0: + resolution: {integrity: sha512-RpYIIK1zXSNEOdwxcfe7FdvGcs7+y5n8rifMhMNWvaxRNMPINJHF5GDeuVxWqnfrcHPSCnp7Oo5yNXHId9Av2Q==} + engines: {node: '>=8'} + dev: true + + /p-map/3.0.0: + resolution: {integrity: sha512-d3qXVTF/s+W+CdJ5A29wywV2n8CQQYahlgz2bFiA+4eVNJbHJodPZ+/gXwPGh0bOqA+j8S+6+ckmvLGPk1QpxQ==} + engines: {node: '>=8'} + dependencies: + aggregate-error: 3.1.0 + dev: true + + /p-map/4.0.0: + resolution: {integrity: sha512-/bjOqmgETBYB5BoEeGVea8dmvHb2m9GLy1E9W43yeyfP6QQCZGFNa+XRceJEuDB6zqr+gKpIAmlLebMpykw/MQ==} + engines: {node: '>=10'} + dependencies: + aggregate-error: 3.1.0 + dev: true + + /p-pipe/3.1.0: + resolution: {integrity: sha512-08pj8ATpzMR0Y80x50yJHn37NF6vjrqHutASaX5LiH5npS9XPvrUmscd9MF5R4fuYRHOxQR1FfMIlF7AzwoPqw==} + engines: {node: '>=8'} + dev: true + + /p-queue/6.6.2: + resolution: {integrity: sha512-RwFpb72c/BhQLEXIZ5K2e+AhgNVmIejGlTgiB9MzZ0e93GRvqZ7uSi0dvRF7/XIXDeNkra2fNHBxTyPDGySpjQ==} + engines: {node: '>=8'} + dependencies: + eventemitter3: 4.0.7 + p-timeout: 3.2.0 + dev: true + + /p-reduce/2.1.0: + resolution: {integrity: sha512-2USApvnsutq8uoxZBGbbWM0JIYLiEMJ9RlaN7fAzVNb9OZN0SHjjTTfIcb667XynS5Y1VhwDJVDa72TnPzAYWw==} + engines: {node: '>=8'} + dev: true + + /p-timeout/3.2.0: + resolution: {integrity: sha512-rhIwUycgwwKcP9yTOOFK/AKsAopjjCakVqLHePO3CC6Mir1Z99xT+R63jZxAT5lFZLa2inS5h+ZS2GvR99/FBg==} + engines: {node: '>=8'} + dependencies: + p-finally: 1.0.0 + dev: true + + /p-try/1.0.0: + resolution: {integrity: sha512-U1etNYuMJoIz3ZXSrrySFjsXQTWOx2/jdi86L+2pRvph/qMKL6sbcCYdH23fqsbm8TH2Gn0OybpT4eSFlCVHww==} + engines: {node: '>=4'} + dev: true + + /p-try/2.2.0: + resolution: {integrity: sha512-R4nPAVTAU0B9D35/Gk3uJf/7XYbQcyohSKdvAxIRSNghFl4e71hVoGnBNQz9cWaXxO2I10KTC+3jMdvvoKw6dQ==} + engines: {node: '>=6'} + dev: true + + /p-waterfall/2.1.1: + resolution: {integrity: sha512-RRTnDb2TBG/epPRI2yYXsimO0v3BXC8Yd3ogr1545IaqKK17VGhbWVeGGN+XfCm/08OK8635nH31c8bATkHuSw==} + engines: {node: '>=8'} + dependencies: + p-reduce: 2.1.0 + dev: true + + /package-hash/4.0.0: + resolution: {integrity: sha512-whdkPIooSu/bASggZ96BWVvZTRMOFxnyUG5PnTSGKoJE2gd5mbVNmR2Nj20QFzxYYgAXpoqC+AiXzl+UMRh7zQ==} + engines: {node: '>=8'} + dependencies: + graceful-fs: 4.2.10 + hasha: 5.2.2 + lodash.flattendeep: 4.4.0 + release-zalgo: 1.0.0 + dev: true + + /package-json/6.5.0: + resolution: {integrity: sha512-k3bdm2n25tkyxcjSKzB5x8kfVxlMdgsbPr0GkZcwHsLpba6cBjqCt1KlcChKEvxHIcTB1FVMuwoijZ26xex5MQ==} + engines: {node: '>=8'} + dependencies: + got: 9.6.0 + registry-auth-token: 4.2.2 + registry-url: 5.1.0 + semver: 6.3.0 + dev: true + + /pacote/11.3.5: + resolution: {integrity: sha512-fT375Yczn4zi+6Hkk2TBe1x1sP8FgFsEIZ2/iWaXY2r/NkhDJfxbcn5paz1+RTFCyNf+dPnaoBDJoAxXSU8Bkg==} + engines: {node: '>=10'} + hasBin: true + dependencies: + '@npmcli/git': 2.1.0 + '@npmcli/installed-package-contents': 1.0.7 + '@npmcli/promise-spawn': 1.3.2 + '@npmcli/run-script': 1.8.6 + cacache: 15.3.0 + chownr: 2.0.0 + fs-minipass: 2.1.0 + infer-owner: 1.0.4 + minipass: 3.3.4 + mkdirp: 1.0.4 + npm-package-arg: 8.1.5 + npm-packlist: 2.2.2 + npm-pick-manifest: 6.1.1 + npm-registry-fetch: 11.0.0 + promise-retry: 2.0.1 + read-package-json-fast: 2.0.3 + rimraf: 3.0.2 + ssri: 8.0.1 + tar: 6.1.11 + transitivePeerDependencies: + - bluebird + - supports-color + dev: true + + /pacote/13.6.2: + resolution: {integrity: sha512-Gu8fU3GsvOPkak2CkbojR7vjs3k3P9cA6uazKTHdsdV0gpCEQq2opelnEv30KRQWgVzP5Vd/5umjcedma3MKtg==} + engines: {node: ^12.13.0 || ^14.15.0 || >=16.0.0} + hasBin: true + dependencies: + '@npmcli/git': 3.0.2 + '@npmcli/installed-package-contents': 1.0.7 + '@npmcli/promise-spawn': 3.0.0 + '@npmcli/run-script': 4.2.1 + cacache: 16.1.3 + chownr: 2.0.0 + fs-minipass: 2.1.0 + infer-owner: 1.0.4 + minipass: 3.3.4 + mkdirp: 1.0.4 + npm-package-arg: 9.1.2 + npm-packlist: 5.1.3 + npm-pick-manifest: 7.0.2 + npm-registry-fetch: 13.3.1 + proc-log: 2.0.1 + promise-retry: 2.0.1 + read-package-json: 5.0.2 + read-package-json-fast: 2.0.3 + rimraf: 3.0.2 + ssri: 9.0.1 + tar: 6.1.11 + transitivePeerDependencies: + - bluebird + - supports-color + dev: true + + /parent-module/1.0.1: + resolution: {integrity: sha512-GQ2EWRpQV8/o+Aw8YqtfZZPfNRWZYkbidE9k5rpl/hC3vtHHBfGm2Ifi6qWV+coDGkrUKZAxE3Lot5kcsRlh+g==} + engines: {node: '>=6'} + dependencies: + callsites: 3.1.0 + dev: true + + /parse-github-url/1.0.2: + resolution: {integrity: sha512-kgBf6avCbO3Cn6+RnzRGLkUsv4ZVqv/VfAYkRsyBcgkshNvVBkRn1FEZcW0Jb+npXQWm2vHPnnOqFteZxRRGNw==} + engines: {node: '>=0.10.0'} + hasBin: true + dev: true + + /parse-json/4.0.0: + resolution: {integrity: sha512-aOIos8bujGN93/8Ox/jPLh7RwVnPEysynVFE+fQZyg6jKELEHwzgKdLRFHUgXJL6kylijVSBC4BvN9OmsB48Rw==} + engines: {node: '>=4'} + dependencies: + error-ex: 1.3.2 + json-parse-better-errors: 1.0.2 + dev: true + + /parse-json/5.2.0: + resolution: {integrity: sha512-ayCKvm/phCGxOkYRSCM82iDwct8/EonSEgCSxWxD7ve6jHggsFl4fZVQBPRNgQoKiuV/odhFrGzQXZwbifC8Rg==} + engines: {node: '>=8'} + dependencies: + '@babel/code-frame': 7.18.6 + error-ex: 1.3.2 + json-parse-even-better-errors: 2.3.1 + lines-and-columns: 1.2.4 + dev: true + + /parse-path/4.0.4: + resolution: {integrity: sha512-Z2lWUis7jlmXC1jeOG9giRO2+FsuyNipeQ43HAjqAZjwSe3SEf+q/84FGPHoso3kyntbxa4c4i77t3m6fGf8cw==} + dependencies: + is-ssh: 1.4.0 + protocols: 1.4.8 + qs: 6.11.0 + query-string: 6.14.1 + dev: true + + /parse-url/6.0.5: + resolution: {integrity: sha512-e35AeLTSIlkw/5GFq70IN7po8fmDUjpDPY1rIK+VubRfsUvBonjQ+PBZG+vWMACnQSmNlvl524IucoDmcioMxA==} + dependencies: + is-ssh: 1.4.0 + normalize-url: 6.1.0 + parse-path: 4.0.4 + protocols: 1.4.8 + dev: true + + /path-exists/3.0.0: + resolution: {integrity: sha512-bpC7GYwiDYQ4wYLe+FA8lhRjhQCMcQGuSgGGqDkg/QerRWw9CmGRT0iSOVRSZJ29NMLZgIzqaljJ63oaL4NIJQ==} + engines: {node: '>=4'} + dev: true + + /path-exists/4.0.0: + resolution: {integrity: sha512-ak9Qy5Q7jYb2Wwcey5Fpvg2KoAc/ZIhLSLOSBmRmygPsGwkVVt0fZa0qrtMz+m6tJTAHfZQ8FnmB4MG4LWy7/w==} + engines: {node: '>=8'} + dev: true + + /path-is-absolute/1.0.1: + resolution: {integrity: sha512-AVbw3UJ2e9bq64vSaS9Am0fje1Pa8pbGqTTsmXfaIiMpnr5DlDhfJOuLj9Sf95ZPVDAUerDfEk88MPmPe7UCQg==} + engines: {node: '>=0.10.0'} + dev: true + + /path-key/3.1.1: + resolution: {integrity: sha512-ojmeN0qd+y0jszEtoY48r0Peq5dwMEkIlCOu6Q5f41lfkswXuKtYrhgoTpLnyIcHm24Uhqx+5Tqm2InSwLhE6Q==} + engines: {node: '>=8'} + dev: true + + /path-parse/1.0.7: + resolution: {integrity: sha512-LDJzPVEEEPR+y48z93A0Ed0yXb8pAByGWo/k5YYdYgpY2/2EsOsksJrq7lOHxryrVOn1ejG6oAp8ahvOIQD8sw==} + dev: true + + /path-type/3.0.0: + resolution: {integrity: sha512-T2ZUsdZFHgA3u4e5PfPbjd7HDDpxPnQb5jN0SrDsjNSuVXHJqtwTnWqG0B1jZrgmJ/7lj1EmVIByWt1gxGkWvg==} + engines: {node: '>=4'} + dependencies: + pify: 3.0.0 + dev: true + + /path-type/4.0.0: + resolution: {integrity: sha512-gDKb8aZMDeD/tZWs9P6+q0J9Mwkdl6xMV8TjnGP3qJVJ06bdMgkbBlLU8IdfOsIsFz2BW1rNVT3XuNEl8zPAvw==} + engines: {node: '>=8'} + dev: true + + /performance-now/2.1.0: + resolution: {integrity: sha512-7EAHlyLHI56VEIdK57uwHdHKIaAGbnXPiw0yWbarQZOKaKpvUIgW0jWRVLiatnM+XXlSwsanIBH/hzGMJulMow==} + dev: true + + /picocolors/1.0.0: + resolution: {integrity: sha512-1fygroTLlHu66zi26VoTDv8yRgm0Fccecssto+MhsZ0D/DGW2sm8E8AjW7NU5VVTRt5GxbeZ5qBuJr+HyLYkjQ==} + dev: true + + /picomatch/2.3.1: + resolution: {integrity: sha512-JU3teHTNjmE2VCGFzuY8EXzCDVwEqB2a8fsIvwaStHhAWJEeVd1o1QD80CU6+ZdEXXSLbSsuLwJjkCBWqRQUVA==} + engines: {node: '>=8.6'} + dev: true + + /pify/2.3.0: + resolution: {integrity: sha512-udgsAY+fTnvv7kI7aaxbqwWNb0AHiB0qBO89PZKPkoTmGOgdbrHDKD+0B2X4uTfJ/FT1R09r9gTsjUjNJotuog==} + engines: {node: '>=0.10.0'} + dev: true + + /pify/3.0.0: + resolution: {integrity: sha512-C3FsVNH1udSEX48gGX1xfvwTWfsYWj5U+8/uK15BGzIGrKoUpghX8hWZwa/OFnakBiiVNmBvemTJR5mcy7iPcg==} + engines: {node: '>=4'} + dev: true + + /pify/4.0.1: + resolution: {integrity: sha512-uB80kBFb/tfd68bVleG9T5GGsGPjJrLAUpR5PZIrhBnIaRTQRjqdJSsIKkOP6OAIFbj7GOrcudc5pNjZ+geV2g==} + engines: {node: '>=6'} + dev: true + + /pify/5.0.0: + resolution: {integrity: sha512-eW/gHNMlxdSP6dmG6uJip6FXN0EQBwm2clYYd8Wul42Cwu/DK8HEftzsapcNdYe2MfLiIwZqsDk2RDEsTE79hA==} + engines: {node: '>=10'} + dev: true + + /pkg-dir/4.2.0: + resolution: {integrity: sha512-HRDzbaKjC+AOWVXxAU/x54COGeIv9eb+6CkDSQoNTt4XyWoIJvuPsXizxu/Fr23EiekbtZwmh1IcIG/l/a10GQ==} + engines: {node: '>=8'} + dependencies: + find-up: 4.1.0 + dev: true + + /prelude-ls/1.2.1: + resolution: {integrity: sha512-vkcDPrRZo1QZLbn5RLGPpg/WmIQ65qoWWhcGKf/b5eplkkarX0m9z8ppCat4mlOqUsWpyNuYgO3VRyrYHSzX5g==} + engines: {node: '>= 0.8.0'} + dev: true + + /prepend-http/2.0.0: + resolution: {integrity: sha512-ravE6m9Atw9Z/jjttRUZ+clIXogdghyZAuWJ3qEzjT+jI/dL1ifAqhZeC5VHzQp1MSt1+jxKkFNemj/iO7tVUA==} + engines: {node: '>=4'} + dev: true + + /proc-log/2.0.1: + resolution: {integrity: sha512-Kcmo2FhfDTXdcbfDH76N7uBYHINxc/8GW7UAVuVP9I+Va3uHSerrnKV6dLooga/gh7GlgzuCCr/eoldnL1muGw==} + engines: {node: ^12.13.0 || ^14.15.0 || >=16.0.0} + dev: true + + /process-nextick-args/2.0.1: + resolution: {integrity: sha512-3ouUOpQhtgrbOa17J7+uxOTpITYWaGP7/AhoR3+A+/1e9skrzelGi/dXzEYyvbxubEF6Wn2ypscTKiKJFFn1ag==} + dev: true + + /process-on-spawn/1.0.0: + resolution: {integrity: sha512-1WsPDsUSMmZH5LeMLegqkPDrsGgsWwk1Exipy2hvB0o/F0ASzbpIctSCcZIK1ykJvtTJULEH+20WOFjMvGnCTg==} + engines: {node: '>=8'} + dependencies: + fromentries: 1.3.2 + dev: true + + /progress/2.0.3: + resolution: {integrity: sha512-7PiHtLll5LdnKIMw100I+8xJXR5gW2QwWYkT6iJva0bXitZKa/XMrSbdmg3r2Xnaidz9Qumd0VPaMrZlF9V9sA==} + engines: {node: '>=0.4.0'} + dev: true + + /promise-inflight/1.0.1: + resolution: {integrity: sha512-6zWPyEOFaQBJYcGMHBKTKJ3u6TBsnMFOIZSa6ce1e/ZrrsOlnHRHbabMjLiBYKp+n44X9eUI6VUPaukCXHuG4g==} + peerDependencies: + bluebird: '*' + peerDependenciesMeta: + bluebird: + optional: true + dev: true + + /promise-retry/2.0.1: + resolution: {integrity: sha512-y+WKFlBR8BGXnsNlIHFGPZmyDf3DFMoLhaflAnyZgV6rG6xu+JwesTo2Q9R6XwYmtmwAFCkAk3e35jEdoeh/3g==} + engines: {node: '>=10'} + dependencies: + err-code: 2.0.3 + retry: 0.12.0 + dev: true + + /prompts/2.4.2: + resolution: {integrity: sha512-NxNv/kLguCA7p3jE8oL2aEBsrJWgAakBpgmgK6lpPWV+WuOmY6r2/zbAVnP+T8bQlA0nzHXSJSJW0Hq7ylaD2Q==} + engines: {node: '>= 6'} + dependencies: + kleur: 3.0.3 + sisteransi: 1.0.5 + dev: true + + /promzard/0.3.0: + resolution: {integrity: sha512-JZeYqd7UAcHCwI+sTOeUDYkvEU+1bQ7iE0UT1MgB/tERkAPkesW46MrpIySzODi+owTjZtiF8Ay5j9m60KmMBw==} + dependencies: + read: 1.0.7 + dev: true + + /proto-list/1.2.4: + resolution: {integrity: sha512-vtK/94akxsTMhe0/cbfpR+syPuszcuwhqVjJq26CuNDgFGj682oRBXOP5MJpv2r7JtE8MsiepGIqvvOTBwn2vA==} + dev: true + + /protocols/1.4.8: + resolution: {integrity: sha512-IgjKyaUSjsROSO8/D49Ab7hP8mJgTYcqApOqdPhLoPxAplXmkp+zRvsrSQjFn5by0rhm4VH0GAUELIPpx7B1yg==} + dev: true + + /protocols/2.0.1: + resolution: {integrity: sha512-/XJ368cyBJ7fzLMwLKv1e4vLxOju2MNAIokcr7meSaNcVbWz/CPcW22cP04mwxOErdA5mwjA8Q6w/cdAQxVn7Q==} + dev: true + + /psl/1.9.0: + resolution: {integrity: sha512-E/ZsdU4HLs/68gYzgGTkMicWTLPdAftJLfJFlLUAAKZGkStNU72sZjT66SnMDVOfOWY/YAoiD7Jxa9iHvngcag==} + dev: true + + /pump/3.0.0: + resolution: {integrity: sha512-LwZy+p3SFs1Pytd/jYct4wpv49HiYCqd9Rlc5ZVdk0V+8Yzv6jR5Blk3TRmPL1ft69TxP0IMZGJ+WPFU2BFhww==} + dependencies: + end-of-stream: 1.4.4 + once: 1.4.0 + dev: true + + /punycode/2.1.1: + resolution: {integrity: sha512-XRsRjdf+j5ml+y/6GKHPZbrF/8p2Yga0JPtdqTIY2Xe5ohJPD9saDJJLPvp9+NSBprVvevdXZybnj2cv8OEd0A==} + engines: {node: '>=6'} + dev: true + + /pupa/2.1.1: + resolution: {integrity: sha512-l1jNAspIBSFqbT+y+5FosojNpVpF94nlI+wDUpqP9enwOTfHx9f0gh5nB96vl+6yTpsJsypeNrwfzPrKuHB41A==} + engines: {node: '>=8'} + dependencies: + escape-goat: 2.1.1 + dev: true + + /q/1.5.1: + resolution: {integrity: sha512-kV/CThkXo6xyFEZUugw/+pIOywXcDbFYgSct5cT3gqlbkBE1SJdwy6UQoZvodiWF/ckQLZyDE/Bu1M6gVu5lVw==} + engines: {node: '>=0.6.0', teleport: '>=0.2.0'} + dev: true + + /qs/6.11.0: + resolution: {integrity: sha512-MvjoMCJwEarSbUYk5O+nmoSzSutSsTwF85zcHPQ9OrlFoZOYIjaqBAJIqIXjptyD5vThxGq52Xu/MaJzRkIk4Q==} + engines: {node: '>=0.6'} + dependencies: + side-channel: 1.0.4 + dev: true + + /qs/6.5.3: + resolution: {integrity: sha512-qxXIEh4pCGfHICj1mAJQ2/2XVZkjCDTcEgfoSQxc/fYivUZxTkk7L3bDBJSoNrEzXI17oUO5Dp07ktqE5KzczA==} + engines: {node: '>=0.6'} + dev: true + + /query-string/6.14.1: + resolution: {integrity: sha512-XDxAeVmpfu1/6IjyT/gXHOl+S0vQ9owggJ30hhWKdHAsNPOcasn5o9BW0eejZqL2e4vMjhAxoW3jVHcD6mbcYw==} + engines: {node: '>=6'} + dependencies: + decode-uri-component: 0.2.0 + filter-obj: 1.1.0 + split-on-first: 1.1.0 + strict-uri-encode: 2.0.0 + dev: true + + /queue-microtask/1.2.3: + resolution: {integrity: sha512-NuaNSa6flKT5JaSYQzJok04JzTL1CA6aGhv5rfLW3PgqA+M2ChpZQnAC8h8i4ZFkBS8X5RqkDBHA7r4hej3K9A==} + dev: true + + /quick-lru/4.0.1: + resolution: {integrity: sha512-ARhCpm70fzdcvNQfPoy49IaanKkTlRWF2JMzqhcJbhSFRZv7nPTvZJdcY7301IPmvW+/p0RgIWnQDLJxifsQ7g==} + engines: {node: '>=8'} + dev: true + + /rc-config-loader/4.1.0: + resolution: {integrity: sha512-aW+kX4qy0CiM9L4fG4Us3oEOpIrOrXzWykAn+xldD07Y9PXWjTH744oHbv0Kc9ZwWaylw3jMjxaf14RgStrNrA==} + dependencies: + debug: 4.3.4 + js-yaml: 4.1.0 + json5: 2.2.1 + require-from-string: 2.0.2 + transitivePeerDependencies: + - supports-color + dev: true + + /rc/1.2.8: + resolution: {integrity: sha512-y3bGgqKj3QBdxLbLkomlohkvsA8gdAiUQlSBJnBhfn+BPxg4bc62d8TcBW15wavDfgexCgccckhcZvywyQYPOw==} + hasBin: true + dependencies: + deep-extend: 0.6.0 + ini: 1.3.8 + minimist: 1.2.7 + strip-json-comments: 2.0.1 + dev: true + + /read-cmd-shim/2.0.0: + resolution: {integrity: sha512-HJpV9bQpkl6KwjxlJcBoqu9Ba0PQg8TqSNIOrulGt54a0uup0HtevreFHzYzkm0lpnleRdNBzXznKrgxglEHQw==} + dev: true + + /read-package-json-fast/2.0.3: + resolution: {integrity: sha512-W/BKtbL+dUjTuRL2vziuYhp76s5HZ9qQhd/dKfWIZveD0O40453QNyZhC0e63lqZrAQ4jiOapVoeJ7JrszenQQ==} + engines: {node: '>=10'} + dependencies: + json-parse-even-better-errors: 2.3.1 + npm-normalize-package-bin: 1.0.1 + dev: true + + /read-package-json/2.1.2: + resolution: {integrity: sha512-D1KmuLQr6ZSJS0tW8hf3WGpRlwszJOXZ3E8Yd/DNRaM5d+1wVRZdHlpGBLAuovjr28LbWvjpWkBHMxpRGGjzNA==} + dependencies: + glob: 7.2.3 + json-parse-even-better-errors: 2.3.1 + normalize-package-data: 2.5.0 + npm-normalize-package-bin: 1.0.1 + dev: true + + /read-package-json/3.0.1: + resolution: {integrity: sha512-aLcPqxovhJTVJcsnROuuzQvv6oziQx4zd3JvG0vGCL5MjTONUc4uJ90zCBC6R7W7oUKBNoR/F8pkyfVwlbxqng==} + engines: {node: '>=10'} + dependencies: + glob: 7.2.3 + json-parse-even-better-errors: 2.3.1 + normalize-package-data: 3.0.3 + npm-normalize-package-bin: 1.0.1 + dev: true + + /read-package-json/4.1.2: + resolution: {integrity: sha512-Dqer4pqzamDE2O4M55xp1qZMuLPqi4ldk2ya648FOMHRjwMzFhuxVrG04wd0c38IsvkVdr3vgHI6z+QTPdAjrQ==} + engines: {node: '>=10'} + dependencies: + glob: 7.2.3 + json-parse-even-better-errors: 2.3.1 + normalize-package-data: 3.0.3 + npm-normalize-package-bin: 1.0.1 + dev: true + + /read-package-json/5.0.2: + resolution: {integrity: sha512-BSzugrt4kQ/Z0krro8zhTwV1Kd79ue25IhNN/VtHFy1mG/6Tluyi+msc0UpwaoQzxSHa28mntAjIZY6kEgfR9Q==} + engines: {node: ^12.13.0 || ^14.15.0 || >=16.0.0} + dependencies: + glob: 8.0.3 + json-parse-even-better-errors: 2.3.1 + normalize-package-data: 4.0.1 + npm-normalize-package-bin: 2.0.0 + dev: true + + /read-package-tree/5.3.1: + resolution: {integrity: sha512-mLUDsD5JVtlZxjSlPPx1RETkNjjvQYuweKwNVt1Sn8kP5Jh44pvYuUHCp6xSVDZWbNxVxG5lyZJ921aJH61sTw==} + deprecated: The functionality that this package provided is now in @npmcli/arborist + dependencies: + read-package-json: 2.1.2 + readdir-scoped-modules: 1.1.0 + util-promisify: 2.1.0 + dev: true + + /read-pkg-up/3.0.0: + resolution: {integrity: sha512-YFzFrVvpC6frF1sz8psoHDBGF7fLPc+llq/8NB43oagqWkx8ar5zYtsTORtOjw9W2RHLpWP+zTWwBvf1bCmcSw==} + engines: {node: '>=4'} + dependencies: + find-up: 2.1.0 + read-pkg: 3.0.0 + dev: true + + /read-pkg-up/7.0.1: + resolution: {integrity: sha512-zK0TB7Xd6JpCLmlLmufqykGE+/TlOePD6qKClNW7hHDKFh/J7/7gCWGR7joEQEW1bKq3a3yUZSObOoWLFQ4ohg==} + engines: {node: '>=8'} + dependencies: + find-up: 4.1.0 + read-pkg: 5.2.0 + type-fest: 0.8.1 + dev: true + + /read-pkg/3.0.0: + resolution: {integrity: sha512-BLq/cCO9two+lBgiTYNqD6GdtK8s4NpaWrl6/rCO9w0TUS8oJl7cmToOZfRYllKTISY6nt1U7jQ53brmKqY6BA==} + engines: {node: '>=4'} + dependencies: + load-json-file: 4.0.0 + normalize-package-data: 2.5.0 + path-type: 3.0.0 + dev: true + + /read-pkg/5.2.0: + resolution: {integrity: sha512-Ug69mNOpfvKDAc2Q8DRpMjjzdtrnv9HcSMX+4VsZxD1aZ6ZzrIE7rlzXBtWTyhULSMKg076AW6WR5iZpD0JiOg==} + engines: {node: '>=8'} + dependencies: + '@types/normalize-package-data': 2.4.1 + normalize-package-data: 2.5.0 + parse-json: 5.2.0 + type-fest: 0.6.0 + dev: true + + /read/1.0.7: + resolution: {integrity: sha512-rSOKNYUmaxy0om1BNjMN4ezNT6VKK+2xF4GBhc81mkH7L60i6dp8qPYrkndNLT3QPphoII3maL9PVC9XmhHwVQ==} + engines: {node: '>=0.8'} + dependencies: + mute-stream: 0.0.8 + dev: true + + /readable-stream/2.3.7: + resolution: {integrity: sha512-Ebho8K4jIbHAxnuxi7o42OrZgF/ZTNcsZj6nRKyUmkhLFq8CHItp/fy6hQZuZmP/n3yZ9VBUbp4zz/mX8hmYPw==} + dependencies: + core-util-is: 1.0.3 + inherits: 2.0.4 + isarray: 1.0.0 + process-nextick-args: 2.0.1 + safe-buffer: 5.1.2 + string_decoder: 1.1.1 + util-deprecate: 1.0.2 + dev: true + + /readable-stream/3.6.0: + resolution: {integrity: sha512-BViHy7LKeTz4oNnkcLJ+lVSL6vpiFeX6/d3oSH8zCW7UxP2onchk+vTGB143xuFjHS3deTgkKoXXymXqymiIdA==} + engines: {node: '>= 6'} + dependencies: + inherits: 2.0.4 + string_decoder: 1.3.0 + util-deprecate: 1.0.2 + dev: true + + /readdir-scoped-modules/1.1.0: + resolution: {integrity: sha512-asaikDeqAQg7JifRsZn1NJZXo9E+VwlyCfbkZhwyISinqk5zNS6266HS5kah6P0SaQKGF6SkNnZVHUzHFYxYDw==} + dependencies: + debuglog: 1.0.1 + dezalgo: 1.0.4 + graceful-fs: 4.2.10 + once: 1.4.0 + dev: true + + /redent/3.0.0: + resolution: {integrity: sha512-6tDA8g98We0zd0GvVeMT9arEOnTw9qM03L9cJXaCjrip1OO764RDBLBfrB4cwzNGDj5OA5ioymC9GkizgWJDUg==} + engines: {node: '>=8'} + dependencies: + indent-string: 4.0.0 + strip-indent: 3.0.0 + dev: true + + /regexp.prototype.flags/1.4.3: + resolution: {integrity: sha512-fjggEOO3slI6Wvgjwflkc4NFRCTZAu5CnNfBd5qOMYhWdn67nJBBu34/TkD++eeFmd8C9r9jfXJ27+nSiRkSUA==} + engines: {node: '>= 0.4'} + dependencies: + call-bind: 1.0.2 + define-properties: 1.1.4 + functions-have-names: 1.2.3 + dev: true + + /regexpp/3.2.0: + resolution: {integrity: sha512-pq2bWo9mVD43nbts2wGv17XLiNLya+GklZ8kaDLV2Z08gDCsGpnKn9BFMepvWuHCbyVvY7J5o5+BVvoQbmlJLg==} + engines: {node: '>=8'} + dev: true + + /registry-auth-token/4.2.2: + resolution: {integrity: sha512-PC5ZysNb42zpFME6D/XlIgtNGdTl8bBOCw90xQLVMpzuuubJKYDWFAEuUNc+Cn8Z8724tg2SDhDRrkVEsqfDMg==} + engines: {node: '>=6.0.0'} + dependencies: + rc: 1.2.8 + dev: true + + /registry-url/5.1.0: + resolution: {integrity: sha512-8acYXXTI0AkQv6RAOjE3vOaIXZkT9wo4LOFbBKYQEEnnMNBpKqdUrI6S4NT0KPIo/WVvJ5tE/X5LF/TQUf0ekw==} + engines: {node: '>=8'} + dependencies: + rc: 1.2.8 + dev: true + + /release-zalgo/1.0.0: + resolution: {integrity: sha512-gUAyHVHPPC5wdqX/LG4LWtRYtgjxyX78oanFNTMMyFEfOqdC54s3eE82imuWKbOeqYht2CrNf64Qb8vgmmtZGA==} + engines: {node: '>=4'} + dependencies: + es6-error: 4.1.1 + dev: true + + /remote-git-tags/3.0.0: + resolution: {integrity: sha512-C9hAO4eoEsX+OXA4rla66pXZQ+TLQ8T9dttgQj18yuKlPMTVkIkdYXvlMC55IuUsIkV6DpmQYi10JKFLaU+l7w==} + engines: {node: '>=8'} + dev: true + + /request/2.88.2: + resolution: {integrity: sha512-MsvtOrfG9ZcrOwAW+Qi+F6HbD0CWXEh9ou77uOb7FM2WPhwT7smM833PzanhJLsgXjN89Ir6V2PczXNnMpwKhw==} + engines: {node: '>= 6'} + deprecated: request has been deprecated, see https://github.com/request/request/issues/3142 + dependencies: + aws-sign2: 0.7.0 + aws4: 1.11.0 + caseless: 0.12.0 + combined-stream: 1.0.8 + extend: 3.0.2 + forever-agent: 0.6.1 + form-data: 2.3.3 + har-validator: 5.1.5 + http-signature: 1.2.0 + is-typedarray: 1.0.0 + isstream: 0.1.2 + json-stringify-safe: 5.0.1 + mime-types: 2.1.35 + oauth-sign: 0.9.0 + performance-now: 2.1.0 + qs: 6.5.3 + safe-buffer: 5.2.1 + tough-cookie: 2.5.0 + tunnel-agent: 0.6.0 + uuid: 3.4.0 + dev: true + + /require-directory/2.1.1: + resolution: {integrity: sha512-fGxEI7+wsG9xrvdjsrlmL22OMTTiHRwAMroiEeMgq8gzoLC/PQr7RsRDSTLUg/bZAZtF+TVIkHc6/4RIKrui+Q==} + engines: {node: '>=0.10.0'} + dev: true + + /require-from-string/2.0.2: + resolution: {integrity: sha512-Xf0nWe6RseziFMu+Ap9biiUbmplq6S9/p+7w7YXP/JBHhrUDDUhwa+vANyubuqfZWTveU//DYVGsDG7RKL/vEw==} + engines: {node: '>=0.10.0'} + dev: true + + /require-main-filename/2.0.0: + resolution: {integrity: sha512-NKN5kMDylKuldxYLSUfrbo5Tuzh4hd+2E8NPPX02mZtn1VuREQToYe/ZdlJy+J3uCpfaiGF05e7B8W0iXbQHmg==} + dev: true + + /resolve-cwd/3.0.0: + resolution: {integrity: sha512-OrZaX2Mb+rJCpH/6CpSqt9xFVpN++x01XnN2ie9g6P5/3xelLAkXWVADpdz1IHD/KFfEXyE6V0U01OQ3UO2rEg==} + engines: {node: '>=8'} + dependencies: + resolve-from: 5.0.0 + dev: true + + /resolve-from/4.0.0: + resolution: {integrity: sha512-pb/MYmXstAkysRFx8piNI1tGFNQIFA3vkE3Gq4EuA1dF6gHp/+vgZqsCGJapvy8N3Q+4o7FwvquPJcnZ7RYy4g==} + engines: {node: '>=4'} + dev: true + + /resolve-from/5.0.0: + resolution: {integrity: sha512-qYg9KP24dD5qka9J47d0aVky0N+b4fTU89LN9iDnjB5waksiC49rvMB0PrUJQGoTmH50XPiqOvAjDfaijGxYZw==} + engines: {node: '>=8'} + dev: true + + /resolve/1.22.1: + resolution: {integrity: sha512-nBpuuYuY5jFsli/JIs1oldw6fOQCBioohqWZg/2hiaOybXOft4lonv85uDOKXdf8rhyK159cxU5cDcK/NKk8zw==} + hasBin: true + dependencies: + is-core-module: 2.10.0 + path-parse: 1.0.7 + supports-preserve-symlinks-flag: 1.0.0 + dev: true + + /responselike/1.0.2: + resolution: {integrity: sha512-/Fpe5guzJk1gPqdJLJR5u7eG/gNY4nImjbRDaVWVMRhne55TCmj2i9Q+54PBRfatRC8v/rIiv9BN0pMd9OV5EQ==} + dependencies: + lowercase-keys: 1.0.1 + dev: true + + /restore-cursor/3.1.0: + resolution: {integrity: sha512-l+sSefzHpj5qimhFSE5a8nufZYAM3sBSVMAPtYkmC+4EH2anSGaEMXSD0izRQbu9nfyQ9y5JrVmp7E8oZrUjvA==} + engines: {node: '>=8'} + dependencies: + onetime: 5.1.2 + signal-exit: 3.0.7 + dev: true + + /retry/0.12.0: + resolution: {integrity: sha512-9LkiTwjUh6rT555DtE9rTX+BKByPfrMzEAtnlEtdEwr3Nkffwiihqe2bWADg+OQRjt9gl6ICdmB/ZFDCGAtSow==} + engines: {node: '>= 4'} + dev: true + + /reusify/1.0.4: + resolution: {integrity: sha512-U9nH88a3fc/ekCF1l0/UP1IosiuIjyTh7hBvXVMHYgVcfGvt897Xguj2UOLDeI5BG2m7/uwyaLVT6fbtCwTyzw==} + engines: {iojs: '>=1.0.0', node: '>=0.10.0'} + dev: true + + /rimraf/2.7.1: + resolution: {integrity: sha512-uWjbaKIK3T1OSVptzX7Nl6PvQ3qAGtKEtVRjRuazjfL3Bx5eI409VZSqgND+4UNnmzLVdPj9FqFJNPqBZFve4w==} + hasBin: true + dependencies: + glob: 7.2.3 + dev: true + + /rimraf/3.0.2: + resolution: {integrity: sha512-JZkJMZkAGFFPP2YqXZXPbMlMBgsxzE8ILs4lMIX/2o0L9UBw9O/Y3o6wFw/i9YLapcUJWwqbi3kdxIPdC62TIA==} + hasBin: true + dependencies: + glob: 7.2.3 + dev: true + + /run-async/2.4.1: + resolution: {integrity: sha512-tvVnVv01b8c1RrA6Ep7JkStj85Guv/YrMcwqYQnwjsAS2cTmmPGBBjAjpCW7RrSodNSoE2/qg9O4bceNvUuDgQ==} + engines: {node: '>=0.12.0'} + dev: true + + /run-parallel/1.2.0: + resolution: {integrity: sha512-5l4VyZR86LZ/lDxZTR6jqL8AFE2S0IFLMP26AbjsLVADxHdhB/c0GUsH+y39UfCi3dzz8OlQuPmnaJOMoDHQBA==} + dependencies: + queue-microtask: 1.2.3 + dev: true + + /rxjs/6.6.7: + resolution: {integrity: sha512-hTdwr+7yYNIT5n4AMYp85KA6yw2Va0FLa3Rguvbpa4W3I5xynaBZo41cM3XM+4Q6fRMj3sBYIR1VAmZMXYJvRQ==} + engines: {npm: '>=2.0.0'} + dependencies: + tslib: 1.14.1 + dev: true + + /safe-buffer/5.1.2: + resolution: {integrity: sha512-Gd2UZBJDkXlY7GbJxfsE8/nvKkUEU1G38c1siN6QP6a9PT9MmHB8GnpscSmMJSoF8LOIrt8ud/wPtojys4G6+g==} + dev: true + + /safe-buffer/5.2.1: + resolution: {integrity: sha512-rp3So07KcdmmKbGvgaNxQSJr7bGVSVk5S9Eq1F+ppbRo70+YeaDxkw5Dd8NPN+GD6bjnYm2VuPuCXmpuYvmCXQ==} + dev: true + + /safe-regex-test/1.0.0: + resolution: {integrity: sha512-JBUUzyOgEwXQY1NuPtvcj/qcBDbDmEvWufhlnXZIm75DEHp+afM1r1ujJpJsV/gSM4t59tpDyPi1sd6ZaPFfsA==} + dependencies: + call-bind: 1.0.2 + get-intrinsic: 1.1.3 + is-regex: 1.1.4 + dev: true + + /safer-buffer/2.1.2: + resolution: {integrity: sha512-YZo3K82SD7Riyi0E1EQPojLz7kpepnSQI9IyPbHHg1XXXevb5dJI7tpyN2ADxGcQbHG7vcyRHk0cbwqcQriUtg==} + dev: true + + /semver-diff/3.1.1: + resolution: {integrity: sha512-GX0Ix/CJcHyB8c4ykpHGIAvLyOwOobtM/8d+TQkAd81/bEjgPHrfba41Vpesr7jX/t8Uh+R3EX9eAS5be+jQYg==} + engines: {node: '>=8'} + dependencies: + semver: 6.3.0 + dev: true + + /semver-utils/1.1.4: + resolution: {integrity: sha512-EjnoLE5OGmDAVV/8YDoN5KiajNadjzIp9BAHOhYeQHt7j0UWxjmgsx4YD48wp4Ue1Qogq38F1GNUJNqF1kKKxA==} + dev: true + + /semver/5.7.1: + resolution: {integrity: sha512-sauaDf/PZdVgrLTNYHRtpXa1iRiKcaebiKQ1BJdpQlWH2lCvexQdX55snPFyK7QzpudqbCI0qXFfOasHdyNDGQ==} + hasBin: true + dev: true + + /semver/6.3.0: + resolution: {integrity: sha512-b39TBaTSfV6yBrapU89p5fKekE2m/NwnDocOVruQFS1/veMgdzuPcnOM34M6CwxW8jH/lxEa5rBoDeUwu5HHTw==} + hasBin: true + dev: true + + /semver/7.3.8: + resolution: {integrity: sha512-NB1ctGL5rlHrPJtFDVIVzTyQylMLu9N9VICA6HSFJo8MCGVTMW6gfpicwKmmK/dAjTOrqu5l63JJOpDSrAis3A==} + engines: {node: '>=10'} + hasBin: true + dependencies: + lru-cache: 6.0.0 + dev: true + + /set-blocking/2.0.0: + resolution: {integrity: sha512-KiKBS8AnWGEyLzofFfmvKwpdPzqiy16LvQfK3yv/fVH7Bj13/wl3JSR1J+rfgRE9q7xUJK4qvgS8raSOeLUehw==} + dev: true + + /shallow-clone/3.0.1: + resolution: {integrity: sha512-/6KqX+GVUdqPuPPd2LxDDxzX6CAbjJehAAOKlNpqqUpAqPM6HeL8f+o3a+JsyGjn2lv0WY8UsTgUJjU9Ok55NA==} + engines: {node: '>=8'} + dependencies: + kind-of: 6.0.3 + dev: true + + /shebang-command/2.0.0: + resolution: {integrity: sha512-kHxr2zZpYtdmrN1qDjrrX/Z1rR1kG8Dx+gkpK1G4eXmvXswmcE1hTWBWYUzlraYw1/yZp6YuDY77YtvbN0dmDA==} + engines: {node: '>=8'} + dependencies: + shebang-regex: 3.0.0 + dev: true + + /shebang-regex/3.0.0: + resolution: {integrity: sha512-7++dFhtcx3353uBaq8DDR4NuxBetBzC7ZQOhmTQInHEd6bSrXdiEyzCvG07Z44UYdLShWUyXt5M/yhz8ekcb1A==} + engines: {node: '>=8'} + dev: true + + /side-channel/1.0.4: + resolution: {integrity: sha512-q5XPytqFEIKHkGdiMIrY10mvLRvnQh42/+GoBlFW3b2LXLE2xxJpZFdm94we0BaoV3RwJyGqg5wS7epxTv0Zvw==} + dependencies: + call-bind: 1.0.2 + get-intrinsic: 1.1.3 + object-inspect: 1.12.2 + dev: true + + /signal-exit/3.0.7: + resolution: {integrity: sha512-wnD2ZE+l+SPC/uoS0vXeE9L1+0wuaMqKlfz9AMUo38JsyLSBWSFcHR1Rri62LZc12vLr1gb3jl7iwQhgwpAbGQ==} + dev: true + + /sisteransi/1.0.5: + resolution: {integrity: sha512-bLGGlR1QxBcynn2d5YmDX4MGjlZvy2MRBDRNHLJ8VI6l6+9FUiyTFNJ0IveOSP0bcXgVDPRcfGqA0pjaqUpfVg==} + dev: true + + /slash/3.0.0: + resolution: {integrity: sha512-g9Q1haeby36OSStwb4ntCGGGaKsaVSjQ68fBxoQcutl5fS1vuY18H3wSt3jFyFtrkx+Kz0V1G85A4MyAdDMi2Q==} + engines: {node: '>=8'} + dev: true + + /slide/1.1.6: + resolution: {integrity: sha512-NwrtjCg+lZoqhFU8fOwl4ay2ei8PaqCBOUV3/ektPY9trO1yQ1oXEfmHAhKArUVUr/hOHvy5f6AdP17dCM0zMw==} + dev: true + + /smart-buffer/4.2.0: + resolution: {integrity: sha512-94hK0Hh8rPqQl2xXc3HsaBoOXKV20MToPkcXvwbISWLEs+64sBq5kFgn2kJDHb1Pry9yrP0dxrCI9RRci7RXKg==} + engines: {node: '>= 6.0.0', npm: '>= 3.0.0'} + dev: true + + /socks-proxy-agent/5.0.1: + resolution: {integrity: sha512-vZdmnjb9a2Tz6WEQVIurybSwElwPxMZaIc7PzqbJTrezcKNznv6giT7J7tZDZ1BojVaa1jvO/UiUdhDVB0ACoQ==} + engines: {node: '>= 6'} + dependencies: + agent-base: 6.0.2 + debug: 4.3.4 + socks: 2.7.1 + transitivePeerDependencies: + - supports-color + dev: true + + /socks-proxy-agent/6.2.1: + resolution: {integrity: sha512-a6KW9G+6B3nWZ1yB8G7pJwL3ggLy1uTzKAgCb7ttblwqdz9fMGJUuTy3uFzEP48FAs9FLILlmzDlE2JJhVQaXQ==} + engines: {node: '>= 10'} + dependencies: + agent-base: 6.0.2 + debug: 4.3.4 + socks: 2.7.1 + transitivePeerDependencies: + - supports-color + dev: true + + /socks-proxy-agent/7.0.0: + resolution: {integrity: sha512-Fgl0YPZ902wEsAyiQ+idGd1A7rSFx/ayC1CQVMw5P+EQx2V0SgpGtf6OKFhVjPflPUl9YMmEOnmfjCdMUsygww==} + engines: {node: '>= 10'} + dependencies: + agent-base: 6.0.2 + debug: 4.3.4 + socks: 2.7.1 + transitivePeerDependencies: + - supports-color + dev: true + + /socks/2.7.1: + resolution: {integrity: sha512-7maUZy1N7uo6+WVEX6psASxtNlKaNVMlGQKkG/63nEDdLOWNbiUMoLK7X4uYoLhQstau72mLgfEWcXcwsaHbYQ==} + engines: {node: '>= 10.13.0', npm: '>= 3.0.0'} + dependencies: + ip: 2.0.0 + smart-buffer: 4.2.0 + dev: true + + /sort-keys/2.0.0: + resolution: {integrity: sha512-/dPCrG1s3ePpWm6yBbxZq5Be1dXGLyLn9Z791chDC3NFrpkVbWGzkBwPN1knaciexFXgRJ7hzdnwZ4stHSDmjg==} + engines: {node: '>=4'} + dependencies: + is-plain-obj: 1.1.0 + dev: true + + /sort-keys/4.2.0: + resolution: {integrity: sha512-aUYIEU/UviqPgc8mHR6IW1EGxkAXpeRETYcrzg8cLAvUPZcpAlleSXHV2mY7G12GphSH6Gzv+4MMVSSkbdteHg==} + engines: {node: '>=8'} + dependencies: + is-plain-obj: 2.1.0 + dev: true + + /source-map-support/0.5.21: + resolution: {integrity: sha512-uBHU3L3czsIyYXKX88fdrGovxdSCoTGDRZ6SYXtSRxLZUzHg5P/66Ht6uoUlHu9EZod+inXhKo3qQgwXUT/y1w==} + dependencies: + buffer-from: 1.1.2 + source-map: 0.6.1 + dev: true + + /source-map/0.6.1: + resolution: {integrity: sha512-UjgapumWlbMhkBgzT7Ykc5YXUT46F0iKu8SGXq0bcwP5dz/h0Plj6enJqjz1Zbq2l5WaqYnrVbwWOWMyF3F47g==} + engines: {node: '>=0.10.0'} + dev: true + + /spawn-please/1.0.0: + resolution: {integrity: sha512-Kz33ip6NRNKuyTRo3aDWyWxeGeM0ORDO552Fs6E1nj4pLWPkl37SrRtTnq+MEopVaqgmaO6bAvVS+v64BJ5M/A==} + engines: {node: '>=10'} + dev: true + + /spawn-wrap/2.0.0: + resolution: {integrity: sha512-EeajNjfN9zMnULLwhZZQU3GWBoFNkbngTUPfaawT4RkMiviTxcX0qfhVbGey39mfctfDHkWtuecgQ8NJcyQWHg==} + engines: {node: '>=8'} + dependencies: + foreground-child: 2.0.0 + is-windows: 1.0.2 + make-dir: 3.1.0 + rimraf: 3.0.2 + signal-exit: 3.0.7 + which: 2.0.2 + dev: true + + /spdx-correct/3.1.1: + resolution: {integrity: sha512-cOYcUWwhCuHCXi49RhFRCyJEK3iPj1Ziz9DpViV3tbZOwXD49QzIN3MpOLJNxh2qwq2lJJZaKMVw9qNi4jTC0w==} + dependencies: + spdx-expression-parse: 3.0.1 + spdx-license-ids: 3.0.12 + dev: true + + /spdx-exceptions/2.3.0: + resolution: {integrity: sha512-/tTrYOC7PPI1nUAgx34hUpqXuyJG+DTHJTnIULG4rDygi4xu/tfgmq1e1cIRwRzwZgo4NLySi+ricLkZkw4i5A==} + dev: true + + /spdx-expression-parse/3.0.1: + resolution: {integrity: sha512-cbqHunsQWnJNE6KhVSMsMeH5H/L9EpymbzqTQ3uLwNCLZ1Q481oWaofqH7nO6V07xlXwY6PhQdQ2IedWx/ZK4Q==} + dependencies: + spdx-exceptions: 2.3.0 + spdx-license-ids: 3.0.12 + dev: true + + /spdx-license-ids/3.0.12: + resolution: {integrity: sha512-rr+VVSXtRhO4OHbXUiAF7xW3Bo9DuuF6C5jH+q/x15j2jniycgKbxU09Hr0WqlSLUs4i4ltHGXqTe7VHclYWyA==} + dev: true + + /split-on-first/1.1.0: + resolution: {integrity: sha512-43ZssAJaMusuKWL8sKUBQXHWOpq8d6CfN/u1p4gUzfJkM05C8rxTmYrkIPTXapZpORA6LkkzcUulJ8FqA7Uudw==} + engines: {node: '>=6'} + dev: true + + /split/1.0.1: + resolution: {integrity: sha512-mTyOoPbrivtXnwnIxZRFYRrPNtEFKlpB2fvjSnCQUiAA6qAZzqwna5envK4uk6OIeP17CsdF3rSBGYVBsU0Tkg==} + dependencies: + through: 2.3.8 + dev: true + + /split2/3.2.2: + resolution: {integrity: sha512-9NThjpgZnifTkJpzTZ7Eue85S49QwpNhZTq6GRJwObb6jnLFNGB7Qm73V5HewTROPyxD0C29xqmaI68bQtV+hg==} + dependencies: + readable-stream: 3.6.0 + dev: true + + /sprintf-js/1.0.3: + resolution: {integrity: sha512-D9cPgkvLlV3t3IzL0D0YLvGA9Ahk4PcvVwUbN0dSGr1aP0Nrt4AEnTUbuGvquEC0mA64Gqt1fzirlRs5ibXx8g==} + dev: true + + /sshpk/1.17.0: + resolution: {integrity: sha512-/9HIEs1ZXGhSPE8X6Ccm7Nam1z8KcoCqPdI7ecm1N33EzAetWahvQWVqLZtaZQ+IDKX4IyA2o0gBzqIMkAagHQ==} + engines: {node: '>=0.10.0'} + hasBin: true + dependencies: + asn1: 0.2.6 + assert-plus: 1.0.0 + bcrypt-pbkdf: 1.0.2 + dashdash: 1.14.1 + ecc-jsbn: 0.1.2 + getpass: 0.1.7 + jsbn: 0.1.1 + safer-buffer: 2.1.2 + tweetnacl: 0.14.5 + dev: true + + /ssri/8.0.1: + resolution: {integrity: sha512-97qShzy1AiyxvPNIkLWoGua7xoQzzPjQ0HAH4B0rWKo7SZ6USuPcrUiAFrws0UH8RrbWmgq3LMTObhPIHbbBeQ==} + engines: {node: '>= 8'} + dependencies: + minipass: 3.3.4 + dev: true + + /ssri/9.0.1: + resolution: {integrity: sha512-o57Wcn66jMQvfHG1FlYbWeZWW/dHZhJXjpIcTfXldXEk5nz5lStPo3mK0OJQfGR3RbZUlbISexbljkJzuEj/8Q==} + engines: {node: ^12.13.0 || ^14.15.0 || >=16.0.0} + dependencies: + minipass: 3.3.4 + dev: true + + /strict-uri-encode/2.0.0: + resolution: {integrity: sha512-QwiXZgpRcKkhTj2Scnn++4PKtWsH0kpzZ62L2R6c/LUVYv7hVnZqcg2+sMuT6R7Jusu1vviK/MFsu6kNJfWlEQ==} + engines: {node: '>=4'} + dev: true + + /string-width/1.0.2: + resolution: {integrity: sha512-0XsVpQLnVCXHJfyEs8tC0zpTVIr5PKKsQtkT29IwupnPTjtPmQ3xT/4yCREF9hYkV/3M3kzcUTSAZT6a6h81tw==} + engines: {node: '>=0.10.0'} + dependencies: + code-point-at: 1.1.0 + is-fullwidth-code-point: 1.0.0 + strip-ansi: 3.0.1 + dev: true + + /string-width/4.2.3: + resolution: {integrity: sha512-wKyQRQpjJ0sIp62ErSZdGsjMJWsap5oRNihHhu6G7JVO/9jIB6UyevL+tXuOqrng8j/cxKTWyWUwvSTriiZz/g==} + engines: {node: '>=8'} + dependencies: + emoji-regex: 8.0.0 + is-fullwidth-code-point: 3.0.0 + strip-ansi: 6.0.1 + dev: true + + /string.prototype.trimend/1.0.5: + resolution: {integrity: sha512-I7RGvmjV4pJ7O3kdf+LXFpVfdNOxtCW/2C8f6jNiW4+PQchwxkCDzlk1/7p+Wl4bqFIZeF47qAHXLuHHWKAxog==} + dependencies: + call-bind: 1.0.2 + define-properties: 1.1.4 + es-abstract: 1.20.4 + dev: true + + /string.prototype.trimstart/1.0.5: + resolution: {integrity: sha512-THx16TJCGlsN0o6dl2o6ncWUsdgnLRSA23rRE5pyGBw/mLr3Ej/R2LaqCtgP8VNMGZsvMWnf9ooZPyY2bHvUFg==} + dependencies: + call-bind: 1.0.2 + define-properties: 1.1.4 + es-abstract: 1.20.4 + dev: true + + /string_decoder/1.1.1: + resolution: {integrity: sha512-n/ShnvDi6FHbbVfviro+WojiFzv+s8MPMHBczVePfUpDJLwoLT0ht1l4YwBCbi8pJAveEEdnkHyPyTP/mzRfwg==} + dependencies: + safe-buffer: 5.1.2 + dev: true + + /string_decoder/1.3.0: + resolution: {integrity: sha512-hkRX8U1WjJFd8LsDJ2yQ/wWWxaopEsABU1XfkM8A+j0+85JAGppt16cr1Whg6KIbb4okU6Mql6BOj+uup/wKeA==} + dependencies: + safe-buffer: 5.2.1 + dev: true + + /strip-ansi/3.0.1: + resolution: {integrity: sha512-VhumSSbBqDTP8p2ZLKj40UjBCV4+v8bUSEpUb4KjRgWk9pbqGF4REFj6KEagidb2f/M6AzC0EmFyDNGaw9OCzg==} + engines: {node: '>=0.10.0'} + dependencies: + ansi-regex: 2.1.1 + dev: true + + /strip-ansi/6.0.1: + resolution: {integrity: sha512-Y38VPSHcqkFrCpFnQ9vuSXmquuv5oXOKpGeT6aGrr3o3Gc9AlVa6JBfUSOCnbxGGZF+/0ooI7KrPuUSztUdU5A==} + engines: {node: '>=8'} + dependencies: + ansi-regex: 5.0.1 + dev: true + + /strip-bom/3.0.0: + resolution: {integrity: sha512-vavAMRXOgBVNF6nyEEmL3DBK19iRpDcoIwW+swQ+CbGiu7lju6t+JklA1MHweoWtadgt4ISVUsXLyDq34ddcwA==} + engines: {node: '>=4'} + dev: true + + /strip-bom/4.0.0: + resolution: {integrity: sha512-3xurFv5tEgii33Zi8Jtp55wEIILR9eh34FAW00PZf+JnSsTmV/ioewSgQl97JHvgjoRGwPShsWm+IdrxB35d0w==} + engines: {node: '>=8'} + dev: true + + /strip-final-newline/2.0.0: + resolution: {integrity: sha512-BrpvfNAE3dcvq7ll3xVumzjKjZQ5tI1sEUIKr3Uoks0XUl45St3FlatVqef9prk4jRDzhW6WZg+3bk93y6pLjA==} + engines: {node: '>=6'} + dev: true + + /strip-indent/3.0.0: + resolution: {integrity: sha512-laJTa3Jb+VQpaC6DseHhF7dXVqHTfJPCRDaEbid/drOhgitgYku/letMUqOXFoWV0zIIUbjpdH2t+tYj4bQMRQ==} + engines: {node: '>=8'} + dependencies: + min-indent: 1.0.1 + dev: true + + /strip-json-comments/2.0.1: + resolution: {integrity: sha512-4gB8na07fecVVkOI6Rs4e7T6NOTki5EmL7TUduTs6bu3EdnSycntVJ4re8kgZA+wx9IueI2Y11bfbgwtzuE0KQ==} + engines: {node: '>=0.10.0'} + dev: true + + /strip-json-comments/3.1.1: + resolution: {integrity: sha512-6fPc+R4ihwqP6N/aIv2f1gMH8lOVtWQHoqC4yK6oSDVVocumAsfCqjkXnqiYMhmMwS/mEHLp7Vehlt3ql6lEig==} + engines: {node: '>=8'} + dev: true + + /strong-log-transformer/2.1.0: + resolution: {integrity: sha512-B3Hgul+z0L9a236FAUC9iZsL+nVHgoCJnqCbN588DjYxvGXaXaaFbfmQ/JhvKjZwsOukuR72XbHv71Qkug0HxA==} + engines: {node: '>=4'} + hasBin: true + dependencies: + duplexer: 0.1.2 + minimist: 1.2.7 + through: 2.3.8 + dev: true + + /supports-color/5.5.0: + resolution: {integrity: sha512-QjVjwdXIt408MIiAqCX4oUKsgU2EqAGzs2Ppkm4aQYbjm+ZEWEcW4SfFNTr4uMNZma0ey4f5lgLrkB0aX0QMow==} + engines: {node: '>=4'} + dependencies: + has-flag: 3.0.0 + dev: true + + /supports-color/7.2.0: + resolution: {integrity: sha512-qpCAvRl9stuOHveKsn7HncJRvv501qIacKzQlO/+Lwxc9+0q2wLyv4Dfvt80/DPn2pqOBsJdDiogXGR9+OvwRw==} + engines: {node: '>=8'} + dependencies: + has-flag: 4.0.0 + dev: true + + /supports-preserve-symlinks-flag/1.0.0: + resolution: {integrity: sha512-ot0WnXS9fgdkgIcePe6RHNk1WA8+muPa6cSjeR3V8K27q9BB1rTE3R1p7Hv0z1ZyAc8s6Vvv8DIyWf681MAt0w==} + engines: {node: '>= 0.4'} + dev: true + + /tar/4.4.19: + resolution: {integrity: sha512-a20gEsvHnWe0ygBY8JbxoM4w3SJdhc7ZAuxkLqh+nvNQN2IOt0B5lLgM490X5Hl8FF0dl0tOf2ewFYAlIFgzVA==} + engines: {node: '>=4.5'} + dependencies: + chownr: 1.1.4 + fs-minipass: 1.2.7 + minipass: 2.9.0 + minizlib: 1.3.3 + mkdirp: 0.5.6 + safe-buffer: 5.2.1 + yallist: 3.1.1 + dev: true + + /tar/6.1.11: + resolution: {integrity: sha512-an/KZQzQUkZCkuoAA64hM92X0Urb6VpRhAFllDzz44U2mcD5scmT3zBc4VgVpkugF580+DQn8eAFSyoQt0tznA==} + engines: {node: '>= 10'} + dependencies: + chownr: 2.0.0 + fs-minipass: 2.1.0 + minipass: 3.3.4 + minizlib: 2.1.2 + mkdirp: 1.0.4 + yallist: 4.0.0 + dev: true + + /temp-dir/1.0.0: + resolution: {integrity: sha512-xZFXEGbG7SNC3itwBzI3RYjq/cEhBkx2hJuKGIUOcEULmkQExXiHat2z/qkISYsuR+IKumhEfKKbV5qXmhICFQ==} + engines: {node: '>=4'} + dev: true + + /temp-write/4.0.0: + resolution: {integrity: sha512-HIeWmj77uOOHb0QX7siN3OtwV3CTntquin6TNVg6SHOqCP3hYKmox90eeFOGaY1MqJ9WYDDjkyZrW6qS5AWpbw==} + engines: {node: '>=8'} + dependencies: + graceful-fs: 4.2.10 + is-stream: 2.0.1 + make-dir: 3.1.0 + temp-dir: 1.0.0 + uuid: 3.4.0 + dev: true + + /test-exclude/6.0.0: + resolution: {integrity: sha512-cAGWPIyOHU6zlmg88jwm7VRyXnMN7iV68OGAbYDk/Mh/xC/pzVPlQtY6ngoIH/5/tciuhGfvESU8GrHrcxD56w==} + engines: {node: '>=8'} + dependencies: + '@istanbuljs/schema': 0.1.3 + glob: 7.2.3 + minimatch: 3.1.2 + dev: true + + /text-extensions/1.9.0: + resolution: {integrity: sha512-wiBrwC1EhBelW12Zy26JeOUkQ5mRu+5o8rpsJk5+2t+Y5vE7e842qtZDQ2g1NpX/29HdyFeJ4nSIhI47ENSxlQ==} + engines: {node: '>=0.10'} + dev: true + + /text-table/0.2.0: + resolution: {integrity: sha512-N+8UisAXDGk8PFXP4HAzVR9nbfmVJ3zYLAWiTIoqC5v5isinhr+r5uaO8+7r3BMfuNIufIsA7RdpVgacC2cSpw==} + dev: true + + /through/2.3.8: + resolution: {integrity: sha512-w89qg7PI8wAdvX60bMDP+bFoD5Dvhm9oLheFp5O4a2QF0cSBGsBX4qZmadPMvVqlLJBBci+WqGGOAPvcDeNSVg==} + dev: true + + /through2/2.0.5: + resolution: {integrity: sha512-/mrRod8xqpA+IHSLyGCQ2s8SPHiCDEeQJSep1jqLYeEUClOFG2Qsh+4FU6G9VeqpZnGW/Su8LQGc4YKni5rYSQ==} + dependencies: + readable-stream: 2.3.7 + xtend: 4.0.2 + dev: true + + /through2/4.0.2: + resolution: {integrity: sha512-iOqSav00cVxEEICeD7TjLB1sueEL+81Wpzp2bY17uZjZN0pWZPuo4suZ/61VujxmqSGFfgOcNuTZ85QJwNZQpw==} + dependencies: + readable-stream: 3.6.0 + dev: true + + /tmp/0.0.33: + resolution: {integrity: sha512-jRCJlojKnZ3addtTOjdIqoRuPEKBvNXcGYqzO6zWZX8KfKEpnGY5jfggJQ3EjKuu8D4bJRr0y+cYJFmYbImXGw==} + engines: {node: '>=0.6.0'} + dependencies: + os-tmpdir: 1.0.2 + dev: true + + /to-fast-properties/2.0.0: + resolution: {integrity: sha512-/OaKK0xYrs3DmxRYqL/yDc+FxFUVYhDlXMhRmv3z915w2HF1tnN1omB354j8VUGO/hbRzyD6Y3sA7v7GS/ceog==} + engines: {node: '>=4'} + dev: true + + /to-readable-stream/1.0.0: + resolution: {integrity: sha512-Iq25XBt6zD5npPhlLVXGFN3/gyR2/qODcKNNyTMd4vbm39HUaOiAM4PMq0eMVC/Tkxz+Zjdsc55g9yyz+Yq00Q==} + engines: {node: '>=6'} + dev: true + + /to-regex-range/5.0.1: + resolution: {integrity: sha512-65P7iz6X5yEr1cwcgvQxbbIw7Uk3gOy5dIdtZ4rDveLqhrdJP+Li/Hx6tyK0NEb+2GCyneCMJiGqrADCSNk8sQ==} + engines: {node: '>=8.0'} + dependencies: + is-number: 7.0.0 + dev: true + + /tough-cookie/2.5.0: + resolution: {integrity: sha512-nlLsUzgm1kfLXSXfRZMc1KLAugd4hqJHDTvc2hDIwS3mZAfMEuMbc03SujMF+GEcpaX/qboeycw6iO8JwVv2+g==} + engines: {node: '>=0.8'} + dependencies: + psl: 1.9.0 + punycode: 2.1.1 + dev: true + + /tr46/0.0.3: + resolution: {integrity: sha512-N3WMsuqV66lT30CrXNbEjx4GEwlow3v6rr4mCcv6prnfwhS01rkgyFdjPNBYd9br7LpXV1+Emh01fHnq2Gdgrw==} + dev: true + + /tr46/2.1.0: + resolution: {integrity: sha512-15Ih7phfcdP5YxqiB+iDtLoaTz4Nd35+IiAv0kQ5FNKHzXgdWqPoTIqEDDJmXceQt4JZk6lVPT8lnDlPpGDppw==} + engines: {node: '>=8'} + dependencies: + punycode: 2.1.1 + dev: true + + /trim-newlines/3.0.1: + resolution: {integrity: sha512-c1PTsA3tYrIsLGkJkzHF+w9F2EyxfXGo4UyJc4pFL++FMjnq0HJS69T3M7d//gKrFKwy429bouPescbjecU+Zw==} + engines: {node: '>=8'} + dev: true + + /tsconfig-paths/3.14.1: + resolution: {integrity: sha512-fxDhWnFSLt3VuTwtvJt5fpwxBHg5AdKWMsgcPOOIilyjymcYVZoCQF8fvFRezCNfblEXmi+PcM1eYHeOAgXCOQ==} + dependencies: + '@types/json5': 0.0.29 + json5: 1.0.1 + minimist: 1.2.7 + strip-bom: 3.0.0 + dev: true + + /tslib/1.14.1: + resolution: {integrity: sha512-Xni35NKzjgMrwevysHTCArtLDpPvye8zV/0E4EyYn43P7/7qvQwPh9BGkHewbMulVntbigmcT7rdX3BNo9wRJg==} + dev: true + + /tsutils/3.21.0_typescript@4.8.4: + resolution: {integrity: sha512-mHKK3iUXL+3UF6xL5k0PEhKRUBKPBCv/+RkEOpjRWxxx27KKRBmmA60A9pgOUvMi8GKhRMPEmjBRPzs2W7O1OA==} + 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' + dependencies: + tslib: 1.14.1 + typescript: 4.8.4 + dev: true + + /tunnel-agent/0.6.0: + resolution: {integrity: sha512-McnNiV1l8RYeY8tBgEpuodCC1mLUdbSN+CYBL7kJsJNInOP8UjDDEwdk6Mw60vdLLrr5NHKZhMAOSrR2NZuQ+w==} + dependencies: + safe-buffer: 5.2.1 + dev: true + + /tweetnacl/0.14.5: + resolution: {integrity: sha512-KXXFFdAbFXY4geFIwoyNK+f5Z1b7swfXABfL7HXCmoIWMKU3dmS26672A4EeQtDzLKy7SXmfBu51JolvEKwtGA==} + dev: true + + /type-check/0.4.0: + resolution: {integrity: sha512-XleUoc9uwGXqjWwXaUTZAmzMcFZ5858QA2vvx1Ur5xIcixXIP+8LnFDgRplU30us6teqdlskFfu+ae4K79Ooew==} + engines: {node: '>= 0.8.0'} + dependencies: + prelude-ls: 1.2.1 + dev: true + + /type-fest/0.18.1: + resolution: {integrity: sha512-OIAYXk8+ISY+qTOwkHtKqzAuxchoMiD9Udx+FSGQDuiRR+PJKJHc2NJAXlbhkGwTt/4/nKZxELY1w3ReWOL8mw==} + engines: {node: '>=10'} + dev: true + + /type-fest/0.20.2: + resolution: {integrity: sha512-Ne+eE4r0/iWnpAxD852z3A+N0Bt5RN//NjJwRd2VFHEmrywxf5vsZlh4R6lixl6B+wz/8d+maTSAkN1FIkI3LQ==} + engines: {node: '>=10'} + dev: true + + /type-fest/0.21.3: + resolution: {integrity: sha512-t0rzBq87m3fVcduHDUFhKmyyX+9eo6WQjZvf51Ea/M0Q7+T374Jp1aUiyUl0GKxp8M/OETVHSDvmkyPgvX+X2w==} + engines: {node: '>=10'} + dev: true + + /type-fest/0.4.1: + resolution: {integrity: sha512-IwzA/LSfD2vC1/YDYMv/zHP4rDF1usCwllsDpbolT3D4fUepIO7f9K70jjmUewU/LmGUKJcwcVtDCpnKk4BPMw==} + engines: {node: '>=6'} + dev: true + + /type-fest/0.6.0: + resolution: {integrity: sha512-q+MB8nYR1KDLrgr4G5yemftpMC7/QLqVndBmEEdqzmNj5dcFOO4Oo8qlwZE3ULT3+Zim1F8Kq4cBnikNhlCMlg==} + engines: {node: '>=8'} + dev: true + + /type-fest/0.8.1: + resolution: {integrity: sha512-4dbzIzqvjtgiM5rw1k5rEHtBANKmdudhGyBEajN01fEyhaAIhsoKNy6y7+IN93IfpFtwY9iqi7kD+xwKhQsNJA==} + engines: {node: '>=8'} + dev: true + + /typedarray-to-buffer/3.1.5: + resolution: {integrity: sha512-zdu8XMNEDepKKR+XYOXAVPtWui0ly0NtohUscw+UmaHiAWT8hrV1rr//H6V+0DvJ3OQ19S979M0laLfX8rm82Q==} + dependencies: + is-typedarray: 1.0.0 + dev: true + + /typedarray/0.0.6: + resolution: {integrity: sha512-/aCDEGatGvZ2BIk+HmLf4ifCJFwvKFNb9/JeZPMulfgFracn9QFcAf5GO8B/mweUjSoblS5In0cWhqpfs/5PQA==} + dev: true + + /typescript/4.8.4: + resolution: {integrity: sha512-QCh+85mCy+h0IGff8r5XWzOVSbBO+KfeYrMQh7NJ58QujwcE22u+NUSmUxqF+un70P9GXKxa2HCNiTTMJknyjQ==} + engines: {node: '>=4.2.0'} + hasBin: true + dev: true + + /uglify-js/3.17.3: + resolution: {integrity: sha512-JmMFDME3iufZnBpyKL+uS78LRiC+mK55zWfM5f/pWBJfpOttXAqYfdDGRukYhJuyRinvPVAtUhvy7rlDybNtFg==} + engines: {node: '>=0.8.0'} + hasBin: true + requiresBuild: true + dev: true + optional: true + + /uid-number/0.0.6: + resolution: {integrity: sha512-c461FXIljswCuscZn67xq9PpszkPT6RjheWFQTgCyabJrTUozElanb0YEqv2UGgk247YpcJkFBuSGNvBlpXM9w==} + dev: true + + /umask/1.1.0: + resolution: {integrity: sha512-lE/rxOhmiScJu9L6RTNVgB/zZbF+vGC0/p6D3xnkAePI2o0sMyFG966iR5Ki50OI/0mNi2yaRnxfLsPmEZF/JA==} + dev: true + + /unbox-primitive/1.0.2: + resolution: {integrity: sha512-61pPlCD9h51VoreyJ0BReideM3MDKMKnh6+V9L08331ipq6Q8OFXZYiqP6n/tbHx4s5I9uRhcye6BrbkizkBDw==} + dependencies: + call-bind: 1.0.2 + has-bigints: 1.0.2 + has-symbols: 1.0.3 + which-boxed-primitive: 1.0.2 + dev: true + + /unique-filename/1.1.1: + resolution: {integrity: sha512-Vmp0jIp2ln35UTXuryvjzkjGdRyf9b2lTXuSYUiPmzRcl3FDtYqAwOnTJkAngD9SWhnoJzDbTKwaOrZ+STtxNQ==} + dependencies: + unique-slug: 2.0.2 + dev: true + + /unique-filename/2.0.1: + resolution: {integrity: sha512-ODWHtkkdx3IAR+veKxFV+VBkUMcN+FaqzUUd7IZzt+0zhDZFPFxhlqwPF3YQvMHx1TD0tdgYl+kuPnJ8E6ql7A==} + engines: {node: ^12.13.0 || ^14.15.0 || >=16.0.0} + dependencies: + unique-slug: 3.0.0 + dev: true + + /unique-slug/2.0.2: + resolution: {integrity: sha512-zoWr9ObaxALD3DOPfjPSqxt4fnZiWblxHIgeWqW8x7UqDzEtHEQLzji2cuJYQFCU6KmoJikOYAZlrTHHebjx2w==} + dependencies: + imurmurhash: 0.1.4 + dev: true + + /unique-slug/3.0.0: + resolution: {integrity: sha512-8EyMynh679x/0gqE9fT9oilG+qEt+ibFyqjuVTsZn1+CMxH+XLlpvr2UZx4nVcCwTpx81nICr2JQFkM+HPLq4w==} + engines: {node: ^12.13.0 || ^14.15.0 || >=16.0.0} + dependencies: + imurmurhash: 0.1.4 + dev: true + + /unique-string/2.0.0: + resolution: {integrity: sha512-uNaeirEPvpZWSgzwsPGtU2zVSTrn/8L5q/IexZmH0eH6SA73CmAA5U4GwORTxQAZs95TAXLNqeLoPPNO5gZfWg==} + engines: {node: '>=8'} + dependencies: + crypto-random-string: 2.0.0 + dev: true + + /universal-user-agent/6.0.0: + resolution: {integrity: sha512-isyNax3wXoKaulPDZWHQqbmIx1k2tb9fb3GGDBRxCscfYV2Ch7WxPArBsFEG8s/safwXTT7H4QGhaIkTp9447w==} + dev: true + + /universalify/2.0.0: + resolution: {integrity: sha512-hAZsKq7Yy11Zu1DE0OzWjw7nnLZmJZYTDZZyEFHZdUhV8FkH5MCfoU1XMaxXovpyW5nq5scPqq0ZDP9Zyl04oQ==} + engines: {node: '>= 10.0.0'} + dev: true + + /upath/2.0.1: + resolution: {integrity: sha512-1uEe95xksV1O0CYKXo8vQvN1JEbtJp7lb7C5U9HMsIp6IVwntkH/oNUzyVNQSd4S1sYk2FpSSW44FqMc8qee5w==} + engines: {node: '>=4'} + dev: true + + /update-browserslist-db/1.0.10_browserslist@4.21.4: + resolution: {integrity: sha512-OztqDenkfFkbSG+tRxBeAnCVPckDBcvibKd35yDONx6OU8N7sqgwc7rCbkJ/WcYtVRZ4ba68d6byhC21GFh7sQ==} + hasBin: true + peerDependencies: + browserslist: '>= 4.21.0' + dependencies: + browserslist: 4.21.4 + escalade: 3.1.1 + picocolors: 1.0.0 + dev: true + + /update-notifier/5.1.0: + resolution: {integrity: sha512-ItnICHbeMh9GqUy31hFPrD1kcuZ3rpxDZbf4KUDavXwS0bW5m7SLbDQpGX3UYr072cbrF5hFUs3r5tUsPwjfHw==} + engines: {node: '>=10'} + dependencies: + boxen: 5.1.2 + chalk: 4.1.2 + configstore: 5.0.1 + has-yarn: 2.1.0 + import-lazy: 2.1.0 + is-ci: 2.0.0 + is-installed-globally: 0.4.0 + is-npm: 5.0.0 + is-yarn-global: 0.3.0 + latest-version: 5.1.0 + pupa: 2.1.1 + semver: 7.3.8 + semver-diff: 3.1.1 + xdg-basedir: 4.0.0 + dev: true + + /uri-js/4.4.1: + resolution: {integrity: sha512-7rKUyy33Q1yc98pQ1DAmLtwX109F7TIfWlW1Ydo8Wl1ii1SeHieeh0HHfPeL2fMXK6z0s8ecKs9frCuLJvndBg==} + dependencies: + punycode: 2.1.1 + dev: true + + /url-parse-lax/3.0.0: + resolution: {integrity: sha512-NjFKA0DidqPa5ciFcSrXnAltTtzz84ogy+NebPvfEgAck0+TNg4UJ4IN+fB7zRZfbgUf0syOo9MDxFkDSMuFaQ==} + engines: {node: '>=4'} + dependencies: + prepend-http: 2.0.0 + dev: true + + /util-deprecate/1.0.2: + resolution: {integrity: sha512-EPD5q1uXyFxJpCrLnCc1nHnq3gOa6DZBocAIiI2TaSCA7VCJ1UJDMagCzIkXNsUYfD1daK//LTEQ8xiIbrHtcw==} + dev: true + + /util-promisify/2.1.0: + resolution: {integrity: sha512-K+5eQPYs14b3+E+hmE2J6gCZ4JmMl9DbYS6BeP2CHq6WMuNxErxf5B/n0fz85L8zUuoO6rIzNNmIQDu/j+1OcA==} + dependencies: + object.getownpropertydescriptors: 2.1.4 + dev: true + + /uuid/3.4.0: + resolution: {integrity: sha512-HjSDRw6gZE5JMggctHBcjVak08+KEVhSIiDzFnT9S9aegmp85S/bReBVTb4QTFaRNptJ9kuYaNhnbNEOkbKb/A==} + deprecated: Please upgrade to version 7 or higher. Older versions may use Math.random() in certain circumstances, which is known to be problematic. See https://v8.dev/blog/math-random for details. + hasBin: true + dev: true + + /uuid/8.3.2: + resolution: {integrity: sha512-+NYs2QeMWy+GWFOEm9xnn6HCDp0l7QBD7ml8zLUmJ+93Q5NF0NocErnwkTkXVFNiX3/fpC6afS8Dhb/gz7R7eg==} + hasBin: true + dev: true + + /validate-npm-package-license/3.0.4: + resolution: {integrity: sha512-DpKm2Ui/xN7/HQKCtpZxoRWBhZ9Z0kqtygG8XCgNQ8ZlDnxuQmWhj566j8fN4Cu3/JmbhsDo7fcAJq4s9h27Ew==} + dependencies: + spdx-correct: 3.1.1 + spdx-expression-parse: 3.0.1 + dev: true + + /validate-npm-package-name/3.0.0: + resolution: {integrity: sha512-M6w37eVCMMouJ9V/sdPGnC5H4uDr73/+xdq0FBLO3TFFX1+7wiUY6Es328NN+y43tmY+doUdN9g9J21vqB7iLw==} + dependencies: + builtins: 1.0.3 + dev: true + + /validate-npm-package-name/4.0.0: + resolution: {integrity: sha512-mzR0L8ZDktZjpX4OB46KT+56MAhl4EIazWP/+G/HPGuvfdaqg4YsCdtOm6U9+LOFyYDoh4dpnpxZRB9MQQns5Q==} + engines: {node: ^12.13.0 || ^14.15.0 || >=16.0.0} + dependencies: + builtins: 5.0.1 + dev: true + + /verror/1.10.0: + resolution: {integrity: sha512-ZZKSmDAEFOijERBLkmYfJ+vmk3w+7hOLYDNkRCuRuMJGEmqYNCNLyBBFwWKVMhfwaEF3WOd0Zlw86U/WC/+nYw==} + engines: {'0': node >=0.6.0} + dependencies: + assert-plus: 1.0.0 + core-util-is: 1.0.2 + extsprintf: 1.3.0 + dev: true + + /wcwidth/1.0.1: + resolution: {integrity: sha512-XHPEwS0q6TaxcvG85+8EYkbiCux2XtWG2mkc47Ng2A77BQu9+DqIOJldST4HgPkuea7dvKSj5VgX3P1d4rW8Tg==} + dependencies: + defaults: 1.0.4 + dev: true + + /webidl-conversions/3.0.1: + resolution: {integrity: sha512-2JAn3z8AR6rjK8Sm8orRC0h/bcl/DqL7tRPdGZ4I1CjdF+EaMLmYxBHyXuKL849eucPFhvBoxMsflfOb8kxaeQ==} + dev: true + + /webidl-conversions/6.1.0: + resolution: {integrity: sha512-qBIvFLGiBpLjfwmYAaHPXsn+ho5xZnGvyGvsarywGNc8VyQJUMHJ8OBKGGrPER0okBeMDaan4mNBlgBROxuI8w==} + engines: {node: '>=10.4'} + dev: true + + /whatwg-url/5.0.0: + resolution: {integrity: sha512-saE57nupxk6v3HY35+jzBwYa0rKSy0XR8JSxZPwgLr7ys0IBzhGviA1/TUGJLmSVqs8pb9AnvICXEuOHLprYTw==} + dependencies: + tr46: 0.0.3 + webidl-conversions: 3.0.1 + dev: true + + /whatwg-url/8.7.0: + resolution: {integrity: sha512-gAojqb/m9Q8a5IV96E3fHJM70AzCkgt4uXYX2O7EmuyOnLrViCQlsEBmF9UQIu3/aeAIp2U17rtbpZWNntQqdg==} + engines: {node: '>=10'} + dependencies: + lodash: 4.17.21 + tr46: 2.1.0 + webidl-conversions: 6.1.0 + dev: true + + /which-boxed-primitive/1.0.2: + resolution: {integrity: sha512-bwZdv0AKLpplFY2KZRX6TvyuN7ojjr7lwkg6ml0roIy9YeuSr7JS372qlNW18UQYzgYK9ziGcerWqZOmEn9VNg==} + dependencies: + is-bigint: 1.0.4 + is-boolean-object: 1.1.2 + is-number-object: 1.0.7 + is-string: 1.0.7 + is-symbol: 1.0.4 + dev: true + + /which-module/2.0.0: + resolution: {integrity: sha512-B+enWhmw6cjfVC7kS8Pj9pCrKSc5txArRyaYGe088shv/FGWH+0Rjx/xPgtsWfsUtS27FkP697E4DDhgrgoc0Q==} + dev: true + + /which/1.3.1: + resolution: {integrity: sha512-HxJdYWq1MTIQbJ3nw0cqssHoTNU267KlrDuGZ1WYlxDStUtKUhOaJmh112/TZmHxxUfuJqPXSOm7tDyas0OSIQ==} + hasBin: true + dependencies: + isexe: 2.0.0 + dev: true + + /which/2.0.2: + resolution: {integrity: sha512-BLI3Tl1TW3Pvl70l3yq3Y64i+awpwXqsGBYWkkqMtnbXgrMD+yj7rhW0kuEDxzJaYXGjEW5ogapKNMEKNMjibA==} + engines: {node: '>= 8'} + hasBin: true + dependencies: + isexe: 2.0.0 + dev: true + + /wide-align/1.1.5: + resolution: {integrity: sha512-eDMORYaPNZ4sQIuuYPDHdQvf4gyCF9rEEV/yPxGfwPkRodwEgiMUUXTx/dex+Me0wxx53S+NgUHaP7y3MGlDmg==} + dependencies: + string-width: 1.0.2 + dev: true + + /widest-line/3.1.0: + resolution: {integrity: sha512-NsmoXalsWVDMGupxZ5R08ka9flZjjiLvHVAWYOKtiKM8ujtZWr9cRffak+uSE48+Ob8ObalXpwyeUiyDD6QFgg==} + engines: {node: '>=8'} + dependencies: + string-width: 4.2.3 + dev: true + + /word-wrap/1.2.3: + resolution: {integrity: sha512-Hz/mrNwitNRh/HUAtM/VT/5VH+ygD6DV7mYKZAtHOrbs8U7lvPS6xf7EJKMF0uW1KJCl0H701g3ZGus+muE5vQ==} + engines: {node: '>=0.10.0'} + dev: true + + /wordwrap/1.0.0: + resolution: {integrity: sha512-gvVzJFlPycKc5dZN4yPkP8w7Dc37BtP1yczEneOb4uq34pXZcvrtRTmWV8W+Ume+XCxKgbjM+nevkyFPMybd4Q==} + dev: true + + /wrap-ansi/6.2.0: + resolution: {integrity: sha512-r6lPcBGxZXlIcymEu7InxDMhdW0KDxpLgoFLcguasxCaJ/SOIZwINatK9KY/tf+ZrlywOKU0UDj3ATXUBfxJXA==} + engines: {node: '>=8'} + dependencies: + ansi-styles: 4.3.0 + string-width: 4.2.3 + strip-ansi: 6.0.1 + dev: true + + /wrap-ansi/7.0.0: + resolution: {integrity: sha512-YVGIj2kamLSTxw6NsZjoBxfSwsn0ycdesmc4p+Q21c5zPuZ1pl+NfxVdxPtdHvmNVOQ6XSYG4AUtyt/Fi7D16Q==} + engines: {node: '>=10'} + dependencies: + ansi-styles: 4.3.0 + string-width: 4.2.3 + strip-ansi: 6.0.1 + dev: true + + /wrappy/1.0.2: + resolution: {integrity: sha512-l4Sp/DRseor9wL6EvV2+TuQn63dMkPjZ/sp9XkghTEbV9KlPS1xUsZ3u7/IQO4wxtcFB4bgpQPRcR3QCvezPcQ==} + dev: true + + /write-file-atomic/2.4.3: + resolution: {integrity: sha512-GaETH5wwsX+GcnzhPgKcKjJ6M2Cq3/iZp1WyY/X1CSqrW+jVNM9Y7D8EC2sM4ZG/V8wZlSniJnCKWPmBYAucRQ==} + dependencies: + graceful-fs: 4.2.10 + imurmurhash: 0.1.4 + signal-exit: 3.0.7 + dev: true + + /write-file-atomic/3.0.3: + resolution: {integrity: sha512-AvHcyZ5JnSfq3ioSyjrBkH9yW4m7Ayk8/9My/DD9onKeu/94fwrMocemO2QAJFAlnnDN+ZDS+ZjAR5ua1/PV/Q==} + dependencies: + imurmurhash: 0.1.4 + is-typedarray: 1.0.0 + signal-exit: 3.0.7 + typedarray-to-buffer: 3.1.5 + dev: true + + /write-json-file/3.2.0: + resolution: {integrity: sha512-3xZqT7Byc2uORAatYiP3DHUUAVEkNOswEWNs9H5KXiicRTvzYzYqKjYc4G7p+8pltvAw641lVByKVtMpf+4sYQ==} + engines: {node: '>=6'} + dependencies: + detect-indent: 5.0.0 + graceful-fs: 4.2.10 + make-dir: 2.1.0 + pify: 4.0.1 + sort-keys: 2.0.0 + write-file-atomic: 2.4.3 + dev: true + + /write-json-file/4.3.0: + resolution: {integrity: sha512-PxiShnxf0IlnQuMYOPPhPkhExoCQuTUNPOa/2JWCYTmBquU9njyyDuwRKN26IZBlp4yn1nt+Agh2HOOBl+55HQ==} + engines: {node: '>=8.3'} + dependencies: + detect-indent: 6.1.0 + graceful-fs: 4.2.10 + is-plain-obj: 2.1.0 + make-dir: 3.1.0 + sort-keys: 4.2.0 + write-file-atomic: 3.0.3 + dev: true + + /write-pkg/4.0.0: + resolution: {integrity: sha512-v2UQ+50TNf2rNHJ8NyWttfm/EJUBWMJcx6ZTYZr6Qp52uuegWw/lBkCtCbnYZEmPRNL61m+u67dAmGxo+HTULA==} + engines: {node: '>=8'} + dependencies: + sort-keys: 2.0.0 + type-fest: 0.4.1 + write-json-file: 3.2.0 + dev: true + + /xdg-basedir/4.0.0: + resolution: {integrity: sha512-PSNhEJDejZYV7h50BohL09Er9VaIefr2LMAf3OEmpCkjOi34eYyQYAXUTjEQtZJTKcF0E2UKTh+osDLsgNim9Q==} + engines: {node: '>=8'} + dev: true + + /xtend/4.0.2: + resolution: {integrity: sha512-LKYU1iAXJXUgAXn9URjiu+MWhyUXHsvfp7mcuYm9dSUKK0/CjtrUwFAxD82/mCWbtLsGjFIad0wIsod4zrTAEQ==} + engines: {node: '>=0.4'} + dev: true + + /y18n/4.0.3: + resolution: {integrity: sha512-JKhqTOwSrqNA1NY5lSztJ1GrBiUodLMmIZuLiDaMRJ+itFd+ABVE8XBjOvIWL+rSqNDC74LCSFmlb/U4UZ4hJQ==} + dev: true + + /y18n/5.0.8: + resolution: {integrity: sha512-0pfFzegeDWJHJIAmTLRP2DwHjdF5s7jo9tuztdQxAhINCdvS+3nGINqPd00AphqJR/0LhANUS6/+7SCb98YOfA==} + engines: {node: '>=10'} + dev: true + + /yallist/3.1.1: + resolution: {integrity: sha512-a4UGQaWPH59mOXUYnAG2ewncQS4i4F43Tv3JoAM+s2VDAmS9NsK8GpDMLrCHPksFT7h3K6TOoUNn2pb7RoXx4g==} + dev: true + + /yallist/4.0.0: + resolution: {integrity: sha512-3wdGidZyq5PB084XLES5TpOSRA3wjXAlIWMhum2kRcv/41Sn2emQ0dycQW4uZXLejwKvg6EsvbdlVL+FYEct7A==} + dev: true + + /yaml/1.10.2: + resolution: {integrity: sha512-r3vXyErRCYJ7wg28yvBY5VSoAF8ZvlcW9/BwUzEtUsjvX/DKs24dIkuwjtuprwJJHsbyUbLApepYTR1BN4uHrg==} + engines: {node: '>= 6'} + dev: true + + /yargs-parser/18.1.3: + resolution: {integrity: sha512-o50j0JeToy/4K6OZcaQmW6lyXXKhq7csREXcDwk2omFPJEwUNOVtJKvmDr9EI1fAJZUyZcRF7kxGBWmRXudrCQ==} + engines: {node: '>=6'} + dependencies: + camelcase: 5.3.1 + decamelize: 1.2.0 + dev: true + + /yargs-parser/20.2.4: + resolution: {integrity: sha512-WOkpgNhPTlE73h4VFAFsOnomJVaovO8VqLDzy5saChRBFQFBoMYirowyW+Q9HB4HFF4Z7VZTiG3iSzJJA29yRA==} + engines: {node: '>=10'} + dev: true + + /yargs-parser/20.2.9: + resolution: {integrity: sha512-y11nGElTIV+CT3Zv9t7VKl+Q3hTQoT9a1Qzezhhl6Rp21gJ/IVTW7Z3y9EWXhuUBC2Shnf+DX0antecpAwSP8w==} + engines: {node: '>=10'} + dev: true + + /yargs/15.4.1: + resolution: {integrity: sha512-aePbxDmcYW++PaqBsJ+HYUFwCdv4LVvdnhBy78E57PIor8/OVvhMrADFFEDh8DHDFRv/O9i3lPhsENjO7QX0+A==} + engines: {node: '>=8'} + dependencies: + cliui: 6.0.0 + decamelize: 1.2.0 + find-up: 4.1.0 + get-caller-file: 2.0.5 + require-directory: 2.1.1 + require-main-filename: 2.0.0 + set-blocking: 2.0.0 + string-width: 4.2.3 + which-module: 2.0.0 + y18n: 4.0.3 + yargs-parser: 18.1.3 + dev: true + + /yargs/16.2.0: + resolution: {integrity: sha512-D1mvvtDG0L5ft/jGWkLpG1+m0eQxOfaBvTNELraWj22wSVUMWxZUvYgJYcKh6jGGIkJFhH4IZPQhR4TKpc8mBw==} + engines: {node: '>=10'} + dependencies: + cliui: 7.0.4 + escalade: 3.1.1 + get-caller-file: 2.0.5 + require-directory: 2.1.1 + string-width: 4.2.3 + y18n: 5.0.8 + yargs-parser: 20.2.9 + dev: true + + /yocto-queue/0.1.0: + resolution: {integrity: sha512-rVksvsnNCdJ/ohGc6xgPwyN8eheCxsiLM8mxuE/t/mOVqJewPuO1miLpTHQiRgTKCLexL4MeAFVagts7HmNZ2Q==} + engines: {node: '>=10'} + dev: true diff --git a/tsconfig.json b/tsconfig.json index 1d354f853d..3144d1beb1 100644 --- a/tsconfig.json +++ b/tsconfig.json @@ -1,5 +1,7 @@ { "compilerOptions": { + // TODO: We should remove this but lib types break all the time + "skipLibCheck": true, /* Basic Options */ "target": "es2018", /* Specify ECMAScript target version: 'ES3' (default), 'ES5', 'ES2015', 'ES2016', 'ES2017','ES2018' or 'ESNEXT'. */ "module": "commonjs", /* Specify module code generation: 'none', 'commonjs', 'amd', 'system', 'umd', 'es2015', or 'ESNext'. */