From faa263bb7dbe5aa8d1f25a71ebe6f084ea81ed14 Mon Sep 17 00:00:00 2001 From: dianjuar Date: Tue, 1 Aug 2023 21:27:33 -0500 Subject: [PATCH] feat: remove internal build process Deprecate the built-in build process in favor of `dependsOn` Nx feature. Add support for libraries that doesn't require build process. BREAKING CHANGE: - `ngx-deploy-npm:install`: Added `--dist-folder-path` option as required. - `ngx-deploy-npm:install`: Drop the option `--projects`, now, each project needs to be specified independently using `--project`. - `ngx-deploy-npm:deploy`: `distFolderPath` option is now required. - `ngx-deploy-npm:deploy`: Remove options `noBuild` and `buildTarget`. --- .eslintrc.json | 7 - .../backwards-compatibility-test.yml | 2 +- .github/workflows/basic-test.yml | 26 +- .github/workflows/integration-test.yml | 16 +- .github/workflows/{ci.yml => pr.yml} | 3 + .github/workflows/publishment.yml | 9 +- .github/workflows/test-nx-next.yml | 6 +- .verdaccio/config.yml | 28 + README.md | 69 +- docs/README_contributors.md | 4 +- docs/UML/UML.mdj | 1013 ------ docs/UML/principal-activity-diagram.jpg | Bin 23495 -> 0 bytes .../integration/angular.spec.ts | 4 +- .../integration/minimal.spec.ts | 90 + .../integration/nest.spec.ts | 4 +- .../integration/next.spec.ts | 2 +- .../integration/node.spec.ts | 4 +- .../integration/nx-js.spec.ts | 4 +- .../integration/nx-plugin.spec.ts | 3 +- .../integration/react-native.spec.ts | 6 +- .../integration/react.spec.ts | 2 +- e2e/ngx-deploy-npm-e2e/tests/build.spec.ts | 6 +- e2e/ngx-deploy-npm-e2e/tests/install.spec.ts | 65 +- e2e/ngx-deploy-npm-e2e/tests/publish.spec.ts | 2 +- e2e/ngx-deploy-npm-e2e/utils/lib-test-set.ts | 4 +- nx.json | 1 - package-lock.json | 2853 +++++++++++++++-- package.json | 13 +- packages/ngx-deploy-npm/.eslintrc.json | 7 + packages/ngx-deploy-npm/jest.config.js | 1 + packages/ngx-deploy-npm/migrations.json | 14 + packages/ngx-deploy-npm/package.json | 5 +- packages/ngx-deploy-npm/project.json | 35 +- .../src/__mocks__/generators/index.ts | 290 -- .../ngx-deploy-npm/src/__mocks__/mocks.ts | 116 + .../src/executors/deploy/actions.spec.ts | 168 +- .../src/executors/deploy/actions.ts | 88 +- .../executors/deploy/engine/engine.spec.ts | 16 +- .../src/executors/deploy/engine/engine.ts | 9 +- .../src/executors/deploy/executor.ts | 7 +- .../src/executors/deploy/schema.d.ts | 14 +- .../src/executors/deploy/schema.json | 13 +- .../src/executors/deploy/utils/file-utils.ts | 6 - .../deploy/utils/get-lib-output-path/index.ts | 1 - .../utils/get-lib-output-path/shared/index.ts | 4 - .../dist-folder-path-option.spec.ts | 64 - .../dist-folder-path-option.ts | 39 - .../get-lib-output-path/strategies/index.ts | 3 - .../strategies/ng-package/ng-package.spec.ts | 107 - .../strategies/ng-package/ng-package.ts | 93 - .../output-path-build-option.spec.ts | 52 - .../output-path-build-option.ts | 49 - .../strategies/shared/common-errors.ts | 12 - .../strategies/shared/index.ts | 2 - .../strategies/shared/interfaces.ts | 15 - .../strategy-selector.spec.ts | 91 - .../get-lib-output-path/strategy-selector.ts | 63 - .../src/executors/deploy/utils/index.ts | 2 - .../src/executors/deploy/utils/interfaces.ts | 5 - .../deploy/utils/set-package-version.spec.ts | 15 +- .../deploy/utils/set-package-version.ts | 6 +- .../src/generators/install/generator.spec.ts | 405 +-- .../src/generators/install/generator.ts | 104 +- .../src/generators/install/schema.d.ts | 8 +- .../src/generators/install/schema.json | 22 +- .../src/generators/install/utils/index.ts | 3 - .../src/generators/install/utils/is-a-lib.ts | 28 - .../install/utils/normalize-options.ts | 11 - .../install/utils/validate-projects.ts | 23 - ...replace-buildtarget-for-depends-on.spec.ts | 463 +++ .../replace-buildtarget-for-depends-on.ts | 149 + ...lder-path-on-deploy-target-options.spec.ts | 132 + ...st-folder-path-on-deploy-target-options.ts | 49 + .../src/utils/file-utils.spec.ts | 45 + .../ngx-deploy-npm/src/utils/file-utils.ts | 15 + packages/ngx-deploy-npm/src/utils/index.ts | 2 + .../ngx-deploy-npm/src/utils/is-a-lib.spec.ts | 85 + packages/ngx-deploy-npm/src/utils/is-a-lib.ts | 15 + project.json | 14 + sonar-project.properties | 8 +- tools/create-nx-workspace.sh | 10 +- 81 files changed, 4411 insertions(+), 2838 deletions(-) rename .github/workflows/{ci.yml => pr.yml} (95%) create mode 100644 .verdaccio/config.yml delete mode 100644 docs/UML/UML.mdj delete mode 100644 docs/UML/principal-activity-diagram.jpg create mode 100644 e2e/ngx-deploy-npm-e2e/integration/minimal.spec.ts create mode 100644 packages/ngx-deploy-npm/migrations.json delete mode 100644 packages/ngx-deploy-npm/src/__mocks__/generators/index.ts create mode 100644 packages/ngx-deploy-npm/src/__mocks__/mocks.ts delete mode 100644 packages/ngx-deploy-npm/src/executors/deploy/utils/file-utils.ts delete mode 100644 packages/ngx-deploy-npm/src/executors/deploy/utils/get-lib-output-path/index.ts delete mode 100644 packages/ngx-deploy-npm/src/executors/deploy/utils/get-lib-output-path/shared/index.ts delete mode 100644 packages/ngx-deploy-npm/src/executors/deploy/utils/get-lib-output-path/strategies/dist-folder-path/dist-folder-path-option.spec.ts delete mode 100644 packages/ngx-deploy-npm/src/executors/deploy/utils/get-lib-output-path/strategies/dist-folder-path/dist-folder-path-option.ts delete mode 100644 packages/ngx-deploy-npm/src/executors/deploy/utils/get-lib-output-path/strategies/index.ts delete mode 100644 packages/ngx-deploy-npm/src/executors/deploy/utils/get-lib-output-path/strategies/ng-package/ng-package.spec.ts delete mode 100644 packages/ngx-deploy-npm/src/executors/deploy/utils/get-lib-output-path/strategies/ng-package/ng-package.ts delete mode 100644 packages/ngx-deploy-npm/src/executors/deploy/utils/get-lib-output-path/strategies/output-path-build-option/output-path-build-option.spec.ts delete mode 100644 packages/ngx-deploy-npm/src/executors/deploy/utils/get-lib-output-path/strategies/output-path-build-option/output-path-build-option.ts delete mode 100644 packages/ngx-deploy-npm/src/executors/deploy/utils/get-lib-output-path/strategies/shared/common-errors.ts delete mode 100644 packages/ngx-deploy-npm/src/executors/deploy/utils/get-lib-output-path/strategies/shared/index.ts delete mode 100644 packages/ngx-deploy-npm/src/executors/deploy/utils/get-lib-output-path/strategies/shared/interfaces.ts delete mode 100644 packages/ngx-deploy-npm/src/executors/deploy/utils/get-lib-output-path/strategy-selector.spec.ts delete mode 100644 packages/ngx-deploy-npm/src/executors/deploy/utils/get-lib-output-path/strategy-selector.ts delete mode 100644 packages/ngx-deploy-npm/src/generators/install/utils/index.ts delete mode 100644 packages/ngx-deploy-npm/src/generators/install/utils/is-a-lib.ts delete mode 100644 packages/ngx-deploy-npm/src/generators/install/utils/normalize-options.ts delete mode 100644 packages/ngx-deploy-npm/src/generators/install/utils/validate-projects.ts create mode 100644 packages/ngx-deploy-npm/src/migrations/8.0.0/replace-buildtarget-for-depends-on.spec.ts create mode 100644 packages/ngx-deploy-npm/src/migrations/8.0.0/replace-buildtarget-for-depends-on.ts create mode 100644 packages/ngx-deploy-npm/src/migrations/8.0.0/write-dist-folder-path-on-deploy-target-options.spec.ts create mode 100644 packages/ngx-deploy-npm/src/migrations/8.0.0/write-dist-folder-path-on-deploy-target-options.ts create mode 100644 packages/ngx-deploy-npm/src/utils/file-utils.spec.ts create mode 100644 packages/ngx-deploy-npm/src/utils/file-utils.ts create mode 100644 packages/ngx-deploy-npm/src/utils/index.ts create mode 100644 packages/ngx-deploy-npm/src/utils/is-a-lib.spec.ts create mode 100644 packages/ngx-deploy-npm/src/utils/is-a-lib.ts create mode 100644 project.json diff --git a/.eslintrc.json b/.eslintrc.json index d045f17c..9ca2e830 100644 --- a/.eslintrc.json +++ b/.eslintrc.json @@ -3,13 +3,6 @@ "ignorePatterns": ["**/*"], "plugins": ["@nx"], "overrides": [ - { - "files": ["package.json"], - "parser": "jsonc-eslint-parser", - "rules": { - "@nx/dependency-checks": "error" - } - }, { "files": ["*.ts", "*.tsx", "*.js", "*.jsx"], "rules": { diff --git a/.github/workflows/backwards-compatibility-test.yml b/.github/workflows/backwards-compatibility-test.yml index bad1ad5a..70b1357c 100644 --- a/.github/workflows/backwards-compatibility-test.yml +++ b/.github/workflows/backwards-compatibility-test.yml @@ -5,7 +5,7 @@ on: - cron: '0 0 * * *' # daily at 00:00 jobs: - integration-test: + backwards-compatibility-test: strategy: matrix: nx-version: [latest, '16.10.0'] diff --git a/.github/workflows/basic-test.yml b/.github/workflows/basic-test.yml index bd301aae..c5070655 100644 --- a/.github/workflows/basic-test.yml +++ b/.github/workflows/basic-test.yml @@ -1,13 +1,6 @@ name: Essential Test -on: - workflow_call: - inputs: - # Enable reports on workflow (lint and coverage) - reports: - type: boolean - default: true - required: false +on: workflow_call jobs: lint: @@ -17,14 +10,12 @@ jobs: - uses: ./.github/actions/setup - name: Lint - run: npx nx lint --outputFile="" + run: npx nx lint ngx-deploy-npm - - if: inputs.reports == true - name: Lint report - run: npx nx lint --format=./tools/sonarqube-linter-reporter.js + - name: Lint report + run: npx nx lint-report ngx-deploy-npm - - if: inputs.reports == true - name: Archive lint report results + - name: Archive lint report results uses: actions/upload-artifact@v3 with: name: lint-report-${{ github.sha }} @@ -36,7 +27,7 @@ jobs: - uses: actions/checkout@v3 - uses: ./.github/actions/setup - - run: npx nx build + - run: npx nx build ngx-deploy-npm - name: Archive build result uses: actions/upload-artifact@v3 @@ -53,9 +44,10 @@ jobs: - uses: actions/checkout@v3 - uses: ./.github/actions/setup - - run: npx nx test --configuration="ci" + - run: npx nx test ngx-deploy-npm --configuration="ci" - - name: Archive coverage report + - if: ${{ matrix.os == 'ubuntu-latest' }} + name: Archive coverage report uses: actions/upload-artifact@v3 with: name: ngx-deploy-npm-coverage-report-${{ github.sha }} diff --git a/.github/workflows/integration-test.yml b/.github/workflows/integration-test.yml index ca363e85..0b61216c 100644 --- a/.github/workflows/integration-test.yml +++ b/.github/workflows/integration-test.yml @@ -6,7 +6,7 @@ on: nx-version: type: string description: The Nx Workspace version to run the integration test - required: true + required: false jobs: integration-test: @@ -15,5 +15,17 @@ jobs: - uses: actions/checkout@v3 - uses: ./.github/actions/setup + - name: Read package.json Nx and set default parameter + id: set-default-param + run: | + version=$(jq -r '.devDependencies.nx'package.json) + if [ -z "${{ github.event.inputs.nx-version }}" ]; then + echo "Setting default value for nx-version parameter: $version" + echo "NX_VERSION=$version" >> $GITHUB_ENV + else + echo "Using provided value for nx-version parameter: ${{ github.event.inputs.nx-version }}" + echo "NX_VERSION=${{ github.event.inputs.nx-version }}" >> $GITHUB_ENV + fi + - name: Integration Test - run: npx nx create-nx-workspace -- ${{ inputs.nx-version }} + run: npx nx create-nx-workspace ngx-deploy-npm -- $NX_VERSION diff --git a/.github/workflows/ci.yml b/.github/workflows/pr.yml similarity index 95% rename from .github/workflows/ci.yml rename to .github/workflows/pr.yml index 0a4e643b..d030f057 100644 --- a/.github/workflows/ci.yml +++ b/.github/workflows/pr.yml @@ -36,6 +36,9 @@ jobs: - name: Check if Prettier was run run: npx pretty-quick --check + automated-manual-test: + uses: ./.github/workflows/integration-test.yml + pr-analysis: name: SonarCloud Pr Analysis runs-on: ubuntu-latest diff --git a/.github/workflows/publishment.yml b/.github/workflows/publishment.yml index 3b6bc60b..1168e9f2 100644 --- a/.github/workflows/publishment.yml +++ b/.github/workflows/publishment.yml @@ -17,6 +17,9 @@ jobs: if: ${{ !contains(github.event.head_commit.message, 'chore(release)') }} uses: ./.github/workflows/integration-test-plugins.yml + automated-manual-test: + uses: ./.github/workflows/integration-test.yml + analysis: name: SonarCloud Main Analysis runs-on: ubuntu-latest @@ -43,12 +46,12 @@ jobs: - uses: ./.github/actions/setup - name: Preliminar Version - run: npx nx version --dry-run + run: npx nx version ngx-deploy-npm --dry-run release: environment: production runs-on: ubuntu-latest - needs: [release-preliminar, e2e-test, test] + needs: [release-preliminar, e2e-test, test, automated-manual-test] steps: - uses: actions/checkout@v3 - uses: ./.github/actions/setup @@ -70,7 +73,7 @@ jobs: # which is set up by `setup-node` action. - name: Version and Publishment - run: npx nx version + run: npx nx version ngx-deploy-npm env: NODE_AUTH_TOKEN: ${{ secrets.NPM_TOKEN }} diff --git a/.github/workflows/test-nx-next.yml b/.github/workflows/test-nx-next.yml index d3d4989b..e2b7500e 100644 --- a/.github/workflows/test-nx-next.yml +++ b/.github/workflows/test-nx-next.yml @@ -14,7 +14,7 @@ jobs: with: nx-version: 'next' - name: Lint - run: npx nx lint + run: npx nx lint ngx-deploy-npm build-next: runs-on: ubuntu-latest @@ -25,7 +25,7 @@ jobs: with: nx-version: 'next' - name: Build - run: npx nx build + run: npx nx build ngx-deploy-npm test-next: runs-on: ubuntu-latest @@ -36,7 +36,7 @@ jobs: with: nx-version: 'next' - name: Test - run: npx nx test + run: npx nx test ngx-deploy-npm e2e-next: runs-on: ubuntu-latest diff --git a/.verdaccio/config.yml b/.verdaccio/config.yml new file mode 100644 index 00000000..a007fe82 --- /dev/null +++ b/.verdaccio/config.yml @@ -0,0 +1,28 @@ +# path to a directory with all packages +storage: ../tmp/local-registry/storage + +# a list of other known repositories we can talk to +uplinks: + npmjs: + url: https://registry.npmjs.org/ + maxage: 60m + +packages: + '**': + # give all users (including non-authenticated users) full access + # because it is a local registry + access: $all + publish: $all + unpublish: $all + + # if package is not available locally, proxy requests to npm registry + proxy: npmjs + +# log settings +logs: + type: stdout + format: pretty + level: warn + +publish: + allow_offline: true # set offline to true to allow publish offline diff --git a/README.md b/README.md index dcb0c3ed..407a2b0f 100644 --- a/README.md +++ b/README.md @@ -85,14 +85,12 @@ - [🚀 Quick Start (local development)](#quick-start-local-development) - [🚀 Continuous Delivery](#continuous-delivery) -- [❓What is done when executing `nx deploy`](#what-is-done-when-executing-nx-deploy) - [📦 Options](#options) - [install](#install) - - [`--projects`](#--projects) + - [`--dist-folder-path`](#--dist-folder-path-install) + - [`--project`](#--project) - [`--access`](#--access-install) - [deploy](#deploy) - - [`--build-target`](#--build-target) - - [`--no-build`](#--no-build) - [`--package-version`](#--package-version) - [`--tag`](#--tag) - [`--access`](#--access) @@ -173,63 +171,45 @@ jobs: > You can check the steps suggested in the [CircleCI's guide](https://circleci.com/blog/publishing-npm-packages-using-circleci-2-0/) -## ❓What is done when executing `nx deploy` - -1. Will build the application using the target `build` - - This will be omitted if the parameter `--no-build` is set -2. Execute `npm publish` +## 📦 Options -The following is the activity diagram. +### install -![Execution activity diagram](docs/UML/principal-activity-diagram.jpg) +#### `--dist-folder-path` -## 📦 Options +- **required** +- Example: + - `nx generate ngx-deploy-npm:install --project=lib-1 --dist-folder-path="dist/libs/lib-1"` -### install +Indicates the dist folder path. The path where is located the bundle of your library. The path should be relative to the project's root. -#### `--projects` +#### `--project` -- **optional** +- **required** - Example: - - `nx generate ngx-deploy-npm:install --projects=lib-1,lib-2` – Only `lib-1` and `lib-2` are going to configure + - `nx generate ngx-deploy-npm:install --project=lib-1 --dist-folder-path="dist/libs/lib-1"` – `lib-1` will be configured. It will create the target deploy with the default options on the project `lib-1`. -Specify which libraries should be configured. Useful when you have a workspace with several libraries and don't want to overwrite existing configuration -Should be `,` separated, without spaces. +Specify which library should be configured. #### `--access` - **optional** - Default: `public` - Example: - - `nx generate ngx-deploy-npm:install --access=restricted` + - `nx generate ngx-deploy-npm:install --access=restricted --project=lib-1 --dist-folder-path="dist/libs/lib-1"` Tells the registry whether to publish the package as public or restricted. It only applies to scoped packages, which default to restricted. If you don't have a paid account, you must publish with --access public to publish scoped packages. ### deploy -#### `--build-target` - -- **optional** -- Example: - - `nx deploy --build-target=production` – The configuration `production` is being used to build your package - -The `buildTarget` points to an existing target configuration on your project, -as specified in the `configurations` section of `workspace.json`. - -This option is equivalent to calling the command `nx build --configuration=XXX`. -This command has no effect if the option `--no-build` option is active. - -#### `--no-build` +#### `--dist-folder-path` -- **optional** -- Default: `false` (string) +- **required** - Example: - - `nx deploy` – The library is built in production mode before the deployment - - `nx deploy --no-build` – The library is NOT built, but the deployment process is being made + - `nx deploy --dist-folder-path='dist/libs/my-project'` -Skip build process during deployment. -This option is useful when the building process is handled by something else. -This command causes the `--build-target` setting to have no effect. +Indicate the dist folder path. +The path must relative to project's root. #### `--package-version` @@ -281,20 +261,11 @@ Configure npm to use any compatible registry you like, and even run your own reg For testing: Run through without making any changes. Execute with `--dry-run`, and nothing will happen. It will show a list of the options used on the console. -#### `--dist-folder-path` - -- **optional** -- Example: - - `nx deploy --dist-folder-path 'dist/my-unsupported-project'` - -Indicate a custom dist folder path. -The path must relative to project's root. -Especially useful when ngx-deploy-npm can not detect your library dist folder path automatically. [Write us an issue](https://github.com/bikecoders/ngx-deploy-npm/issues/new) if you think we should support the library you are trying to publish - ## Compatibility overview with Nx | Version | Nx Workspace Version | | ------- | ---------------------- | +| v8.0.0 | `^16.0.0 \|\| ^17.0.0` | | v7.1.0 | `^16.0.0 \|\| ^17.0.0` | | v7.0.1 | `^16.0.0` | diff --git a/docs/README_contributors.md b/docs/README_contributors.md index 5a7380f9..b2f86dbd 100644 --- a/docs/README_contributors.md +++ b/docs/README_contributors.md @@ -66,7 +66,7 @@ There are two ways of debugging: #### Option A), the easy one -> ⚡ **Pre Step:** follow the steps of [yarn link](###angular-workspace) as pre step +> ⚡ **Pre Step:** follow the steps of [yarn link](#angular-workspace) as pre step > > ⚠️ Only works on VsCode! @@ -77,7 +77,7 @@ On VsCode, create a [_JavaScript Debug Terminal_](https://code.visualstudio.com/ #### Option B), the traditional one -> ⚡ **Pre Step:** follow the steps of [yarn link](###angular-workspace) as pre step +> ⚡ **Pre Step:** follow the steps of [yarn link](#angular-workspace) as pre step 1. Use your favorite [Inspector Client](https://nodejs.org/de/docs/guides/debugging-getting-started/#inspector-clients) to debug diff --git a/docs/UML/UML.mdj b/docs/UML/UML.mdj deleted file mode 100644 index 85dad98b..00000000 --- a/docs/UML/UML.mdj +++ /dev/null @@ -1,1013 +0,0 @@ -{ - "_type": "Project", - "_id": "AAAAAAFF+h6SjaM2Hec=", - "name": "Untitled", - "ownedElements": [ - { - "_type": "UMLModel", - "_id": "AAAAAAFF+qBWK6M3Z8Y=", - "_parent": { - "$ref": "AAAAAAFF+h6SjaM2Hec=" - }, - "name": "Model", - "ownedElements": [ - { - "_type": "UMLClassDiagram", - "_id": "AAAAAAFF+qBtyKM79qY=", - "_parent": { - "$ref": "AAAAAAFF+qBWK6M3Z8Y=" - }, - "name": "Main", - "defaultDiagram": true - } - ] - }, - { - "_type": "UMLActivity", - "_id": "AAAAAAF+QmzEMrji1mg=", - "_parent": { - "$ref": "AAAAAAFF+h6SjaM2Hec=" - }, - "name": "Activity1", - "ownedElements": [ - { - "_type": "UMLActivityDiagram", - "_id": "AAAAAAF+QmzEMrjjDuw=", - "_parent": { - "$ref": "AAAAAAF+QmzEMrji1mg=" - }, - "name": "Principal Activity Diagram", - "ownedViews": [ - { - "_type": "UMLControlNodeView", - "_id": "AAAAAAF+QnCWjrjpoaY=", - "_parent": { - "$ref": "AAAAAAF+QmzEMrjjDuw=" - }, - "model": { - "$ref": "AAAAAAF+QnCWjrjnBg0=" - }, - "font": "Arial;13;0", - "containerChangeable": true, - "left": 160, - "top": 120, - "width": 20, - "height": 20 - }, - { - "_type": "UMLControlNodeView", - "_id": "AAAAAAF+QnCbp7juSWU=", - "_parent": { - "$ref": "AAAAAAF+QmzEMrjjDuw=" - }, - "model": { - "$ref": "AAAAAAF+QnCbp7jsu+8=" - }, - "font": "Arial;13;0", - "containerChangeable": true, - "left": 368, - "top": 320, - "width": 26, - "height": 26 - }, - { - "_type": "UMLControlNodeView", - "_id": "AAAAAAF+QnGqMrkcV28=", - "_parent": { - "$ref": "AAAAAAF+QmzEMrjjDuw=" - }, - "model": { - "$ref": "AAAAAAF+QnGqMrkahfk=" - }, - "font": "Arial;13;0", - "containerChangeable": true, - "left": 224, - "top": 112, - "width": 33, - "height": 35 - }, - { - "_type": "UMLActionView", - "_id": "AAAAAAF+QnG9zrkh2SQ=", - "_parent": { - "$ref": "AAAAAAF+QmzEMrjjDuw=" - }, - "model": { - "$ref": "AAAAAAF+QnG9zrkfbUU=" - }, - "subViews": [ - { - "_type": "UMLNameCompartmentView", - "_id": "AAAAAAF+QnG9z7kiwLU=", - "_parent": { - "$ref": "AAAAAAF+QnG9zrkh2SQ=" - }, - "model": { - "$ref": "AAAAAAF+QnG9zrkfbUU=" - }, - "subViews": [ - { - "_type": "LabelView", - "_id": "AAAAAAF+QnG9z7kjyfk=", - "_parent": { - "$ref": "AAAAAAF+QnG9z7kiwLU=" - }, - "visible": false, - "font": "Arial;13;0", - "left": 688, - "top": -336, - "height": 13 - }, - { - "_type": "LabelView", - "_id": "AAAAAAF+QnG9z7kk6Nk=", - "_parent": { - "$ref": "AAAAAAF+QnG9z7kiwLU=" - }, - "font": "Arial;13;1", - "left": 517, - "top": 111, - "width": 106.8818359375, - "height": 13, - "text": "Build Application" - }, - { - "_type": "LabelView", - "_id": "AAAAAAF+QnG9z7kl9lE=", - "_parent": { - "$ref": "AAAAAAF+QnG9z7kiwLU=" - }, - "visible": false, - "font": "Arial;13;0", - "left": 688, - "top": -336, - "width": 86.6708984375, - "height": 13, - "text": "(from Activity1)" - }, - { - "_type": "LabelView", - "_id": "AAAAAAF+QnG9z7kmAYg=", - "_parent": { - "$ref": "AAAAAAF+QnG9z7kiwLU=" - }, - "visible": false, - "font": "Arial;13;0", - "left": 688, - "top": -336, - "height": 13, - "horizontalAlignment": 1 - } - ], - "font": "Arial;13;0", - "left": 512, - "top": 104, - "width": 116.8818359375, - "height": 25, - "stereotypeLabel": { - "$ref": "AAAAAAF+QnG9z7kjyfk=" - }, - "nameLabel": { - "$ref": "AAAAAAF+QnG9z7kk6Nk=" - }, - "namespaceLabel": { - "$ref": "AAAAAAF+QnG9z7kl9lE=" - }, - "propertyLabel": { - "$ref": "AAAAAAF+QnG9z7kmAYg=" - } - } - ], - "font": "Arial;13;0", - "containerChangeable": true, - "left": 512, - "top": 104, - "width": 116.8818359375, - "height": 41, - "nameCompartment": { - "$ref": "AAAAAAF+QnG9z7kiwLU=" - } - }, - { - "_type": "UMLControlFlowView", - "_id": "AAAAAAF+QnIJhrlNAa8=", - "_parent": { - "$ref": "AAAAAAF+QmzEMrjjDuw=" - }, - "model": { - "$ref": "AAAAAAF+QnIJhrlM0yE=" - }, - "subViews": [ - { - "_type": "EdgeLabelView", - "_id": "AAAAAAF+QnIJhrlOoCo=", - "_parent": { - "$ref": "AAAAAAF+QnIJhrlNAa8=" - }, - "model": { - "$ref": "AAAAAAF+QnIJhrlM0yE=" - }, - "font": "Arial;13;0", - "left": 283, - "top": 106, - "width": 201.56982421875, - "height": 13, - "alpha": 1.5707963267948966, - "distance": 15, - "hostEdge": { - "$ref": "AAAAAAF+QnIJhrlNAa8=" - }, - "edgePosition": 1, - "text": "`--no-build` parameter set to `false`" - }, - { - "_type": "EdgeLabelView", - "_id": "AAAAAAF+QnIJhrlPsHs=", - "_parent": { - "$ref": "AAAAAAF+QnIJhrlNAa8=" - }, - "model": { - "$ref": "AAAAAAF+QnIJhrlM0yE=" - }, - "visible": null, - "font": "Arial;13;0", - "left": 383, - "top": 91, - "height": 13, - "alpha": 1.5707963267948966, - "distance": 30, - "hostEdge": { - "$ref": "AAAAAAF+QnIJhrlNAa8=" - }, - "edgePosition": 1 - }, - { - "_type": "EdgeLabelView", - "_id": "AAAAAAF+QnIJhrlQuR8=", - "_parent": { - "$ref": "AAAAAAF+QnIJhrlNAa8=" - }, - "model": { - "$ref": "AAAAAAF+QnIJhrlM0yE=" - }, - "visible": false, - "font": "Arial;13;0", - "left": 384, - "top": 135, - "height": 13, - "alpha": -1.5707963267948966, - "distance": 15, - "hostEdge": { - "$ref": "AAAAAAF+QnIJhrlNAa8=" - }, - "edgePosition": 1 - } - ], - "font": "Arial;13;0", - "head": { - "$ref": "AAAAAAF+QnG9zrkh2SQ=" - }, - "tail": { - "$ref": "AAAAAAF+QnGqMrkcV28=" - }, - "lineStyle": 1, - "points": "257:129;511:125", - "showVisibility": true, - "nameLabel": { - "$ref": "AAAAAAF+QnIJhrlOoCo=" - }, - "stereotypeLabel": { - "$ref": "AAAAAAF+QnIJhrlPsHs=" - }, - "propertyLabel": { - "$ref": "AAAAAAF+QnIJhrlQuR8=" - } - }, - { - "_type": "UMLActionView", - "_id": "AAAAAAF+QnNMxrlkLo0=", - "_parent": { - "$ref": "AAAAAAF+QmzEMrjjDuw=" - }, - "model": { - "$ref": "AAAAAAF+QnNMxrliqzU=" - }, - "subViews": [ - { - "_type": "UMLNameCompartmentView", - "_id": "AAAAAAF+QnNMx7ll1zk=", - "_parent": { - "$ref": "AAAAAAF+QnNMxrlkLo0=" - }, - "model": { - "$ref": "AAAAAAF+QnNMxrliqzU=" - }, - "subViews": [ - { - "_type": "LabelView", - "_id": "AAAAAAF+QnNMx7lm0Ng=", - "_parent": { - "$ref": "AAAAAAF+QnNMx7ll1zk=" - }, - "visible": false, - "font": "Arial;13;0", - "left": -32, - "top": 96, - "height": 13 - }, - { - "_type": "LabelView", - "_id": "AAAAAAF+QnNMx7ln+r4=", - "_parent": { - "$ref": "AAAAAAF+QnNMx7ll1zk=" - }, - "font": "Arial;13;1", - "left": 189, - "top": 319, - "width": 101.82275390625, - "height": 13, - "text": "npm publish" - }, - { - "_type": "LabelView", - "_id": "AAAAAAF+QnNMx7loraE=", - "_parent": { - "$ref": "AAAAAAF+QnNMx7ll1zk=" - }, - "visible": false, - "font": "Arial;13;0", - "left": -32, - "top": 96, - "width": 86.6708984375, - "height": 13, - "text": "(from Activity1)" - }, - { - "_type": "LabelView", - "_id": "AAAAAAF+QnNMx7lpUio=", - "_parent": { - "$ref": "AAAAAAF+QnNMx7ll1zk=" - }, - "visible": false, - "font": "Arial;13;0", - "left": -32, - "top": 96, - "height": 13, - "horizontalAlignment": 1 - } - ], - "font": "Arial;13;0", - "left": 184, - "top": 312, - "width": 111.82275390625, - "height": 25, - "stereotypeLabel": { - "$ref": "AAAAAAF+QnNMx7lm0Ng=" - }, - "nameLabel": { - "$ref": "AAAAAAF+QnNMx7ln+r4=" - }, - "namespaceLabel": { - "$ref": "AAAAAAF+QnNMx7loraE=" - }, - "propertyLabel": { - "$ref": "AAAAAAF+QnNMx7lpUio=" - } - } - ], - "font": "Arial;13;0", - "containerChangeable": true, - "left": 184, - "top": 312, - "width": 111.82275390625, - "height": 41, - "nameCompartment": { - "$ref": "AAAAAAF+QnNMx7ll1zk=" - } - }, - { - "_type": "UMLControlFlowView", - "_id": "AAAAAAF+QnP8ALm4RL4=", - "_parent": { - "$ref": "AAAAAAF+QmzEMrjjDuw=" - }, - "model": { - "$ref": "AAAAAAF+QnP8ALm309I=" - }, - "subViews": [ - { - "_type": "EdgeLabelView", - "_id": "AAAAAAF+QnP8Abm5sXQ=", - "_parent": { - "$ref": "AAAAAAF+QnP8ALm4RL4=" - }, - "model": { - "$ref": "AAAAAAF+QnP8ALm309I=" - }, - "visible": false, - "font": "Arial;13;0", - "left": 201, - "top": 108, - "height": 13, - "alpha": 1.5707963267948966, - "distance": 15, - "hostEdge": { - "$ref": "AAAAAAF+QnP8ALm4RL4=" - }, - "edgePosition": 1 - }, - { - "_type": "EdgeLabelView", - "_id": "AAAAAAF+QnP8Abm60ok=", - "_parent": { - "$ref": "AAAAAAF+QnP8ALm4RL4=" - }, - "model": { - "$ref": "AAAAAAF+QnP8ALm309I=" - }, - "visible": null, - "font": "Arial;13;0", - "left": 201, - "top": 93, - "height": 13, - "alpha": 1.5707963267948966, - "distance": 30, - "hostEdge": { - "$ref": "AAAAAAF+QnP8ALm4RL4=" - }, - "edgePosition": 1 - }, - { - "_type": "EdgeLabelView", - "_id": "AAAAAAF+QnP8Abm7rms=", - "_parent": { - "$ref": "AAAAAAF+QnP8ALm4RL4=" - }, - "model": { - "$ref": "AAAAAAF+QnP8ALm309I=" - }, - "visible": false, - "font": "Arial;13;0", - "left": 201, - "top": 138, - "height": 13, - "alpha": -1.5707963267948966, - "distance": 15, - "hostEdge": { - "$ref": "AAAAAAF+QnP8ALm4RL4=" - }, - "edgePosition": 1 - } - ], - "font": "Arial;13;0", - "head": { - "$ref": "AAAAAAF+QnGqMrkcV28=" - }, - "tail": { - "$ref": "AAAAAAF+QnCWjrjpoaY=" - }, - "lineStyle": 1, - "points": "180:129;223:129", - "showVisibility": true, - "nameLabel": { - "$ref": "AAAAAAF+QnP8Abm5sXQ=" - }, - "stereotypeLabel": { - "$ref": "AAAAAAF+QnP8Abm60ok=" - }, - "propertyLabel": { - "$ref": "AAAAAAF+QnP8Abm7rms=" - } - }, - { - "_type": "UMLControlFlowView", - "_id": "AAAAAAF+QnRy6Ln0Pls=", - "_parent": { - "$ref": "AAAAAAF+QmzEMrjjDuw=" - }, - "model": { - "$ref": "AAAAAAF+QnRy6Lnzo5c=" - }, - "subViews": [ - { - "_type": "EdgeLabelView", - "_id": "AAAAAAF+QnRy6Ln1mXg=", - "_parent": { - "$ref": "AAAAAAF+QnRy6Ln0Pls=" - }, - "model": { - "$ref": "AAAAAAF+QnRy6Lnzo5c=" - }, - "font": "Arial;13;0", - "left": 44, - "top": 191, - "width": 196.5107421875, - "height": 13, - "alpha": -1.5805901321529996, - "distance": 98.00510190801293, - "hostEdge": { - "$ref": "AAAAAAF+QnRy6Ln0Pls=" - }, - "edgePosition": 1, - "text": "`--no-build` parameter set to `true`" - }, - { - "_type": "EdgeLabelView", - "_id": "AAAAAAF+QnRy6Ln2eSQ=", - "_parent": { - "$ref": "AAAAAAF+QnRy6Ln0Pls=" - }, - "model": { - "$ref": "AAAAAAF+QnRy6Lnzo5c=" - }, - "visible": null, - "font": "Arial;13;0", - "left": 270, - "top": 190, - "height": 13, - "alpha": 1.5707963267948966, - "distance": 30, - "hostEdge": { - "$ref": "AAAAAAF+QnRy6Ln0Pls=" - }, - "edgePosition": 1 - }, - { - "_type": "EdgeLabelView", - "_id": "AAAAAAF+QnRy6Ln3XRY=", - "_parent": { - "$ref": "AAAAAAF+QnRy6Ln0Pls=" - }, - "model": { - "$ref": "AAAAAAF+QnRy6Lnzo5c=" - }, - "visible": false, - "font": "Arial;13;0", - "left": 226, - "top": 191, - "height": 13, - "alpha": -1.5707963267948966, - "distance": 15, - "hostEdge": { - "$ref": "AAAAAAF+QnRy6Ln0Pls=" - }, - "edgePosition": 1 - } - ], - "font": "Arial;13;0", - "head": { - "$ref": "AAAAAAF+QnXSprqbVic=" - }, - "tail": { - "$ref": "AAAAAAF+QnGqMrkcV28=" - }, - "lineStyle": 1, - "points": "240:147;242:247", - "showVisibility": true, - "nameLabel": { - "$ref": "AAAAAAF+QnRy6Ln1mXg=" - }, - "stereotypeLabel": { - "$ref": "AAAAAAF+QnRy6Ln2eSQ=" - }, - "propertyLabel": { - "$ref": "AAAAAAF+QnRy6Ln3XRY=" - } - }, - { - "_type": "UMLControlFlowView", - "_id": "AAAAAAF+QnSK4LoFFAQ=", - "_parent": { - "$ref": "AAAAAAF+QmzEMrjjDuw=" - }, - "model": { - "$ref": "AAAAAAF+QnSK4LoEHVg=" - }, - "subViews": [ - { - "_type": "EdgeLabelView", - "_id": "AAAAAAF+QnSK4LoGnik=", - "_parent": { - "$ref": "AAAAAAF+QnSK4LoFFAQ=" - }, - "model": { - "$ref": "AAAAAAF+QnSK4LoEHVg=" - }, - "visible": false, - "font": "Arial;13;0", - "left": 387, - "top": 203, - "height": 13, - "alpha": 1.5707963267948966, - "distance": 15, - "hostEdge": { - "$ref": "AAAAAAF+QnSK4LoFFAQ=" - }, - "edgePosition": 1 - }, - { - "_type": "EdgeLabelView", - "_id": "AAAAAAF+QnSK4LoHh1Y=", - "_parent": { - "$ref": "AAAAAAF+QnSK4LoFFAQ=" - }, - "model": { - "$ref": "AAAAAAF+QnSK4LoEHVg=" - }, - "visible": null, - "font": "Arial;13;0", - "left": 392, - "top": 217, - "height": 13, - "alpha": 1.5707963267948966, - "distance": 30, - "hostEdge": { - "$ref": "AAAAAAF+QnSK4LoFFAQ=" - }, - "edgePosition": 1 - }, - { - "_type": "EdgeLabelView", - "_id": "AAAAAAF+QnSK4LoIAUc=", - "_parent": { - "$ref": "AAAAAAF+QnSK4LoFFAQ=" - }, - "model": { - "$ref": "AAAAAAF+QnSK4LoEHVg=" - }, - "visible": false, - "font": "Arial;13;0", - "left": 376, - "top": 176, - "height": 13, - "alpha": -1.5707963267948966, - "distance": 15, - "hostEdge": { - "$ref": "AAAAAAF+QnSK4LoFFAQ=" - }, - "edgePosition": 1 - } - ], - "font": "Arial;13;0", - "head": { - "$ref": "AAAAAAF+QnXSprqbVic=" - }, - "tail": { - "$ref": "AAAAAAF+QnG9zrkh2SQ=" - }, - "lineStyle": 1, - "points": "515:145;250:247", - "showVisibility": true, - "nameLabel": { - "$ref": "AAAAAAF+QnSK4LoGnik=" - }, - "stereotypeLabel": { - "$ref": "AAAAAAF+QnSK4LoHh1Y=" - }, - "propertyLabel": { - "$ref": "AAAAAAF+QnSK4LoIAUc=" - } - }, - { - "_type": "UMLControlFlowView", - "_id": "AAAAAAF+QnSazroWa4Y=", - "_parent": { - "$ref": "AAAAAAF+QmzEMrjjDuw=" - }, - "model": { - "$ref": "AAAAAAF+QnSazroVrxM=" - }, - "subViews": [ - { - "_type": "EdgeLabelView", - "_id": "AAAAAAF+QnSaz7oXjPA=", - "_parent": { - "$ref": "AAAAAAF+QnSazroWa4Y=" - }, - "model": { - "$ref": "AAAAAAF+QnSazroVrxM=" - }, - "visible": false, - "font": "Arial;13;0", - "left": 255, - "top": 276, - "height": 13, - "alpha": 1.5707963267948966, - "distance": 15, - "hostEdge": { - "$ref": "AAAAAAF+QnSazroWa4Y=" - }, - "edgePosition": 1 - }, - { - "_type": "EdgeLabelView", - "_id": "AAAAAAF+QnSaz7oYVkM=", - "_parent": { - "$ref": "AAAAAAF+QnSazroWa4Y=" - }, - "model": { - "$ref": "AAAAAAF+QnSazroVrxM=" - }, - "visible": null, - "font": "Arial;13;0", - "left": 270, - "top": 277, - "height": 13, - "alpha": 1.5707963267948966, - "distance": 30, - "hostEdge": { - "$ref": "AAAAAAF+QnSazroWa4Y=" - }, - "edgePosition": 1 - }, - { - "_type": "EdgeLabelView", - "_id": "AAAAAAF+QnSaz7oZT0s=", - "_parent": { - "$ref": "AAAAAAF+QnSazroWa4Y=" - }, - "model": { - "$ref": "AAAAAAF+QnSazroVrxM=" - }, - "visible": false, - "font": "Arial;13;0", - "left": 226, - "top": 275, - "height": 13, - "alpha": -1.5707963267948966, - "distance": 15, - "hostEdge": { - "$ref": "AAAAAAF+QnSazroWa4Y=" - }, - "edgePosition": 1 - } - ], - "font": "Arial;13;0", - "head": { - "$ref": "AAAAAAF+QnNMxrlkLo0=" - }, - "tail": { - "$ref": "AAAAAAF+QnXSprqbVic=" - }, - "lineStyle": 1, - "points": "242:254;240:311", - "showVisibility": true, - "nameLabel": { - "$ref": "AAAAAAF+QnSaz7oXjPA=" - }, - "stereotypeLabel": { - "$ref": "AAAAAAF+QnSaz7oYVkM=" - }, - "propertyLabel": { - "$ref": "AAAAAAF+QnSaz7oZT0s=" - } - }, - { - "_type": "UMLControlFlowView", - "_id": "AAAAAAF+QnU8QrozY/A=", - "_parent": { - "$ref": "AAAAAAF+QmzEMrjjDuw=" - }, - "model": { - "$ref": "AAAAAAF+QnU8Qroy6jw=" - }, - "subViews": [ - { - "_type": "EdgeLabelView", - "_id": "AAAAAAF+QnU8Qro04h0=", - "_parent": { - "$ref": "AAAAAAF+QnU8QrozY/A=" - }, - "model": { - "$ref": "AAAAAAF+QnU8Qroy6jw=" - }, - "visible": false, - "font": "Arial;13;0", - "left": 331, - "top": 311, - "height": 13, - "alpha": 1.5707963267948966, - "distance": 15, - "hostEdge": { - "$ref": "AAAAAAF+QnU8QrozY/A=" - }, - "edgePosition": 1 - }, - { - "_type": "EdgeLabelView", - "_id": "AAAAAAF+QnU8Qro1WCE=", - "_parent": { - "$ref": "AAAAAAF+QnU8QrozY/A=" - }, - "model": { - "$ref": "AAAAAAF+QnU8Qroy6jw=" - }, - "visible": null, - "font": "Arial;13;0", - "left": 331, - "top": 296, - "height": 13, - "alpha": 1.5707963267948966, - "distance": 30, - "hostEdge": { - "$ref": "AAAAAAF+QnU8QrozY/A=" - }, - "edgePosition": 1 - }, - { - "_type": "EdgeLabelView", - "_id": "AAAAAAF+QnU8Qro2dl0=", - "_parent": { - "$ref": "AAAAAAF+QnU8QrozY/A=" - }, - "model": { - "$ref": "AAAAAAF+QnU8Qroy6jw=" - }, - "visible": false, - "font": "Arial;13;0", - "left": 331, - "top": 341, - "height": 13, - "alpha": -1.5707963267948966, - "distance": 15, - "hostEdge": { - "$ref": "AAAAAAF+QnU8QrozY/A=" - }, - "edgePosition": 1 - } - ], - "font": "Arial;13;0", - "head": { - "$ref": "AAAAAAF+QnCbp7juSWU=" - }, - "tail": { - "$ref": "AAAAAAF+QnNMxrlkLo0=" - }, - "lineStyle": 1, - "points": "296:332;367:332", - "showVisibility": true, - "nameLabel": { - "$ref": "AAAAAAF+QnU8Qro04h0=" - }, - "stereotypeLabel": { - "$ref": "AAAAAAF+QnU8Qro1WCE=" - }, - "propertyLabel": { - "$ref": "AAAAAAF+QnU8Qro2dl0=" - } - }, - { - "_type": "UMLControlNodeView", - "_id": "AAAAAAF+QnXSprqbVic=", - "_parent": { - "$ref": "AAAAAAF+QmzEMrjjDuw=" - }, - "model": { - "$ref": "AAAAAAF+QnXSpbqZ61c=" - }, - "font": "Arial;13;0", - "containerChangeable": true, - "left": 208, - "top": 248, - "width": 70, - "height": 6 - } - ] - } - ], - "nodes": [ - { - "_type": "UMLInitialNode", - "_id": "AAAAAAF+QnCWjrjnBg0=", - "_parent": { - "$ref": "AAAAAAF+QmzEMrji1mg=" - }, - "name": "InitialNode1" - }, - { - "_type": "UMLActivityFinalNode", - "_id": "AAAAAAF+QnCbp7jsu+8=", - "_parent": { - "$ref": "AAAAAAF+QmzEMrji1mg=" - }, - "name": "ActivityFinalNode1" - }, - { - "_type": "UMLDecisionNode", - "_id": "AAAAAAF+QnGqMrkahfk=", - "_parent": { - "$ref": "AAAAAAF+QmzEMrji1mg=" - }, - "name": "DecisionNode1" - }, - { - "_type": "UMLAction", - "_id": "AAAAAAF+QnG9zrkfbUU=", - "_parent": { - "$ref": "AAAAAAF+QmzEMrji1mg=" - }, - "name": "Build Application" - }, - { - "_type": "UMLAction", - "_id": "AAAAAAF+QnNMxrliqzU=", - "_parent": { - "$ref": "AAAAAAF+QmzEMrji1mg=" - }, - "name": "npm publish" - }, - { - "_type": "UMLJoinNode", - "_id": "AAAAAAF+QnXSpbqZ61c=", - "_parent": { - "$ref": "AAAAAAF+QmzEMrji1mg=" - }, - "name": "JoinNode1" - } - ], - "edges": [ - { - "_type": "UMLControlFlow", - "_id": "AAAAAAF+QnIJhrlM0yE=", - "_parent": { - "$ref": "AAAAAAF+QmzEMrji1mg=" - }, - "name": "`--no-build` parameter set to `false`", - "source": { - "$ref": "AAAAAAF+QnGqMrkahfk=" - }, - "target": { - "$ref": "AAAAAAF+QnG9zrkfbUU=" - } - }, - { - "_type": "UMLControlFlow", - "_id": "AAAAAAF+QnP8ALm309I=", - "_parent": { - "$ref": "AAAAAAF+QmzEMrji1mg=" - }, - "source": { - "$ref": "AAAAAAF+QnCWjrjnBg0=" - }, - "target": { - "$ref": "AAAAAAF+QnGqMrkahfk=" - } - }, - { - "_type": "UMLControlFlow", - "_id": "AAAAAAF+QnRy6Lnzo5c=", - "_parent": { - "$ref": "AAAAAAF+QmzEMrji1mg=" - }, - "name": "`--no-build` parameter set to `true`", - "source": { - "$ref": "AAAAAAF+QnGqMrkahfk=" - }, - "target": { - "$ref": "AAAAAAF+QnXSpbqZ61c=" - }, - "visibility": "private" - }, - { - "_type": "UMLControlFlow", - "_id": "AAAAAAF+QnSK4LoEHVg=", - "_parent": { - "$ref": "AAAAAAF+QmzEMrji1mg=" - }, - "source": { - "$ref": "AAAAAAF+QnG9zrkfbUU=" - }, - "target": { - "$ref": "AAAAAAF+QnXSpbqZ61c=" - } - }, - { - "_type": "UMLControlFlow", - "_id": "AAAAAAF+QnSazroVrxM=", - "_parent": { - "$ref": "AAAAAAF+QmzEMrji1mg=" - }, - "source": { - "$ref": "AAAAAAF+QnXSpbqZ61c=" - }, - "target": { - "$ref": "AAAAAAF+QnNMxrliqzU=" - } - }, - { - "_type": "UMLControlFlow", - "_id": "AAAAAAF+QnU8Qroy6jw=", - "_parent": { - "$ref": "AAAAAAF+QmzEMrji1mg=" - }, - "source": { - "$ref": "AAAAAAF+QnNMxrliqzU=" - }, - "target": { - "$ref": "AAAAAAF+QnCbp7jsu+8=" - } - } - ] - } - ] -} \ No newline at end of file diff --git a/docs/UML/principal-activity-diagram.jpg b/docs/UML/principal-activity-diagram.jpg deleted file mode 100644 index 2f83b4e05bf7c7900eba2b9606eb50010e84eed8..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 23495 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 { const libName = 'angular-lib'; const nxPlugin = '@nx/angular'; - basicSetTestForLibs(libName, nxPlugin); + basicSetTestForLibs(libName, nxPlugin, { + libGeneratorCommandOptions: '--style css --directory libs', + }); }); diff --git a/e2e/ngx-deploy-npm-e2e/integration/minimal.spec.ts b/e2e/ngx-deploy-npm-e2e/integration/minimal.spec.ts new file mode 100644 index 00000000..2c696e65 --- /dev/null +++ b/e2e/ngx-deploy-npm-e2e/integration/minimal.spec.ts @@ -0,0 +1,90 @@ +import { + ensureNxProject, + runNxCommand, + runPackageManagerInstall, + uniq, +} from '@nx/plugin/testing'; +import * as fs from 'fs'; + +describe('Minimal Project', () => { + const setup = async () => { + ensureNxProject('ngx-deploy-npm', 'dist/packages/ngx-deploy-npm'); + runPackageManagerInstall(); + + const uniqLibName = uniq('minimal-lib'); + + const { libRoot } = await createMinimalLib(uniqLibName); + + // Install the project + runNxCommand( + `generate ngx-deploy-npm:install --project="${uniqLibName}" --dist-folder-path="${libRoot}"` + ); + + async function createMinimalLib(libName: string) { + // Create Lib + const libRoot = `libs/${libName}`; + const libRootAbsolutePath = `./tmp/nx-e2e/proj/${libRoot}`; + + // Create the lib folder + await fs.promises.mkdir(libRootAbsolutePath, { + recursive: true, + }); + + const createProjectJsonPromise = fs.promises.writeFile( + `${libRootAbsolutePath}/project.json`, + generateProjectJSON(libName), + 'utf8' + ); + const createPackageJsonPromise = fs.promises.writeFile( + `${libRootAbsolutePath}/package.json`, + generatePackageJSON(libName), + 'utf8' + ); + const createUniqueFilePromise = fs.promises.writeFile( + `${libRootAbsolutePath}/hello-world.js`, + "console.log('Hello World!');", + 'utf8' + ); + await Promise.all([ + createProjectJsonPromise, + createPackageJsonPromise, + createUniqueFilePromise, + ]); + + return { libRoot }; + + function generateProjectJSON(projectName: string): string { + const content = { + name: projectName, + $schema: '../../node_modules/nx/schemas/project-schema.json', + projectType: 'library', + }; + + return JSON.stringify(content, null, 2); + } + + function generatePackageJSON(projectName: string): string { + const content = { + name: `@mock-domain/${projectName}`, + description: 'Minimal LIb', + version: '1.0.0', + }; + + return JSON.stringify(content, null, 2); + } + } + + return { + libRoot, + uniqLibName, + }; + }; + + it('should publish the lib', async () => { + const { uniqLibName } = await setup(); + + expect(() => { + runNxCommand(`deploy ${uniqLibName} --dry-run`); + }).not.toThrow(); + }, 120000); +}); diff --git a/e2e/ngx-deploy-npm-e2e/integration/nest.spec.ts b/e2e/ngx-deploy-npm-e2e/integration/nest.spec.ts index 2fca51a8..37364852 100644 --- a/e2e/ngx-deploy-npm-e2e/integration/nest.spec.ts +++ b/e2e/ngx-deploy-npm-e2e/integration/nest.spec.ts @@ -6,5 +6,7 @@ describe('Nest', () => { const libName = 'nest-lib'; const nxPlugin = '@nx/nest'; - basicSetTestForLibs(libName, nxPlugin); + basicSetTestForLibs(libName, nxPlugin, { + libGeneratorCommandOptions: '--directory="libs"', + }); }); diff --git a/e2e/ngx-deploy-npm-e2e/integration/next.spec.ts b/e2e/ngx-deploy-npm-e2e/integration/next.spec.ts index bcf3de98..bd08a73e 100644 --- a/e2e/ngx-deploy-npm-e2e/integration/next.spec.ts +++ b/e2e/ngx-deploy-npm-e2e/integration/next.spec.ts @@ -7,6 +7,6 @@ describe('Next', () => { const nxPlugin = '@nx/next'; basicSetTestForLibs(libName, nxPlugin, { - libGeneratorCommandOptions: '--style css --bundler rollup', + libGeneratorCommandOptions: '--style css --bundler rollup --directory libs', }); }); diff --git a/e2e/ngx-deploy-npm-e2e/integration/node.spec.ts b/e2e/ngx-deploy-npm-e2e/integration/node.spec.ts index f2ee0e2d..4f77547a 100644 --- a/e2e/ngx-deploy-npm-e2e/integration/node.spec.ts +++ b/e2e/ngx-deploy-npm-e2e/integration/node.spec.ts @@ -6,5 +6,7 @@ describe('Node', () => { const libName = 'node-lib'; const nxPlugin = '@nx/node'; - basicSetTestForLibs(libName, nxPlugin); + basicSetTestForLibs(libName, nxPlugin, { + libGeneratorCommandOptions: '--directory="libs"', + }); }); diff --git a/e2e/ngx-deploy-npm-e2e/integration/nx-js.spec.ts b/e2e/ngx-deploy-npm-e2e/integration/nx-js.spec.ts index 82b09f23..19a7f1c4 100644 --- a/e2e/ngx-deploy-npm-e2e/integration/nx-js.spec.ts +++ b/e2e/ngx-deploy-npm-e2e/integration/nx-js.spec.ts @@ -6,5 +6,7 @@ describe('Nx JS', () => { const libName = 'nx-js'; const nxPlugin = '@nx/js'; - basicSetTestForLibs(libName, nxPlugin); + basicSetTestForLibs(libName, nxPlugin, { + libGeneratorCommandOptions: '--directory="libs"', + }); }); diff --git a/e2e/ngx-deploy-npm-e2e/integration/nx-plugin.spec.ts b/e2e/ngx-deploy-npm-e2e/integration/nx-plugin.spec.ts index 210bd190..eaa99a60 100644 --- a/e2e/ngx-deploy-npm-e2e/integration/nx-plugin.spec.ts +++ b/e2e/ngx-deploy-npm-e2e/integration/nx-plugin.spec.ts @@ -1,6 +1,6 @@ import { initNgxDeployNPMProject, basicSetTestForLibs } from '../utils'; -describe('Nx JS', () => { +describe('Nx Plugin', () => { initNgxDeployNPMProject(); const libName = 'nx-plugin'; @@ -9,5 +9,6 @@ describe('Nx JS', () => { basicSetTestForLibs(libName, nxPlugin, { generator: 'plugin', setPublishableOption: false, + libGeneratorCommandOptions: '--directory="libs"', }); }); diff --git a/e2e/ngx-deploy-npm-e2e/integration/react-native.spec.ts b/e2e/ngx-deploy-npm-e2e/integration/react-native.spec.ts index c170a8dc..00c485c1 100644 --- a/e2e/ngx-deploy-npm-e2e/integration/react-native.spec.ts +++ b/e2e/ngx-deploy-npm-e2e/integration/react-native.spec.ts @@ -24,7 +24,7 @@ describe('React Native', () => { ); }); - generateLib(nxPlugin, uniqLibName); + generateLib(nxPlugin, uniqLibName, '--directory="libs"'); beforeEach(() => { runNxCommand( @@ -33,7 +33,9 @@ describe('React Native', () => { }); // Install the project - installNgxDeployNPMProject(); + installNgxDeployNPMProject( + `--project="${uniqLibName}" --distFolderPath="dist/libs/${uniqLibName}"` + ); it('should publish the lib', () => { expect(() => { diff --git a/e2e/ngx-deploy-npm-e2e/integration/react.spec.ts b/e2e/ngx-deploy-npm-e2e/integration/react.spec.ts index 4b87cda9..7cd8bf83 100644 --- a/e2e/ngx-deploy-npm-e2e/integration/react.spec.ts +++ b/e2e/ngx-deploy-npm-e2e/integration/react.spec.ts @@ -8,6 +8,6 @@ describe('React', () => { basicSetTestForLibs(libName, nxPlugin, { libGeneratorCommandOptions: - '--style css --bundler vite --unitTestRunner jest', + '--style css --bundler vite --unitTestRunner jest --directory="libs"', }); }); diff --git a/e2e/ngx-deploy-npm-e2e/tests/build.spec.ts b/e2e/ngx-deploy-npm-e2e/tests/build.spec.ts index 50555df7..d98fc862 100644 --- a/e2e/ngx-deploy-npm-e2e/tests/build.spec.ts +++ b/e2e/ngx-deploy-npm-e2e/tests/build.spec.ts @@ -16,9 +16,11 @@ describe('build', () => { generateLib(nxPlugin, publishableLib, `--dir="libs"`); // Install the project - installNgxDeployNPMProject(); + installNgxDeployNPMProject( + `--project="${publishableLib}" --distFolderPath="dist/libs/${publishableLib}"` + ); - it('should build the lib', () => { + it('should build the lib due to the `dependsOn` option created on the target', () => { runNxCommand(`deploy ${publishableLib} --dry-run`); expect(() => diff --git a/e2e/ngx-deploy-npm-e2e/tests/install.spec.ts b/e2e/ngx-deploy-npm-e2e/tests/install.spec.ts index 75e4859d..541356bf 100644 --- a/e2e/ngx-deploy-npm-e2e/tests/install.spec.ts +++ b/e2e/ngx-deploy-npm-e2e/tests/install.spec.ts @@ -10,9 +10,10 @@ import { installNgxDeployNPMProject, } from '../utils'; +// TODO, migrate to SIFERS describe('install', () => { const publicLib = 'node-lib1'; - let projectWorkSpacepublicLib: ProjectConfiguration; + let projectWorkSpacePublicLib: ProjectConfiguration; const publicLib2 = 'node-lib2'; let projectWorkSpacePublicLib2: ProjectConfiguration; @@ -23,6 +24,26 @@ describe('install', () => { const libNOTset = 'node-lib-not-set'; let projectWorkSpaceLibNOTSet: ProjectConfiguration; + const expectedTarget = ( + projectName: string, + isBuildable = true, + access: npmAccess = npmAccess.public + ): TargetConfiguration => { + const target: TargetConfiguration = { + executor: 'ngx-deploy-npm:deploy', + options: { + distFolderPath: `dist/libs/${projectName}`, + access: access, + }, + }; + + if (isBuildable) { + target.dependsOn = ['build']; + } + + return target; + }; + initNgxDeployNPMProject(); installDependencies('@nx/node'); @@ -32,14 +53,28 @@ describe('install', () => { generateLib('@nx/node', restrictedLib, `--dir="libs"`); generateLib('@nx/node', libNOTset, `--dir="libs"`); - installNgxDeployNPMProject(`--projects ${publicLib},${publicLib2}`); + const buildMockDistPath = (projectName: string) => { + return `dist/libs/${projectName}`; + }; installNgxDeployNPMProject( - `--projects ${restrictedLib} --access ${npmAccess.restricted}` + `--project ${publicLib} --dist-folder-path="${buildMockDistPath( + publicLib + )}"` + ); + installNgxDeployNPMProject( + `--project ${publicLib2} --dist-folder-path="${buildMockDistPath( + publicLib2 + )}"` + ); + installNgxDeployNPMProject( + `--project=${restrictedLib} --dist-folder-path="${buildMockDistPath( + restrictedLib + )}" --access ${npmAccess.restricted}` ); beforeEach(() => { - projectWorkSpacepublicLib = readJson(`libs/${publicLib}/project.json`); + projectWorkSpacePublicLib = readJson(`libs/${publicLib}/project.json`); projectWorkSpacePublicLib2 = readJson(`libs/${publicLib2}/project.json`); projectWorkSpaceRestrictedLib = readJson( `libs/${restrictedLib}/project.json` @@ -48,28 +83,14 @@ describe('install', () => { }); it('should modify the workspace for publishable libs', () => { - const expectedPublicTarget: TargetConfiguration = { - executor: 'ngx-deploy-npm:deploy', - options: { - access: npmAccess.public, - } as DeployExecutorOptions, - }; - - const expectedRestrictedTarget: TargetConfiguration = { - executor: 'ngx-deploy-npm:deploy', - options: { - access: npmAccess.restricted, - } as DeployExecutorOptions, - }; - - expect(projectWorkSpacepublicLib.targets?.deploy).toEqual( - expectedPublicTarget + expect(projectWorkSpacePublicLib.targets?.deploy).toEqual( + expectedTarget(publicLib) ); expect(projectWorkSpacePublicLib2.targets?.deploy).toEqual( - expectedPublicTarget + expectedTarget(publicLib2) ); expect(projectWorkSpaceRestrictedLib.targets?.deploy).toEqual( - expectedRestrictedTarget + expectedTarget(restrictedLib, true, npmAccess.restricted) ); expect(projectWorkSpaceLibNOTSet.targets?.deploy).toEqual(undefined); }); diff --git a/e2e/ngx-deploy-npm-e2e/tests/publish.spec.ts b/e2e/ngx-deploy-npm-e2e/tests/publish.spec.ts index da2a7dce..262ae3c6 100644 --- a/e2e/ngx-deploy-npm-e2e/tests/publish.spec.ts +++ b/e2e/ngx-deploy-npm-e2e/tests/publish.spec.ts @@ -8,7 +8,7 @@ describe('Publish', () => { const nxPlugin = '@nx/angular'; basicSetTestForLibs(libName, nxPlugin, { - libGeneratorCommandOptions: '--style css', + libGeneratorCommandOptions: '--style css --directory="libs"', }); }); diff --git a/e2e/ngx-deploy-npm-e2e/utils/lib-test-set.ts b/e2e/ngx-deploy-npm-e2e/utils/lib-test-set.ts index 7f013177..4c4a8a43 100644 --- a/e2e/ngx-deploy-npm-e2e/utils/lib-test-set.ts +++ b/e2e/ngx-deploy-npm-e2e/utils/lib-test-set.ts @@ -37,7 +37,9 @@ export function basicSetTestForLibs( ); // Install the project - installNgxDeployNPMProject(); + installNgxDeployNPMProject( + `--project="${uniqLibName}" --distFolderPath="dist/libs/${uniqLibName}"` + ); it('should publish the lib', () => { expect(() => { diff --git a/nx.json b/nx.json index 536f57e2..b2aca8a7 100644 --- a/nx.json +++ b/nx.json @@ -20,7 +20,6 @@ "appsDir": "e2e", "libsDir": "packages" }, - "defaultProject": "ngx-deploy-npm", "namedInputs": { "default": ["{projectRoot}/**/*", "sharedGlobals"], "sharedGlobals": [], diff --git a/package-lock.json b/package-lock.json index e9f1e045..5a2ca19c 100644 --- a/package-lock.json +++ b/package-lock.json @@ -44,7 +44,8 @@ "pretty-quick": "^3.1.3", "ts-jest": "29.1.0", "ts-node": "10.9.1", - "typescript": "5.2.2" + "typescript": "5.2.2", + "verdaccio": "^5.0.4" } }, "node_modules/@aashutoshrathi/word-wrap": { @@ -4066,6 +4067,12 @@ "@types/node": "*" } }, + "node_modules/@types/lodash": { + "version": "4.14.202", + "resolved": "https://registry.npmjs.org/@types/lodash/-/lodash-4.14.202.tgz", + "integrity": "sha512-OvlIYQK9tNneDlS0VN54LLd5uiPCBOp7gS5Z0f1mjoJYBrtStzgmJBxONW3U6OZqdtNzZPmn9BS/7WI7BFFcFQ==", + "dev": true + }, "node_modules/@types/minimatch": { "version": "3.0.5", "resolved": "https://registry.npmjs.org/@types/minimatch/-/minimatch-3.0.5.tgz", @@ -4645,238 +4652,735 @@ "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.46", - "resolved": "https://registry.npmjs.org/@yarnpkg/parsers/-/parsers-3.0.0-rc.46.tgz", - "integrity": "sha512-aiATs7pSutzda/rq8fnuPwTglyVwjM22bNnK2ZgjrpAjQHSSl3lztd2f9evst1W/qnC58DRz7T7QndUDumAR4Q==", + "node_modules/@verdaccio/commons-api": { + "version": "10.2.0", + "resolved": "https://registry.npmjs.org/@verdaccio/commons-api/-/commons-api-10.2.0.tgz", + "integrity": "sha512-F/YZANu4DmpcEV0jronzI7v2fGVWkQ5Mwi+bVmV+ACJ+EzR0c9Jbhtbe5QyLUuzR97t8R5E/Xe53O0cc2LukdQ==", "dev": true, "dependencies": { - "js-yaml": "^3.10.0", - "tslib": "^2.4.0" + "http-errors": "2.0.0", + "http-status-codes": "2.2.0" }, "engines": { - "node": ">=14.15.0" + "node": ">=8" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/verdaccio" } }, - "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==", + "node_modules/@verdaccio/config": { + "version": "7.0.0-next.3", + "resolved": "https://registry.npmjs.org/@verdaccio/config/-/config-7.0.0-next.3.tgz", + "integrity": "sha512-DWBd7THRNDTd1UKwipCYyppdJ5h9sB495FPi9Vaad+DQtN5tNYRx3+aMvuqlDRwHZrssPJeAp8wu8cjLNpMokQ==", "dev": true, "dependencies": { - "argparse": "^2.0.1" + "@verdaccio/core": "7.0.0-next.3", + "@verdaccio/utils": "7.0.0-next.3", + "debug": "4.3.4", + "js-yaml": "4.1.0", + "lodash": "4.17.21", + "minimatch": "7.4.6", + "yup": "0.32.11" }, - "bin": { - "js-yaml": "bin/js-yaml.js" + "engines": { + "node": ">=12" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/verdaccio" } }, - "node_modules/@zkochan/js-yaml/node_modules/argparse": { + "node_modules/@verdaccio/config/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/abab": { - "version": "2.0.6", - "resolved": "https://registry.npmjs.org/abab/-/abab-2.0.6.tgz", - "integrity": "sha512-j2afSsaIENvHZN2B8GOpF566vZ5WVk5opAiMTvWgaQT8DkbOqsTfvNAvHoRGU2zzP8cPoqys+xHTRDWW8L+/BA==", - "dev": true - }, - "node_modules/acorn": { - "version": "8.11.2", - "resolved": "https://registry.npmjs.org/acorn/-/acorn-8.11.2.tgz", - "integrity": "sha512-nc0Axzp/0FILLEVsm4fNwLCwMttvhEI263QtVPQcbpfZZ3ts0hLsZGOpE6czNlid7CJ9MlyH8reXkpsf3YUY4w==", + "node_modules/@verdaccio/config/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, - "bin": { - "acorn": "bin/acorn" - }, - "engines": { - "node": ">=0.4.0" + "dependencies": { + "balanced-match": "^1.0.0" } }, - "node_modules/acorn-globals": { - "version": "7.0.1", - "resolved": "https://registry.npmjs.org/acorn-globals/-/acorn-globals-7.0.1.tgz", - "integrity": "sha512-umOSDSDrfHbTNPuNpC2NSnnA3LUrqpevPb4T9jRx4MagXNS0rs+gwiTcAvqCRmsD6utzsrzNt+ebm00SNWiC3Q==", + "node_modules/@verdaccio/config/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": { - "acorn": "^8.1.0", - "acorn-walk": "^8.0.2" + "argparse": "^2.0.1" + }, + "bin": { + "js-yaml": "bin/js-yaml.js" } }, - "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==", + "node_modules/@verdaccio/config/node_modules/minimatch": { + "version": "7.4.6", + "resolved": "https://registry.npmjs.org/minimatch/-/minimatch-7.4.6.tgz", + "integrity": "sha512-sBz8G/YjVniEz6lKPNpKxXwazJe4c19fEfV2GDMX6AjFz+MX9uDWIZW8XreVhkFW3fkIdTv/gxWr/Kks5FFAVw==", "dev": true, - "peerDependencies": { - "acorn": "^6.0.0 || ^7.0.0 || ^8.0.0" + "dependencies": { + "brace-expansion": "^2.0.1" + }, + "engines": { + "node": ">=10" + }, + "funding": { + "url": "https://github.com/sponsors/isaacs" } }, - "node_modules/acorn-walk": { - "version": "8.3.0", - "resolved": "https://registry.npmjs.org/acorn-walk/-/acorn-walk-8.3.0.tgz", - "integrity": "sha512-FS7hV565M5l1R08MXqo8odwMTB02C2UqzB17RVgu9EyuYFBqJZ3/ZY97sQD5FewVu1UyDFc1yztUDrAwT0EypA==", + "node_modules/@verdaccio/core": { + "version": "7.0.0-next.3", + "resolved": "https://registry.npmjs.org/@verdaccio/core/-/core-7.0.0-next.3.tgz", + "integrity": "sha512-P6XniWZMPcXF/nYRqfyDZDzH5xUMQw9ZiJJ1l+H1SqfTNgxLhRhciOQG39lTvRb3aYnzRtWUjd3ink4IytXpjg==", "dev": true, + "dependencies": { + "ajv": "8.12.0", + "core-js": "3.30.2", + "http-errors": "2.0.0", + "http-status-codes": "2.2.0", + "process-warning": "1.0.0", + "semver": "7.5.4" + }, "engines": { - "node": ">=0.4.0" + "node": ">=12" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/verdaccio" } }, - "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/address": { - "version": "1.2.2", - "resolved": "https://registry.npmjs.org/address/-/address-1.2.2.tgz", - "integrity": "sha512-4B/qKCfeE/ODUaAUpSwfzazo5x29WD4r3vXiWsB7I2mSDAihwEqKO+g8GELZUQSSAo5e1XTYh3ZVfLyxBc12nA==", + "node_modules/@verdaccio/core/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.0.0" + "node": ">=10" } }, - "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==", + "node_modules/@verdaccio/core/node_modules/semver": { + "version": "7.5.4", + "resolved": "https://registry.npmjs.org/semver/-/semver-7.5.4.tgz", + "integrity": "sha512-1bCSESV6Pv+i21Hvpxp3Dx+pSD8lIPt8uVjRrxAUt/nbswYc+tK6Y2btiULjd4+fnq15PX+nqQDC7Oft7WkwcA==", "dev": true, "dependencies": { - "debug": "4" + "lru-cache": "^6.0.0" + }, + "bin": { + "semver": "bin/semver.js" }, "engines": { - "node": ">= 6.0.0" + "node": ">=10" } }, - "node_modules/ajv": { - "version": "8.12.0", - "resolved": "https://registry.npmjs.org/ajv/-/ajv-8.12.0.tgz", - "integrity": "sha512-sRu1kpcO9yLtYxBKvqfTeh9KzZEwO3STyX1HT+4CaDzC6HpTGYhIhPIzj9XuKU7KYDwnaeh5hcOwjy1QuJzBPA==", + "node_modules/@verdaccio/core/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/@verdaccio/file-locking": { + "version": "10.3.1", + "resolved": "https://registry.npmjs.org/@verdaccio/file-locking/-/file-locking-10.3.1.tgz", + "integrity": "sha512-oqYLfv3Yg3mAgw9qhASBpjD50osj2AX4IwbkUtyuhhKGyoFU9eZdrbeW6tpnqUnj6yBMtAPm2eGD4BwQuX400g==", "dev": true, "dependencies": { - "fast-deep-equal": "^3.1.1", - "json-schema-traverse": "^1.0.0", - "require-from-string": "^2.0.2", - "uri-js": "^4.2.2" + "lockfile": "1.0.4" + }, + "engines": { + "node": ">=12" }, "funding": { - "type": "github", - "url": "https://github.com/sponsors/epoberezkin" + "type": "opencollective", + "url": "https://opencollective.com/verdaccio" } }, - "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==", + "node_modules/@verdaccio/local-storage": { + "version": "10.3.3", + "resolved": "https://registry.npmjs.org/@verdaccio/local-storage/-/local-storage-10.3.3.tgz", + "integrity": "sha512-/n0FH+1hxVg80YhYBfJuW7F2AuvLY2fra8/DTCilWDll9Y5yZDxwntZfcKHJLerCA4atrbJtvaqpWkoV3Q9x8w==", "dev": true, + "dependencies": { + "@verdaccio/commons-api": "10.2.0", + "@verdaccio/file-locking": "10.3.1", + "@verdaccio/streams": "10.2.1", + "async": "3.2.4", + "debug": "4.3.4", + "lodash": "4.17.21", + "lowdb": "1.0.0", + "mkdirp": "1.0.4" + }, "engines": { - "node": ">=6" + "node": ">=8" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/verdaccio" } }, - "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==", + "node_modules/@verdaccio/local-storage/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/@verdaccio/logger-7": { + "version": "7.0.0-next.3", + "resolved": "https://registry.npmjs.org/@verdaccio/logger-7/-/logger-7-7.0.0-next.3.tgz", + "integrity": "sha512-JURPnpBnai+1/hgblJ5ayJGHJo068X00QzdZ8u/iB8t6fZRZIVKwVMSBfgOquDUODuJypaueG1MP+twvcUco0Q==", "dev": true, "dependencies": { - "type-fest": "^0.21.3" + "@verdaccio/logger-commons": "7.0.0-next.3", + "pino": "7.11.0" }, "engines": { - "node": ">=8" + "node": ">=12" }, "funding": { - "url": "https://github.com/sponsors/sindresorhus" + "type": "opencollective", + "url": "https://opencollective.com/verdaccio" } }, - "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==", + "node_modules/@verdaccio/logger-commons": { + "version": "7.0.0-next.3", + "resolved": "https://registry.npmjs.org/@verdaccio/logger-commons/-/logger-commons-7.0.0-next.3.tgz", + "integrity": "sha512-j1+9OeGN7WCuo+QZve8fbJEH9ju8rW18H0/xC+OEx6hzmNrmREgc60S5H6OEdSs8mn6wfD4LcMuV8ZDx/JaLMQ==", "dev": true, + "dependencies": { + "@verdaccio/core": "7.0.0-next.3", + "@verdaccio/logger-prettify": "7.0.0-next.1", + "colorette": "2.0.20", + "debug": "4.3.4" + }, "engines": { - "node": ">=8" + "node": ">=12" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/verdaccio" } }, - "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==", + "node_modules/@verdaccio/logger-prettify": { + "version": "7.0.0-next.1", + "resolved": "https://registry.npmjs.org/@verdaccio/logger-prettify/-/logger-prettify-7.0.0-next.1.tgz", + "integrity": "sha512-ZF71AS2k0OiSnKVT05+NUWARZ+yn0keGAlpkgNWU7SHiYeFS1ZDVpapi9PXR23gJ5U756fyPKaqvlRcYgEpsgA==", "dev": true, "dependencies": { - "color-convert": "^2.0.1" + "colorette": "2.0.20", + "dayjs": "1.11.7", + "lodash": "4.17.21", + "pino-abstract-transport": "1.0.0", + "sonic-boom": "3.3.0" }, "engines": { - "node": ">=8" + "node": ">=12" }, "funding": { - "url": "https://github.com/chalk/ansi-styles?sponsor=1" + "type": "opencollective", + "url": "https://opencollective.com/verdaccio" } }, - "node_modules/anymatch": { - "version": "3.1.3", - "resolved": "https://registry.npmjs.org/anymatch/-/anymatch-3.1.3.tgz", - "integrity": "sha512-KMReFUr0B4t+D+OBkjR3KYqvocp2XaSzO55UcB6mgQMd3KbcE+mWTyvVV7D/zsdEbNnV6acZUutkiHQXvTr1Rw==", + "node_modules/@verdaccio/middleware": { + "version": "7.0.0-next.3", + "resolved": "https://registry.npmjs.org/@verdaccio/middleware/-/middleware-7.0.0-next.3.tgz", + "integrity": "sha512-7+K23DIakzewjVUiekU2n6gZVXdPZxStKZIh+wE3NGdfIP4tYOQQajJSoIycoLDAcax+ws6BpKRCt2/3DlU0bA==", "dev": true, "dependencies": { - "normalize-path": "^3.0.0", - "picomatch": "^2.0.4" + "@verdaccio/config": "7.0.0-next.3", + "@verdaccio/core": "7.0.0-next.3", + "@verdaccio/url": "12.0.0-next.3", + "@verdaccio/utils": "7.0.0-next.3", + "debug": "4.3.4", + "express": "4.18.2", + "express-rate-limit": "5.5.1", + "lodash": "4.17.21", + "lru-cache": "7.18.3", + "mime": "2.6.0" }, "engines": { - "node": ">= 8" + "node": ">=12" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/verdaccio" } }, - "node_modules/arch": { - "version": "2.2.0", - "resolved": "https://registry.npmjs.org/arch/-/arch-2.2.0.tgz", - "integrity": "sha512-Of/R0wqp83cgHozfIYLbBMnej79U/SVGOOyuB3VVFv1NRM/PSFMK12x9KVtiYzJqmnU5WR2qp0Z5rHb7sWGnFQ==", + "node_modules/@verdaccio/middleware/node_modules/lru-cache": { + "version": "7.18.3", + "resolved": "https://registry.npmjs.org/lru-cache/-/lru-cache-7.18.3.tgz", + "integrity": "sha512-jumlc0BIUrS3qJGgIkWZsyfAM7NCWiBcCDhnd+3NNM5KbBmLTgHVfWBcg6W+rLUsIpzpERPsvwUP7CckAQSOoA==", "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" - } - ] + "engines": { + "node": ">=12" + } }, - "node_modules/arg": { - "version": "4.1.3", - "resolved": "https://registry.npmjs.org/arg/-/arg-4.1.3.tgz", - "integrity": "sha512-58S9QDqG0Xx27YwPSt9fJxivjYl432YCwfDMfZ+71RAqUrZef7LrKQZ3LHLOwCS4FLNBplP533Zx895SeOCHvA==", - "dev": true + "node_modules/@verdaccio/middleware/node_modules/mime": { + "version": "2.6.0", + "resolved": "https://registry.npmjs.org/mime/-/mime-2.6.0.tgz", + "integrity": "sha512-USPkMeET31rOMiarsBNIHZKLGgvKc/LrjofAnBlOttf5ajRvqiRA8QsenbcooctK6d6Ts6aqZXBA+XbkKthiQg==", + "dev": true, + "bin": { + "mime": "cli.js" + }, + "engines": { + "node": ">=4.0.0" + } }, - "node_modules/argparse": { - "version": "1.0.10", - "resolved": "https://registry.npmjs.org/argparse/-/argparse-1.0.10.tgz", - "integrity": "sha512-o5Roy6tNG4SL/FOkCAN6RzjiakZS25RLYFrcMttJqbdd8BWrnA+fGz57iN5Pb06pvBGvl5gQ0B48dJlslXvoTg==", + "node_modules/@verdaccio/search": { + "version": "7.0.0-next.2", + "resolved": "https://registry.npmjs.org/@verdaccio/search/-/search-7.0.0-next.2.tgz", + "integrity": "sha512-NoGSpubKB+SB4gRMIoEl3E3NkoKE5f0DnANghB3SnMtVxpJGdwZgylosqDxt8swhQ80+16hYdAp6g44uhjVE6Q==", "dev": true, - "dependencies": { - "sprintf-js": "~1.0.2" + "engines": { + "node": ">=12" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/verdaccio" } }, - "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==", + "node_modules/@verdaccio/signature": { + "version": "7.0.0-next.1", + "resolved": "https://registry.npmjs.org/@verdaccio/signature/-/signature-7.0.0-next.1.tgz", + "integrity": "sha512-uq6divC36rcwyBd6+JeTJXQ9K7d4Kuh7HNg6ZMU4ItSCYkLHJjVqNC2Kzo/SdkYNOd11xJuNlYU8NNuhpqpVuw==", "dev": true, + "dependencies": { + "debug": "4.3.4", + "jsonwebtoken": "9.0.2", + "lodash": "4.17.21" + }, "engines": { - "node": ">=8" + "node": ">=12" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/verdaccio" } }, - "node_modules/array-ify": { + "node_modules/@verdaccio/streams": { + "version": "10.2.1", + "resolved": "https://registry.npmjs.org/@verdaccio/streams/-/streams-10.2.1.tgz", + "integrity": "sha512-OojIG/f7UYKxC4dYX8x5ax8QhRx1b8OYUAMz82rUottCuzrssX/4nn5QE7Ank0DUSX3C9l/HPthc4d9uKRJqJQ==", + "dev": true, + "engines": { + "node": ">=12", + "npm": ">=5" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/verdaccio" + } + }, + "node_modules/@verdaccio/tarball": { + "version": "12.0.0-next.3", + "resolved": "https://registry.npmjs.org/@verdaccio/tarball/-/tarball-12.0.0-next.3.tgz", + "integrity": "sha512-pIZ24sVd5TmoKKrOcOvLqDU3rOjpjEpDCn3nsEk8UuWhWG121/3Hxr+9EirBjqWJ7Tnurz5mMl1jpgJNQOylKg==", + "dev": true, + "dependencies": { + "@verdaccio/core": "7.0.0-next.3", + "@verdaccio/url": "12.0.0-next.3", + "@verdaccio/utils": "7.0.0-next.3", + "debug": "4.3.4", + "lodash": "4.17.21" + }, + "engines": { + "node": ">=12" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/verdaccio" + } + }, + "node_modules/@verdaccio/ui-theme": { + "version": "7.0.0-next.3", + "resolved": "https://registry.npmjs.org/@verdaccio/ui-theme/-/ui-theme-7.0.0-next.3.tgz", + "integrity": "sha512-mk132QldyfU1abdzLnV6OsYp46k6l4CtACyw0q3bgT8ytRp3fKF05/31vQObEayNWwhSDr/LvCz12s4e3BuVUA==", + "dev": true + }, + "node_modules/@verdaccio/url": { + "version": "12.0.0-next.3", + "resolved": "https://registry.npmjs.org/@verdaccio/url/-/url-12.0.0-next.3.tgz", + "integrity": "sha512-iuGn4KU0sq7GBfefzMbOotWp3s/43VLSyGPf38AZ44cTErjsRH92q8UOx7E9CsVACPRiBfrhUfsKl8qTk/Qs9Q==", + "dev": true, + "dependencies": { + "@verdaccio/core": "7.0.0-next.3", + "debug": "4.3.4", + "lodash": "4.17.21", + "validator": "13.9.0" + }, + "engines": { + "node": ">=12" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/verdaccio" + } + }, + "node_modules/@verdaccio/url/node_modules/validator": { + "version": "13.9.0", + "resolved": "https://registry.npmjs.org/validator/-/validator-13.9.0.tgz", + "integrity": "sha512-B+dGG8U3fdtM0/aNK4/X8CXq/EcxU2WPrPEkJGslb47qyHsxmbggTWK0yEA4qnYVNF+nxNlN88o14hIcPmSIEA==", + "dev": true, + "engines": { + "node": ">= 0.10" + } + }, + "node_modules/@verdaccio/utils": { + "version": "7.0.0-next.3", + "resolved": "https://registry.npmjs.org/@verdaccio/utils/-/utils-7.0.0-next.3.tgz", + "integrity": "sha512-yawwfOXVgR/woFbe4q30Zqyq95N0lPCry4L9YS7ytts7pPdB6FbDnOW9mFHbdKurkDQ563zxyuBWdBZGITG1kQ==", + "dev": true, + "dependencies": { + "@verdaccio/core": "7.0.0-next.3", + "lodash": "4.17.21", + "minimatch": "7.4.6", + "semver": "7.5.4" + }, + "engines": { + "node": ">=12" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/verdaccio" + } + }, + "node_modules/@verdaccio/utils/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/@verdaccio/utils/node_modules/lru-cache": { + "version": "6.0.0", + "resolved": "https://registry.npmjs.org/lru-cache/-/lru-cache-6.0.0.tgz", + "integrity": "sha512-Jo6dJ04CmSjuznwJSS3pUeWmd/H0ffTlkXXgwZi+eq1UCmqQwCh+eLsYOYCwY991i2Fah4h1BEMCx4qThGbsiA==", + "dev": true, + "dependencies": { + "yallist": "^4.0.0" + }, + "engines": { + "node": ">=10" + } + }, + "node_modules/@verdaccio/utils/node_modules/minimatch": { + "version": "7.4.6", + "resolved": "https://registry.npmjs.org/minimatch/-/minimatch-7.4.6.tgz", + "integrity": "sha512-sBz8G/YjVniEz6lKPNpKxXwazJe4c19fEfV2GDMX6AjFz+MX9uDWIZW8XreVhkFW3fkIdTv/gxWr/Kks5FFAVw==", + "dev": true, + "dependencies": { + "brace-expansion": "^2.0.1" + }, + "engines": { + "node": ">=10" + }, + "funding": { + "url": "https://github.com/sponsors/isaacs" + } + }, + "node_modules/@verdaccio/utils/node_modules/semver": { + "version": "7.5.4", + "resolved": "https://registry.npmjs.org/semver/-/semver-7.5.4.tgz", + "integrity": "sha512-1bCSESV6Pv+i21Hvpxp3Dx+pSD8lIPt8uVjRrxAUt/nbswYc+tK6Y2btiULjd4+fnq15PX+nqQDC7Oft7WkwcA==", + "dev": true, + "dependencies": { + "lru-cache": "^6.0.0" + }, + "bin": { + "semver": "bin/semver.js" + }, + "engines": { + "node": ">=10" + } + }, + "node_modules/@verdaccio/utils/node_modules/yallist": { + "version": "4.0.0", + "resolved": "https://registry.npmjs.org/yallist/-/yallist-4.0.0.tgz", + "integrity": "sha512-3wdGidZyq5PB084XLES5TpOSRA3wjXAlIWMhum2kRcv/41Sn2emQ0dycQW4uZXLejwKvg6EsvbdlVL+FYEct7A==", + "dev": true + }, + "node_modules/@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.46", + "resolved": "https://registry.npmjs.org/@yarnpkg/parsers/-/parsers-3.0.0-rc.46.tgz", + "integrity": "sha512-aiATs7pSutzda/rq8fnuPwTglyVwjM22bNnK2ZgjrpAjQHSSl3lztd2f9evst1W/qnC58DRz7T7QndUDumAR4Q==", + "dev": true, + "dependencies": { + "js-yaml": "^3.10.0", + "tslib": "^2.4.0" + }, + "engines": { + "node": ">=14.15.0" + } + }, + "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/@zkochan/js-yaml/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/abab": { + "version": "2.0.6", + "resolved": "https://registry.npmjs.org/abab/-/abab-2.0.6.tgz", + "integrity": "sha512-j2afSsaIENvHZN2B8GOpF566vZ5WVk5opAiMTvWgaQT8DkbOqsTfvNAvHoRGU2zzP8cPoqys+xHTRDWW8L+/BA==", + "dev": true + }, + "node_modules/abort-controller": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/abort-controller/-/abort-controller-3.0.0.tgz", + "integrity": "sha512-h8lQ8tacZYnR3vNQTgibj+tODHI5/+l06Au2Pcriv/Gmet0eaj4TwWH41sO9wnHDiQsEj19q0drzdWdeAHtweg==", + "dev": true, + "dependencies": { + "event-target-shim": "^5.0.0" + }, + "engines": { + "node": ">=6.5" + } + }, + "node_modules/accepts": { + "version": "1.3.8", + "resolved": "https://registry.npmjs.org/accepts/-/accepts-1.3.8.tgz", + "integrity": "sha512-PYAthTa2m2VKxuvSD3DPC/Gy+U+sOA1LAuT8mkmRuvw+NACSaeXEQ+NHcVF7rONl6qcaxV3Uuemwawk+7+SJLw==", + "dev": true, + "dependencies": { + "mime-types": "~2.1.34", + "negotiator": "0.6.3" + }, + "engines": { + "node": ">= 0.6" + } + }, + "node_modules/acorn": { + "version": "8.11.2", + "resolved": "https://registry.npmjs.org/acorn/-/acorn-8.11.2.tgz", + "integrity": "sha512-nc0Axzp/0FILLEVsm4fNwLCwMttvhEI263QtVPQcbpfZZ3ts0hLsZGOpE6czNlid7CJ9MlyH8reXkpsf3YUY4w==", + "dev": true, + "bin": { + "acorn": "bin/acorn" + }, + "engines": { + "node": ">=0.4.0" + } + }, + "node_modules/acorn-globals": { + "version": "7.0.1", + "resolved": "https://registry.npmjs.org/acorn-globals/-/acorn-globals-7.0.1.tgz", + "integrity": "sha512-umOSDSDrfHbTNPuNpC2NSnnA3LUrqpevPb4T9jRx4MagXNS0rs+gwiTcAvqCRmsD6utzsrzNt+ebm00SNWiC3Q==", + "dev": true, + "dependencies": { + "acorn": "^8.1.0", + "acorn-walk": "^8.0.2" + } + }, + "node_modules/acorn-jsx": { + "version": "5.3.2", + "resolved": "https://registry.npmjs.org/acorn-jsx/-/acorn-jsx-5.3.2.tgz", + "integrity": "sha512-rq9s+JNhf0IChjtDXxllJ7g41oZk5SlXtp0LHwyA5cejwn7vKmKp4pPri6YEePv2PU65sAsegbXtIinmDFDXgQ==", + "dev": true, + "peerDependencies": { + "acorn": "^6.0.0 || ^7.0.0 || ^8.0.0" + } + }, + "node_modules/acorn-walk": { + "version": "8.3.0", + "resolved": "https://registry.npmjs.org/acorn-walk/-/acorn-walk-8.3.0.tgz", + "integrity": "sha512-FS7hV565M5l1R08MXqo8odwMTB02C2UqzB17RVgu9EyuYFBqJZ3/ZY97sQD5FewVu1UyDFc1yztUDrAwT0EypA==", + "dev": true, + "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": "sha512-qQLMr+8o0WC4FZGQTcJiKBVC59JylcPSrTtk6usvmIDFUOCKegapy1VHQwRbFMOFyb/inzUVqHs+eMYKDM1YeQ==", + "dev": true + }, + "node_modules/address": { + "version": "1.2.2", + "resolved": "https://registry.npmjs.org/address/-/address-1.2.2.tgz", + "integrity": "sha512-4B/qKCfeE/ODUaAUpSwfzazo5x29WD4r3vXiWsB7I2mSDAihwEqKO+g8GELZUQSSAo5e1XTYh3ZVfLyxBc12nA==", + "dev": true, + "engines": { + "node": ">= 10.0.0" + } + }, + "node_modules/agent-base": { + "version": "6.0.2", + "resolved": "https://registry.npmjs.org/agent-base/-/agent-base-6.0.2.tgz", + "integrity": "sha512-RZNwNclF7+MS/8bDg70amg32dyeZGZxiDuQmZxKLAlQjr3jGyLx+4Kkk58UO7D2QdgFIQCovuSuZESne6RG6XQ==", + "dev": true, + "dependencies": { + "debug": "4" + }, + "engines": { + "node": ">= 6.0.0" + } + }, + "node_modules/ajv": { + "version": "8.12.0", + "resolved": "https://registry.npmjs.org/ajv/-/ajv-8.12.0.tgz", + "integrity": "sha512-sRu1kpcO9yLtYxBKvqfTeh9KzZEwO3STyX1HT+4CaDzC6HpTGYhIhPIzj9XuKU7KYDwnaeh5hcOwjy1QuJzBPA==", + "dev": true, + "dependencies": { + "fast-deep-equal": "^3.1.1", + "json-schema-traverse": "^1.0.0", + "require-from-string": "^2.0.2", + "uri-js": "^4.2.2" + }, + "funding": { + "type": "github", + "url": "https://github.com/sponsors/epoberezkin" + } + }, + "node_modules/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-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.3", + "resolved": "https://registry.npmjs.org/anymatch/-/anymatch-3.1.3.tgz", + "integrity": "sha512-KMReFUr0B4t+D+OBkjR3KYqvocp2XaSzO55UcB6mgQMd3KbcE+mWTyvVV7D/zsdEbNnV6acZUutkiHQXvTr1Rw==", + "dev": true, + "dependencies": { + "normalize-path": "^3.0.0", + "picomatch": "^2.0.4" + }, + "engines": { + "node": ">= 8" + } + }, + "node_modules/apache-md5": { + "version": "1.1.8", + "resolved": "https://registry.npmjs.org/apache-md5/-/apache-md5-1.1.8.tgz", + "integrity": "sha512-FCAJojipPn0bXjuEpjOOOMN8FZDkxfWWp4JGN9mifU2IhxvKyXZYqpzPHdnTSUpmPDy+tsslB6Z1g+Vg6nVbYA==", + "dev": true, + "engines": { + "node": ">=8" + } + }, + "node_modules/arch": { + "version": "2.2.0", + "resolved": "https://registry.npmjs.org/arch/-/arch-2.2.0.tgz", + "integrity": "sha512-Of/R0wqp83cgHozfIYLbBMnej79U/SVGOOyuB3VVFv1NRM/PSFMK12x9KVtiYzJqmnU5WR2qp0Z5rHb7sWGnFQ==", + "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/arg": { + "version": "4.1.3", + "resolved": "https://registry.npmjs.org/arg/-/arg-4.1.3.tgz", + "integrity": "sha512-58S9QDqG0Xx27YwPSt9fJxivjYl432YCwfDMfZ+71RAqUrZef7LrKQZ3LHLOwCS4FLNBplP533Zx895SeOCHvA==", + "dev": true + }, + "node_modules/argparse": { + "version": "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/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": "sha512-PCVAQswWemu6UdxsDFFX/+gVeYqKAod3D3UVm91jHwynguOwAvYPhx8nNlM++NqRcK6CxxpUafjmhIdKiHibqg==", + "dev": true + }, + "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==", @@ -4900,6 +5404,24 @@ "node": ">=0.10.0" } }, + "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/assert-plus": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/assert-plus/-/assert-plus-1.0.0.tgz", + "integrity": "sha512-NfJ4UzBCcQGLDlQq7nHxH+tv3kyZ0hHQqF5BO6J7tNJeP5do1llPr8dZ8zHonfhAu0PHAdMkSo+8o0wxg9lZWw==", + "dev": true, + "engines": { + "node": ">=0.8" + } + }, "node_modules/async": { "version": "3.2.5", "resolved": "https://registry.npmjs.org/async/-/async-3.2.5.tgz", @@ -4921,6 +5443,30 @@ "node": ">= 4.0.0" } }, + "node_modules/atomic-sleep": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/atomic-sleep/-/atomic-sleep-1.0.0.tgz", + "integrity": "sha512-kNOjDqAh7px0XWNI+4QbzoiR/nTkHAWNud2uvnJquD1/x5a7EQZMJT0AczqK0Qn67oY/TTQ1LbUKajZpp3I9tQ==", + "dev": true, + "engines": { + "node": ">=8.0.0" + } + }, + "node_modules/aws-sign2": { + "version": "0.7.0", + "resolved": "https://registry.npmjs.org/aws-sign2/-/aws-sign2-0.7.0.tgz", + "integrity": "sha512-08kcGqnYf/YmjoRhfxyu+CLxBjUtHLXLXX/vUfx9l2LYzG3c1m61nrpyFUZI6zeS+Li/wWMMidD9KgrqtGq3mA==", + "dev": true, + "engines": { + "node": "*" + } + }, + "node_modules/aws4": { + "version": "1.12.0", + "resolved": "https://registry.npmjs.org/aws4/-/aws4-1.12.0.tgz", + "integrity": "sha512-NmWvPnx0F1SfrQbYwOi7OeaNGokp9XhzNioJ/CSBs8Qa4vxug81mhJEAVZwxXuBmYB5KDRfMq/F3RR0BIU7sWg==", + "dev": true + }, "node_modules/axios": { "version": "1.6.2", "resolved": "https://registry.npmjs.org/axios/-/axios-1.6.2.tgz", @@ -5172,6 +5718,21 @@ } ] }, + "node_modules/bcrypt-pbkdf": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/bcrypt-pbkdf/-/bcrypt-pbkdf-1.0.2.tgz", + "integrity": "sha512-qeFIXtP4MSoi6NLqO12WfqARWWuCKi2Rn/9hJLEmtB5yTNr9DqFWkJRCf2qShWzPeAMRnOgCrq0sg/KLv5ES9w==", + "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": "sha512-V/Hy/X9Vt7f3BbPJEi8BdVFMByHi+jNXrYkW3huaybV/kQ0KJg0Y6PkEMbn+zeT+i+SiKZ/HMqJGIIt4LZDqNQ==", + "dev": true + }, "node_modules/bin-check": { "version": "4.1.0", "resolved": "https://registry.npmjs.org/bin-check/-/bin-check-4.1.0.tgz", @@ -5346,6 +5907,54 @@ "readable-stream": "^3.4.0" } }, + "node_modules/body-parser": { + "version": "1.20.1", + "resolved": "https://registry.npmjs.org/body-parser/-/body-parser-1.20.1.tgz", + "integrity": "sha512-jWi7abTbYwajOytWCQc37VulmWiRae5RyTpaCyDcS5/lMdtwSz5lOpDE67srw/HYe35f1z3fDQw+3txg7gNtWw==", + "dev": true, + "dependencies": { + "bytes": "3.1.2", + "content-type": "~1.0.4", + "debug": "2.6.9", + "depd": "2.0.0", + "destroy": "1.2.0", + "http-errors": "2.0.0", + "iconv-lite": "0.4.24", + "on-finished": "2.4.1", + "qs": "6.11.0", + "raw-body": "2.5.1", + "type-is": "~1.6.18", + "unpipe": "1.0.0" + }, + "engines": { + "node": ">= 0.8", + "npm": "1.2.8000 || >= 1.4.16" + } + }, + "node_modules/body-parser/node_modules/bytes": { + "version": "3.1.2", + "resolved": "https://registry.npmjs.org/bytes/-/bytes-3.1.2.tgz", + "integrity": "sha512-/Nf7TyzTx6S3yRJObOAV7956r8cr2+Oj8AC5dt8wSP3BQAoeX58NoHyCU8P8zGkNXStjTSi6fzO6F0pBdcYbEg==", + "dev": true, + "engines": { + "node": ">= 0.8" + } + }, + "node_modules/body-parser/node_modules/debug": { + "version": "2.6.9", + "resolved": "https://registry.npmjs.org/debug/-/debug-2.6.9.tgz", + "integrity": "sha512-bC7ElrdJaJnPbAP+1EotYvqZsb3ecl5wi6Bfi6BJTUcNowp6cvspg0jXznRTKDjm/E7AdgFBVeAPVMNcKGsHMA==", + "dev": true, + "dependencies": { + "ms": "2.0.0" + } + }, + "node_modules/body-parser/node_modules/ms": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/ms/-/ms-2.0.0.tgz", + "integrity": "sha512-Tpp60P6IUJDTuOq/5Z8cdskzJujfwqfOTkrwIwj7IRISpnkJnT6SyJ4PCPnGMoFjC9ddhal5KVIYtAt97ix05A==", + "dev": true + }, "node_modules/brace-expansion": { "version": "1.1.11", "resolved": "https://registry.npmjs.org/brace-expansion/-/brace-expansion-1.1.11.tgz", @@ -5445,6 +6054,12 @@ "ieee754": "^1.1.13" } }, + "node_modules/buffer-equal-constant-time": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/buffer-equal-constant-time/-/buffer-equal-constant-time-1.0.1.tgz", + "integrity": "sha512-zRpUiDwd/xk6ADqPMATG8vc9VPrkck7T07OIx0gnjmJAnHnTVXNQG3vfvWNuiZIkwu9KrKdA1iJKfsfTVxE6NA==", + "dev": true + }, "node_modules/buffer-from": { "version": "1.1.2", "resolved": "https://registry.npmjs.org/buffer-from/-/buffer-from-1.1.2.tgz", @@ -5460,6 +6075,15 @@ "semver": "^7.0.0" } }, + "node_modules/bytes": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/bytes/-/bytes-3.0.0.tgz", + "integrity": "sha512-pMhOfFDPiv9t5jjIXkHosWmkSyQbvsgEVNkz0ERHbuLh2T/7j4Mqqpz523Fe8MVY89KC6Sh/QfS2sM+SjgFDcw==", + "dev": true, + "engines": { + "node": ">= 0.8" + } + }, "node_modules/cacheable-lookup": { "version": "5.0.4", "resolved": "https://registry.npmjs.org/cacheable-lookup/-/cacheable-lookup-5.0.4.tgz", @@ -5511,6 +6135,20 @@ "node": ">=6" } }, + "node_modules/call-bind": { + "version": "1.0.5", + "resolved": "https://registry.npmjs.org/call-bind/-/call-bind-1.0.5.tgz", + "integrity": "sha512-C3nQxfFZxFRVoJoGKKI8y3MOEo129NQ+FgQ08iye+Mk4zNZZGdjfs06bVTr+DBSlA66Q2VEcMki/cUCP4SercQ==", + "dev": true, + "dependencies": { + "function-bind": "^1.1.2", + "get-intrinsic": "^1.2.1", + "set-function-length": "^1.1.1" + }, + "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", @@ -5575,6 +6213,12 @@ } ] }, + "node_modules/caseless": { + "version": "0.12.0", + "resolved": "https://registry.npmjs.org/caseless/-/caseless-0.12.0.tgz", + "integrity": "sha512-4tYFyifaFfGacoiObjJegolkwSU4xQNGbVgUiNYVUxbQ2x2lUsFvY4hVgVzGiIe6WLOPqycWXA40l+PWsxthUw==", + "dev": true + }, "node_modules/chalk": { "version": "4.1.2", "resolved": "https://registry.npmjs.org/chalk/-/chalk-4.1.2.tgz", @@ -5660,6 +6304,18 @@ "node": ">= 10" } }, + "node_modules/clipanion": { + "version": "3.2.1", + "resolved": "https://registry.npmjs.org/clipanion/-/clipanion-3.2.1.tgz", + "integrity": "sha512-dYFdjLb7y1ajfxQopN05mylEpK9ZX0sO1/RfMXdfmwjlIsPkbh4p7A682x++zFPLDCo1x3p82dtljHf5cW2LKA==", + "dev": true, + "dependencies": { + "typanion": "^3.8.0" + }, + "peerDependencies": { + "typanion": "*" + } + }, "node_modules/cliui": { "version": "8.0.1", "resolved": "https://registry.npmjs.org/cliui/-/cliui-8.0.1.tgz", @@ -5868,6 +6524,57 @@ "dot-prop": "^5.1.0" } }, + "node_modules/compressible": { + "version": "2.0.18", + "resolved": "https://registry.npmjs.org/compressible/-/compressible-2.0.18.tgz", + "integrity": "sha512-AF3r7P5dWxL8MxyITRMlORQNaOA2IkAFaTr4k7BUumjPtRpGDTZpl0Pb1XCO6JeDCBdp126Cgs9sMxqSjgYyRg==", + "dev": true, + "dependencies": { + "mime-db": ">= 1.43.0 < 2" + }, + "engines": { + "node": ">= 0.6" + } + }, + "node_modules/compression": { + "version": "1.7.4", + "resolved": "https://registry.npmjs.org/compression/-/compression-1.7.4.tgz", + "integrity": "sha512-jaSIDzP9pZVS4ZfQ+TzvtiWhdpFhE2RDHz8QJkpX9SIpLq88VueF5jJw6t+6CUQcAoA6t+x89MLrWAqpfDE8iQ==", + "dev": true, + "dependencies": { + "accepts": "~1.3.5", + "bytes": "3.0.0", + "compressible": "~2.0.16", + "debug": "2.6.9", + "on-headers": "~1.0.2", + "safe-buffer": "5.1.2", + "vary": "~1.1.2" + }, + "engines": { + "node": ">= 0.8.0" + } + }, + "node_modules/compression/node_modules/debug": { + "version": "2.6.9", + "resolved": "https://registry.npmjs.org/debug/-/debug-2.6.9.tgz", + "integrity": "sha512-bC7ElrdJaJnPbAP+1EotYvqZsb3ecl5wi6Bfi6BJTUcNowp6cvspg0jXznRTKDjm/E7AdgFBVeAPVMNcKGsHMA==", + "dev": true, + "dependencies": { + "ms": "2.0.0" + } + }, + "node_modules/compression/node_modules/ms": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/ms/-/ms-2.0.0.tgz", + "integrity": "sha512-Tpp60P6IUJDTuOq/5Z8cdskzJujfwqfOTkrwIwj7IRISpnkJnT6SyJ4PCPnGMoFjC9ddhal5KVIYtAt97ix05A==", + "dev": true + }, + "node_modules/compression/node_modules/safe-buffer": { + "version": "5.1.2", + "resolved": "https://registry.npmjs.org/safe-buffer/-/safe-buffer-5.1.2.tgz", + "integrity": "sha512-Gd2UZBJDkXlY7GbJxfsE8/nvKkUEU1G38c1siN6QP6a9PT9MmHB8GnpscSmMJSoF8LOIrt8ud/wPtojys4G6+g==", + "dev": true + }, "node_modules/concat-map": { "version": "0.0.1", "resolved": "https://registry.npmjs.org/concat-map/-/concat-map-0.0.1.tgz", @@ -5907,6 +6614,15 @@ "node": ">= 0.6" } }, + "node_modules/content-type": { + "version": "1.0.5", + "resolved": "https://registry.npmjs.org/content-type/-/content-type-1.0.5.tgz", + "integrity": "sha512-nTjqfcBFEipKdXCv4YDQWCfmcLZKm81ldF0pAopTvyrFGVbcR6P/VAAd5G7N+0tTr8QqiU0tFadD6FK4NtJwOA==", + "dev": true, + "engines": { + "node": ">= 0.6" + } + }, "node_modules/conventional-changelog": { "version": "4.0.0", "resolved": "https://registry.npmjs.org/conventional-changelog/-/conventional-changelog-4.0.0.tgz", @@ -6183,6 +6899,45 @@ "integrity": "sha512-Kvp459HrV2FEJ1CAsi1Ku+MY3kasH19TFykTz2xWmMeq6bk2NU3XXvfJ+Q61m0xktWwt+1HSYf3JZsTms3aRJg==", "dev": true }, + "node_modules/cookie": { + "version": "0.5.0", + "resolved": "https://registry.npmjs.org/cookie/-/cookie-0.5.0.tgz", + "integrity": "sha512-YZ3GUyn/o8gfKJlnlX7g7xq4gyO6OSuhGPKaaGssGB2qgDUS0gPgtTvoyZLTt9Ab6dC4hfc9dV5arkvc/OCmrw==", + "dev": true, + "engines": { + "node": ">= 0.6" + } + }, + "node_modules/cookie-signature": { + "version": "1.0.6", + "resolved": "https://registry.npmjs.org/cookie-signature/-/cookie-signature-1.0.6.tgz", + "integrity": "sha512-QADzlaHc8icV8I7vbaJXJwod9HWYp8uCqf1xa4OfNu1T7JVxQIrUgOWtHdNDtPiywmFbiS12VjotIXLrKM3orQ==", + "dev": true + }, + "node_modules/cookies": { + "version": "0.8.0", + "resolved": "https://registry.npmjs.org/cookies/-/cookies-0.8.0.tgz", + "integrity": "sha512-8aPsApQfebXnuI+537McwYsDtjVxGm8gTIzQI3FDW6t5t/DAhERxtnbEPN/8RX+uZthoz4eCOgloXaE5cYyNow==", + "dev": true, + "dependencies": { + "depd": "~2.0.0", + "keygrip": "~1.1.0" + }, + "engines": { + "node": ">= 0.8" + } + }, + "node_modules/core-js": { + "version": "3.30.2", + "resolved": "https://registry.npmjs.org/core-js/-/core-js-3.30.2.tgz", + "integrity": "sha512-uBJiDmwqsbJCWHAwjrx3cvjbMXP7xD72Dmsn5LOJpiRmE3WbBbN5rCqQ2Qh6Ek6/eOrjlWngEynBWo4VxerQhg==", + "dev": true, + "hasInstallScript": true, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/core-js" + } + }, "node_modules/core-js-compat": { "version": "3.33.3", "resolved": "https://registry.npmjs.org/core-js-compat/-/core-js-compat-3.33.3.tgz", @@ -6202,6 +6957,19 @@ "integrity": "sha512-ZQBvi1DcpJ4GDqanjucZ2Hj3wEO5pZDS89BWbkcrvdxksJorwUDDZamX9ldFkp9aw2lmBDLgkObEA4DWNJ9FYQ==", "dev": true }, + "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==", + "dev": true, + "dependencies": { + "object-assign": "^4", + "vary": "^1" + }, + "engines": { + "node": ">= 0.10" + } + }, "node_modules/cosmiconfig": { "version": "8.3.6", "resolved": "https://registry.npmjs.org/cosmiconfig/-/cosmiconfig-8.3.6.tgz", @@ -6467,6 +7235,18 @@ "node": ">=8" } }, + "node_modules/dashdash": { + "version": "1.14.1", + "resolved": "https://registry.npmjs.org/dashdash/-/dashdash-1.14.1.tgz", + "integrity": "sha512-jRFi8UDGo6j+odZiEpjazZaWqEal3w/basFjQHQEwVtZJGDpxbH1MeYluwCS8Xq5wmLJooDlMgvVarmWfGM44g==", + "dev": true, + "dependencies": { + "assert-plus": "^1.0.0" + }, + "engines": { + "node": ">=0.10" + } + }, "node_modules/data-urls": { "version": "3.0.2", "resolved": "https://registry.npmjs.org/data-urls/-/data-urls-3.0.2.tgz", @@ -6490,6 +7270,12 @@ "node": "*" } }, + "node_modules/dayjs": { + "version": "1.11.7", + "resolved": "https://registry.npmjs.org/dayjs/-/dayjs-1.11.7.tgz", + "integrity": "sha512-+Yw9U6YO5TQohxLcIkrXBeY73WP3ejHWVvx8XCk3gxvQDCTEmS48ZrSZCKciI7Bhl/uCMyxYtE9UqRILmFphkQ==", + "dev": true + }, "node_modules/debug": { "version": "4.3.4", "resolved": "https://registry.npmjs.org/debug/-/debug-4.3.4.tgz", @@ -6616,6 +7402,20 @@ "node": ">=10" } }, + "node_modules/define-data-property": { + "version": "1.1.1", + "resolved": "https://registry.npmjs.org/define-data-property/-/define-data-property-1.1.1.tgz", + "integrity": "sha512-E7uGkTzkk1d0ByLeSc6ZsFS79Axg+m1P/VsgYsxHgiuc3tFSj+MjMIwe90FC4lOAZzNBdY7kkO2P2wKdsQ1vgQ==", + "dev": true, + "dependencies": { + "get-intrinsic": "^1.2.1", + "gopd": "^1.0.1", + "has-property-descriptors": "^1.0.0" + }, + "engines": { + "node": ">= 0.4" + } + }, "node_modules/define-lazy-prop": { "version": "2.0.0", "resolved": "https://registry.npmjs.org/define-lazy-prop/-/define-lazy-prop-2.0.0.tgz", @@ -6634,6 +7434,25 @@ "node": ">=0.4.0" } }, + "node_modules/depd": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/depd/-/depd-2.0.0.tgz", + "integrity": "sha512-g7nH6P6dyDioJogAAGprGpCtVImJhpPk/roCzdb3fIh61/s/nPsfR6onyMwkCAR/OlC3yBC0lESvUoQEAssIrw==", + "dev": true, + "engines": { + "node": ">= 0.8" + } + }, + "node_modules/destroy": { + "version": "1.2.0", + "resolved": "https://registry.npmjs.org/destroy/-/destroy-1.2.0.tgz", + "integrity": "sha512-2sJGJTaXIIaR1w4iJSNoN0hnMY7Gpc/n8D4qSCJw8QqFWXf7cuAgnEHxBpweaVcPevC2l3KpjYCx3NypQQgaJg==", + "dev": true, + "engines": { + "node": ">= 0.8", + "npm": "1.2.8000 || >= 1.4.16" + } + }, "node_modules/detect-file": { "version": "1.0.0", "resolved": "https://registry.npmjs.org/detect-file/-/detect-file-1.0.0.tgz", @@ -6768,6 +7587,43 @@ "integrity": "sha512-jtD6YG370ZCIi/9GTaJKQxWTZD045+4R4hTk/x1UyoqadyJ9x9CgSi1RlVDQF8U2sxLLSnFkCaMihqljHIWgMg==", "dev": true }, + "node_modules/duplexify": { + "version": "4.1.2", + "resolved": "https://registry.npmjs.org/duplexify/-/duplexify-4.1.2.tgz", + "integrity": "sha512-fz3OjcNCHmRP12MJoZMPglx8m4rrFP8rovnk4vT8Fs+aonZoCwGg10dSsQsfP/E62eZcPTMSMP6686fu9Qlqtw==", + "dev": true, + "dependencies": { + "end-of-stream": "^1.4.1", + "inherits": "^2.0.3", + "readable-stream": "^3.1.1", + "stream-shift": "^1.0.0" + } + }, + "node_modules/ecc-jsbn": { + "version": "0.1.2", + "resolved": "https://registry.npmjs.org/ecc-jsbn/-/ecc-jsbn-0.1.2.tgz", + "integrity": "sha512-eh9O+hwRHNbG4BLTjEl3nw044CkGm5X6LoaCf7LPp7UU8Qrt47JYNi6nPX8xjW97TKGKm1ouctg0QSpZe9qrnw==", + "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==", + "dev": true, + "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": "sha512-WMwm9LhRUo+WUaRN+vRuETqG89IgZphVSNkdFgeb6sS/E4OrDIN7t48CAewSHXc6C8lefD8KKfr5vY61brQlow==", + "dev": true + }, "node_modules/ejs": { "version": "3.1.9", "resolved": "https://registry.npmjs.org/ejs/-/ejs-3.1.9.tgz", @@ -6807,6 +7663,15 @@ "integrity": "sha512-MSjYzcWNOA0ewAHpz0MxpYFvwg6yjy1NG3xteoqz644VCo/RPgnr1/GGt+ic3iJTzQ8Eu3TdM14SawnVUmGE6A==", "dev": true }, + "node_modules/encodeurl": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/encodeurl/-/encodeurl-1.0.2.tgz", + "integrity": "sha512-TPJXq8JqFaVYm2CWmPvnP2Iyo4ZSM7/QKcSmuMLDObfpH5fi7RUGmd/rTDf+rut/saiDiQEeVTNgAmJEdAOx0w==", + "dev": true, + "engines": { + "node": ">= 0.8" + } + }, "node_modules/end-of-stream": { "version": "1.4.4", "resolved": "https://registry.npmjs.org/end-of-stream/-/end-of-stream-1.4.4.tgz", @@ -6840,6 +7705,18 @@ "url": "https://github.com/fb55/entities?sponsor=1" } }, + "node_modules/envinfo": { + "version": "7.10.0", + "resolved": "https://registry.npmjs.org/envinfo/-/envinfo-7.10.0.tgz", + "integrity": "sha512-ZtUjZO6l5mwTHvc1L9+1q5p/R3wTopcfqMW8r5t8SJSKqeVI/LtajORwRFEKpEFuekjD0VBjwu1HMxL4UalIRw==", + "dev": true, + "bin": { + "envinfo": "dist/cli.js" + }, + "engines": { + "node": ">=4" + } + }, "node_modules/error-ex": { "version": "1.3.2", "resolved": "https://registry.npmjs.org/error-ex/-/error-ex-1.3.2.tgz", @@ -6858,6 +7735,12 @@ "node": ">=6" } }, + "node_modules/escape-html": { + "version": "1.0.3", + "resolved": "https://registry.npmjs.org/escape-html/-/escape-html-1.0.3.tgz", + "integrity": "sha512-NiSupZ4OeuGwr68lGIeym/ksIZMJodUGOSCZ/FSnTxcrekbvqrgdUxlJOMpijaKZVjAJrWrGs/6Jy8OMuyj9ow==", + "dev": true + }, "node_modules/escape-string-regexp": { "version": "4.0.0", "resolved": "https://registry.npmjs.org/escape-string-regexp/-/escape-string-regexp-4.0.0.tgz", @@ -7146,6 +8029,33 @@ "node": ">=0.10.0" } }, + "node_modules/etag": { + "version": "1.8.1", + "resolved": "https://registry.npmjs.org/etag/-/etag-1.8.1.tgz", + "integrity": "sha512-aIL5Fx7mawVa300al2BnEE4iNvo1qETxLrPI/o05L7z6go7fCw1J6EQmbK4FmJ2AS7kgVF/KEZWufBfdClMcPg==", + "dev": true, + "engines": { + "node": ">= 0.6" + } + }, + "node_modules/event-target-shim": { + "version": "5.0.1", + "resolved": "https://registry.npmjs.org/event-target-shim/-/event-target-shim-5.0.1.tgz", + "integrity": "sha512-i/2XbnSz/uxRCU6+NdVJgKWDTM427+MqYbkQzD321DuCQJUqOuJKIA0IM2+W2xtYHdKOmZ4dR6fExsd4SXL+WQ==", + "dev": true, + "engines": { + "node": ">=6" + } + }, + "node_modules/events": { + "version": "3.3.0", + "resolved": "https://registry.npmjs.org/events/-/events-3.3.0.tgz", + "integrity": "sha512-mQw+2fkQbALzQ7V0MY0IqdnXNOeTtP4r0lN9z7AAawCXgqea7bDii20AYrIBrFd/Hx0M2Ocz6S111CaFkUcb0Q==", + "dev": true, + "engines": { + "node": ">=0.8.x" + } + }, "node_modules/execa": { "version": "5.1.1", "resolved": "https://registry.npmjs.org/execa/-/execa-5.1.1.tgz", @@ -7218,6 +8128,69 @@ "node": "^14.15.0 || ^16.10.0 || >=18.0.0" } }, + "node_modules/express": { + "version": "4.18.2", + "resolved": "https://registry.npmjs.org/express/-/express-4.18.2.tgz", + "integrity": "sha512-5/PsL6iGPdfQ/lKM1UuielYgv3BUoJfz1aUwU9vHZ+J7gyvwdQXFEBIEIaxeGf0GIcreATNyBExtalisDbuMqQ==", + "dev": true, + "dependencies": { + "accepts": "~1.3.8", + "array-flatten": "1.1.1", + "body-parser": "1.20.1", + "content-disposition": "0.5.4", + "content-type": "~1.0.4", + "cookie": "0.5.0", + "cookie-signature": "1.0.6", + "debug": "2.6.9", + "depd": "2.0.0", + "encodeurl": "~1.0.2", + "escape-html": "~1.0.3", + "etag": "~1.8.1", + "finalhandler": "1.2.0", + "fresh": "0.5.2", + "http-errors": "2.0.0", + "merge-descriptors": "1.0.1", + "methods": "~1.1.2", + "on-finished": "2.4.1", + "parseurl": "~1.3.3", + "path-to-regexp": "0.1.7", + "proxy-addr": "~2.0.7", + "qs": "6.11.0", + "range-parser": "~1.2.1", + "safe-buffer": "5.2.1", + "send": "0.18.0", + "serve-static": "1.15.0", + "setprototypeof": "1.2.0", + "statuses": "2.0.1", + "type-is": "~1.6.18", + "utils-merge": "1.0.1", + "vary": "~1.1.2" + }, + "engines": { + "node": ">= 0.10.0" + } + }, + "node_modules/express-rate-limit": { + "version": "5.5.1", + "resolved": "https://registry.npmjs.org/express-rate-limit/-/express-rate-limit-5.5.1.tgz", + "integrity": "sha512-MTjE2eIbHv5DyfuFz4zLYWxpqVhEhkTiwFGuB74Q9CSou2WHO52nlE5y3Zlg6SIsiYUIPj6ifFxnkPz6O3sIUg==", + "dev": true + }, + "node_modules/express/node_modules/debug": { + "version": "2.6.9", + "resolved": "https://registry.npmjs.org/debug/-/debug-2.6.9.tgz", + "integrity": "sha512-bC7ElrdJaJnPbAP+1EotYvqZsb3ecl5wi6Bfi6BJTUcNowp6cvspg0jXznRTKDjm/E7AdgFBVeAPVMNcKGsHMA==", + "dev": true, + "dependencies": { + "ms": "2.0.0" + } + }, + "node_modules/express/node_modules/ms": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/ms/-/ms-2.0.0.tgz", + "integrity": "sha512-Tpp60P6IUJDTuOq/5Z8cdskzJujfwqfOTkrwIwj7IRISpnkJnT6SyJ4PCPnGMoFjC9ddhal5KVIYtAt97ix05A==", + "dev": true + }, "node_modules/ext-list": { "version": "2.2.2", "resolved": "https://registry.npmjs.org/ext-list/-/ext-list-2.2.2.tgz", @@ -7243,6 +8216,12 @@ "node": ">=4" } }, + "node_modules/extend": { + "version": "3.0.2", + "resolved": "https://registry.npmjs.org/extend/-/extend-3.0.2.tgz", + "integrity": "sha512-fjquC59cD7CyW6urNXK0FBufkZcoiGG80wTuPujX590cB5Ttln20E2UB4S/WARVqhXffZl2LNgS+gQdPIIim/g==", + "dev": true + }, "node_modules/external-editor": { "version": "3.1.0", "resolved": "https://registry.npmjs.org/external-editor/-/external-editor-3.1.0.tgz", @@ -7269,6 +8248,15 @@ "node": ">=0.6.0" } }, + "node_modules/extsprintf": { + "version": "1.3.0", + "resolved": "https://registry.npmjs.org/extsprintf/-/extsprintf-1.3.0.tgz", + "integrity": "sha512-11Ndz7Nv+mvAC1j0ktTa7fAb0vLyGGX+rMHNBYQviQDGU0Hw7lhctJANqbPhu9nV9/izT/IntTgZ7Im/9LJs9g==", + "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", @@ -7315,6 +8303,21 @@ "integrity": "sha512-DCXu6Ifhqcks7TZKY3Hxp3y6qphY5SJZmrWMDrKcERSOXWQdMhU9Ig/PYrzyw/ul9jOIyh0N4M0tbC5hodg8dw==", "dev": true }, + "node_modules/fast-redact": { + "version": "3.3.0", + "resolved": "https://registry.npmjs.org/fast-redact/-/fast-redact-3.3.0.tgz", + "integrity": "sha512-6T5V1QK1u4oF+ATxs1lWUmlEk6P2T9HqJG3e2DnHOdVgZy2rFJBoEnrIedcTXlkAHU/zKC+7KETJ+KGGKwxgMQ==", + "dev": true, + "engines": { + "node": ">=6" + } + }, + "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==", + "dev": true + }, "node_modules/fastq": { "version": "1.15.0", "resolved": "https://registry.npmjs.org/fastq/-/fastq-1.15.0.tgz", @@ -7457,6 +8460,39 @@ "node": ">=8" } }, + "node_modules/finalhandler": { + "version": "1.2.0", + "resolved": "https://registry.npmjs.org/finalhandler/-/finalhandler-1.2.0.tgz", + "integrity": "sha512-5uXcUVftlQMFnWC9qu/svkWv3GTd2PfUhK/3PLkYNAe7FbqJMt3515HaxE6eRL74GdsriiwujiawdaB1BpEISg==", + "dev": true, + "dependencies": { + "debug": "2.6.9", + "encodeurl": "~1.0.2", + "escape-html": "~1.0.3", + "on-finished": "2.4.1", + "parseurl": "~1.3.3", + "statuses": "2.0.1", + "unpipe": "~1.0.0" + }, + "engines": { + "node": ">= 0.8" + } + }, + "node_modules/finalhandler/node_modules/debug": { + "version": "2.6.9", + "resolved": "https://registry.npmjs.org/debug/-/debug-2.6.9.tgz", + "integrity": "sha512-bC7ElrdJaJnPbAP+1EotYvqZsb3ecl5wi6Bfi6BJTUcNowp6cvspg0jXznRTKDjm/E7AdgFBVeAPVMNcKGsHMA==", + "dev": true, + "dependencies": { + "ms": "2.0.0" + } + }, + "node_modules/finalhandler/node_modules/ms": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/ms/-/ms-2.0.0.tgz", + "integrity": "sha512-Tpp60P6IUJDTuOq/5Z8cdskzJujfwqfOTkrwIwj7IRISpnkJnT6SyJ4PCPnGMoFjC9ddhal5KVIYtAt97ix05A==", + "dev": true + }, "node_modules/find-node-modules": { "version": "2.1.3", "resolved": "https://registry.npmjs.org/find-node-modules/-/find-node-modules-2.1.3.tgz", @@ -7568,6 +8604,15 @@ } } }, + "node_modules/forever-agent": { + "version": "0.6.1", + "resolved": "https://registry.npmjs.org/forever-agent/-/forever-agent-0.6.1.tgz", + "integrity": "sha512-j0KLYPhm6zeac4lz3oJ3o65qvgQCcPubiyotZrXqEaG4hNagNYO8qdlUrX5vwqv9ohqeT/Z3j6+yW067yWWdUw==", + "dev": true, + "engines": { + "node": "*" + } + }, "node_modules/form-data": { "version": "4.0.0", "resolved": "https://registry.npmjs.org/form-data/-/form-data-4.0.0.tgz", @@ -7582,6 +8627,24 @@ "node": ">= 6" } }, + "node_modules/forwarded": { + "version": "0.2.0", + "resolved": "https://registry.npmjs.org/forwarded/-/forwarded-0.2.0.tgz", + "integrity": "sha512-buRG0fpBtRHSTCOASe6hD258tEubFoRLb4ZNA6NxMVHNw2gOcwHo9wyablzMzOA5z9xA9L1KNjk/Nt6MT9aYow==", + "dev": true, + "engines": { + "node": ">= 0.6" + } + }, + "node_modules/fresh": { + "version": "0.5.2", + "resolved": "https://registry.npmjs.org/fresh/-/fresh-0.5.2.tgz", + "integrity": "sha512-zJ2mQYM18rEFOudeV4GShTGIQ7RbzA7ozbU9I/XBpm7kqgMywgmylMwXHxZJmkVoYkna9d2pVXVXPdYTP9ej8Q==", + "dev": true, + "engines": { + "node": ">= 0.6" + } + }, "node_modules/fs-constants": { "version": "1.0.0", "resolved": "https://registry.npmjs.org/fs-constants/-/fs-constants-1.0.0.tgz", @@ -7649,6 +8712,21 @@ "node": "6.* || 8.* || >= 10.*" } }, + "node_modules/get-intrinsic": { + "version": "1.2.2", + "resolved": "https://registry.npmjs.org/get-intrinsic/-/get-intrinsic-1.2.2.tgz", + "integrity": "sha512-0gSo4ml/0j98Y3lngkFEot/zhiCeWsbYIlZ+uZOVgzLyLaUw7wxUL+nCTP0XJvJg1AXulJRI3UJi8GsbDuxdGA==", + "dev": true, + "dependencies": { + "function-bind": "^1.1.2", + "has-proto": "^1.0.1", + "has-symbols": "^1.0.3", + "hasown": "^2.0.0" + }, + "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", @@ -7726,6 +8804,15 @@ "url": "https://github.com/sponsors/sindresorhus" } }, + "node_modules/getpass": { + "version": "0.1.7", + "resolved": "https://registry.npmjs.org/getpass/-/getpass-0.1.7.tgz", + "integrity": "sha512-0fzj9JxOLfJ+XGLhR8ze3unN0KZCgZwiSSDz168VERjK8Wl8kVSdcu2kspd4s4wtAa1y/qrVRiAA0WclVsu0ng==", + "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", @@ -7965,6 +9052,18 @@ "node": ">= 6" } }, + "node_modules/gopd": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/gopd/-/gopd-1.0.1.tgz", + "integrity": "sha512-d65bNlIadxvpb/A2abVdlqKqV563juRnZ1Wtk6s1sIR8uNsXR70xqIzVqxVf1eTqDunwT2MkczEeaezCKTZhwA==", + "dev": true, + "dependencies": { + "get-intrinsic": "^1.1.3" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, "node_modules/got": { "version": "11.8.6", "resolved": "https://registry.npmjs.org/got/-/got-11.8.6.tgz", @@ -8032,6 +9131,51 @@ "node": ">=0.10.0" } }, + "node_modules/har-schema": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/har-schema/-/har-schema-2.0.0.tgz", + "integrity": "sha512-Oqluz6zhGX8cyRaTQlFMPw80bSJVG2x/cFb8ZPhUILGgHka9SsokCCOQgpveePerqidZOrT14ipqfJb7ILcW5Q==", + "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", @@ -8041,19 +9185,55 @@ "node": ">=6" } }, - "node_modules/harmony-reflect": { - "version": "1.6.2", - "resolved": "https://registry.npmjs.org/harmony-reflect/-/harmony-reflect-1.6.2.tgz", - "integrity": "sha512-HIp/n38R9kQjDEziXyDTuW3vvoxxyxjxFzXLrBr18uB47GnSt+G9D29fqrpM5ZkspMcPICud3XsBJQ4Y2URg8g==", - "dev": true - }, - "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==", + "node_modules/harmony-reflect": { + "version": "1.6.2", + "resolved": "https://registry.npmjs.org/harmony-reflect/-/harmony-reflect-1.6.2.tgz", + "integrity": "sha512-HIp/n38R9kQjDEziXyDTuW3vvoxxyxjxFzXLrBr18uB47GnSt+G9D29fqrpM5ZkspMcPICud3XsBJQ4Y2URg8g==", + "dev": true + }, + "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-property-descriptors": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/has-property-descriptors/-/has-property-descriptors-1.0.1.tgz", + "integrity": "sha512-VsX8eaIewvas0xnvinAe9bw4WfIeODpGYikiWYLH+dma0Jw6KHYqWiWfhQlgOVK8D6PvjubK5Uc4P0iIhIcNVg==", + "dev": true, + "dependencies": { + "get-intrinsic": "^1.2.2" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/has-proto": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/has-proto/-/has-proto-1.0.1.tgz", + "integrity": "sha512-7qE+iP+O+bgF9clE5+UoBFzE65mlBiVj3tKCrlNQ0Ogwm0BjpT/gK4SlLYDMybDh5I3TCTKnPPa0oMG7JDYrhg==", + "dev": true, + "engines": { + "node": ">= 0.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/has-symbols": { + "version": "1.0.3", + "resolved": "https://registry.npmjs.org/has-symbols/-/has-symbols-1.0.3.tgz", + "integrity": "sha512-l3LCuF6MgDNwTDKkdYGEihYjt5pRPbEg46rtlmnSPlUbgmB8LOIrKJbYYFBSbnPaJexMKtiPO8hmeRjRz2Td+A==", "dev": true, "engines": { - "node": ">=8" + "node": ">= 0.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" } }, "node_modules/hasown": { @@ -8134,6 +9314,22 @@ "integrity": "sha512-er295DKPVsV82j5kw1Gjt+ADA/XYHsajl82cGNQG2eyoPkvgUhX+nDIyelzhIWbbsXP39EHcI6l5tYs2FYqYXQ==", "dev": true }, + "node_modules/http-errors": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/http-errors/-/http-errors-2.0.0.tgz", + "integrity": "sha512-FtwrG/euBzaEjYeRqOgly7G0qviiXoJWnvEH2Z1plBdXgbyjv34pHTSb9zoeHMyDy33+DWy5Wt9Wo+TURtOYSQ==", + "dev": true, + "dependencies": { + "depd": "2.0.0", + "inherits": "2.0.4", + "setprototypeof": "1.2.0", + "statuses": "2.0.1", + "toidentifier": "1.0.1" + }, + "engines": { + "node": ">= 0.8" + } + }, "node_modules/http-proxy-agent": { "version": "5.0.0", "resolved": "https://registry.npmjs.org/http-proxy-agent/-/http-proxy-agent-5.0.0.tgz", @@ -8148,6 +9344,27 @@ "node": ">= 6" } }, + "node_modules/http-signature": { + "version": "1.2.0", + "resolved": "https://registry.npmjs.org/http-signature/-/http-signature-1.2.0.tgz", + "integrity": "sha512-CAbnr6Rz4CYQkLYUtSNXxQPUH2gK8f3iWexVlsnMeD+GjlsQ0Xsy1cOX+mN3dtxYomRy21CiOzU8Uhw6OwncEQ==", + "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/http-status-codes": { + "version": "2.2.0", + "resolved": "https://registry.npmjs.org/http-status-codes/-/http-status-codes-2.2.0.tgz", + "integrity": "sha512-feERVo9iWxvnejp3SEfm/+oNG517npqL2/PIA8ORjyOZjGC7TwCRQsZylciLS64i6pJ0wRYz3rkXLRwbtFa8Ng==", + "dev": true + }, "node_modules/http2-wrapper": { "version": "1.0.3", "resolved": "https://registry.npmjs.org/http2-wrapper/-/http2-wrapper-1.0.3.tgz", @@ -8329,6 +9546,15 @@ "integrity": "sha512-k/vGaX4/Yla3WzyMCvTQOXYeIHvqOKtnqBduzTHpzpQZzAskKMhZ2K+EnBiSM9zGSoIFeMpXKxa4dYeZIQqewQ==", "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==", + "dev": true, + "engines": { + "node": ">= 0.10" + } + }, "node_modules/is-arrayish": { "version": "0.2.1", "resolved": "https://registry.npmjs.org/is-arrayish/-/is-arrayish-0.2.1.tgz", @@ -8452,6 +9678,12 @@ "integrity": "sha512-bCYeRA2rVibKZd+s2625gGnGF/t7DSqDs4dP7CrLA1m7jKWz6pps0LpYLJN8Q64HtmPKJ1hrN3nzPNKFEKOUiQ==", "dev": true }, + "node_modules/is-promise": { + "version": "2.2.2", + "resolved": "https://registry.npmjs.org/is-promise/-/is-promise-2.2.2.tgz", + "integrity": "sha512-+lP4/6lKUBfQjZ2pdxThZvLUAafmZb8OAxFb8XXtiQmS35INgr85hdOGoEs124ez1FCnZJt6jau/T+alh58QFQ==", + "dev": true + }, "node_modules/is-stream": { "version": "2.0.1", "resolved": "https://registry.npmjs.org/is-stream/-/is-stream-2.0.1.tgz", @@ -8476,6 +9708,12 @@ "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", @@ -8527,6 +9765,12 @@ "integrity": "sha512-RHxMLp9lnKHGHRng9QFhRCMbYAcVpn69smSGcq3f36xjgVVWThj4qqLbTLlq7Ssj8B+fIQ1EuCEGI2lKsyQeIw==", "dev": true }, + "node_modules/isstream": { + "version": "0.1.2", + "resolved": "https://registry.npmjs.org/isstream/-/isstream-0.1.2.tgz", + "integrity": "sha512-Yljz7ffyPbrLpLngrMtZ7NduUgVvi6wG9RJ9IUcyCd59YQ911PBJphODUcbOVbqYfxe1wuYf/LJ8PauMRwsM/g==", + "dev": true + }, "node_modules/istanbul-lib-coverage": { "version": "3.2.2", "resolved": "https://registry.npmjs.org/istanbul-lib-coverage/-/istanbul-lib-coverage-3.2.2.tgz", @@ -9343,6 +10587,12 @@ "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": "sha512-UVU9dibq2JcFWxQPA6KCqj5O42VOmAY3zQUfEKxU0KpTGXwNoCjkX1e13eHNvw/xPynt6pU0rZ1htjWTNTSXsg==", + "dev": true + }, "node_modules/jsdom": { "version": "20.0.3", "resolved": "https://registry.npmjs.org/jsdom/-/jsdom-20.0.3.tgz", @@ -9418,6 +10668,12 @@ "integrity": "sha512-xyFwyhro/JEof6Ghe2iz2NcXoj2sloNsWr/XsERDK/oiPCfaNhl5ONfp+jQdAZRQQ0IJWNzH9zIZF7li91kh2w==", "dev": true }, + "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==", + "dev": true + }, "node_modules/json-schema-traverse": { "version": "1.0.0", "resolved": "https://registry.npmjs.org/json-schema-traverse/-/json-schema-traverse-1.0.0.tgz", @@ -9509,6 +10765,109 @@ "node": "*" } }, + "node_modules/jsonwebtoken": { + "version": "9.0.2", + "resolved": "https://registry.npmjs.org/jsonwebtoken/-/jsonwebtoken-9.0.2.tgz", + "integrity": "sha512-PRp66vJ865SSqOlgqS8hujT5U4AOgMfhrwYIuIhfKaoSCZcirrmASQr8CX7cUg+RMih+hgznrjp99o+W4pJLHQ==", + "dev": true, + "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": "^7.5.4" + }, + "engines": { + "node": ">=12", + "npm": ">=6" + } + }, + "node_modules/jsonwebtoken/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/jsonwebtoken/node_modules/semver": { + "version": "7.5.4", + "resolved": "https://registry.npmjs.org/semver/-/semver-7.5.4.tgz", + "integrity": "sha512-1bCSESV6Pv+i21Hvpxp3Dx+pSD8lIPt8uVjRrxAUt/nbswYc+tK6Y2btiULjd4+fnq15PX+nqQDC7Oft7WkwcA==", + "dev": true, + "dependencies": { + "lru-cache": "^6.0.0" + }, + "bin": { + "semver": "bin/semver.js" + }, + "engines": { + "node": ">=10" + } + }, + "node_modules/jsonwebtoken/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/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": "1.4.1", + "resolved": "https://registry.npmjs.org/jwa/-/jwa-1.4.1.tgz", + "integrity": "sha512-qiLX/xhEEFKUAJ6FiBMbes3w9ATzyk5W7Hvzpa/SLYdxNtng+gcurvrI7TbACjIXlsJyr05/S1oUhZrc63evQA==", + "dev": true, + "dependencies": { + "buffer-equal-constant-time": "1.0.1", + "ecdsa-sig-formatter": "1.0.11", + "safe-buffer": "^5.0.1" + } + }, + "node_modules/jws": { + "version": "3.2.2", + "resolved": "https://registry.npmjs.org/jws/-/jws-3.2.2.tgz", + "integrity": "sha512-YHlZCB6lMTllWDtSPHz/ZXTsi8S00usEV6v1tjq8tOUZzw7DpSDWVXjXDre6ed1w/pd495ODpHZYSdkRTsa0HA==", + "dev": true, + "dependencies": { + "jwa": "^1.4.1", + "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==", + "dev": true, + "dependencies": { + "tsscmp": "1.0.6" + }, + "engines": { + "node": ">= 0.6" + } + }, "node_modules/keyv": { "version": "4.5.4", "resolved": "https://registry.npmjs.org/keyv/-/keyv-4.5.4.tgz", @@ -9628,12 +10987,27 @@ "url": "https://github.com/sponsors/sindresorhus" } }, + "node_modules/lockfile": { + "version": "1.0.4", + "resolved": "https://registry.npmjs.org/lockfile/-/lockfile-1.0.4.tgz", + "integrity": "sha512-cvbTwETRfsFh4nHsL1eGWapU1XFi5Ot9E85sWAwia7Y7EgB7vfqcZhTKZ+l7hCGxSPoushMv5GKhT5PdLv03WA==", + "dev": true, + "dependencies": { + "signal-exit": "^3.0.2" + } + }, "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-es": { + "version": "4.17.21", + "resolved": "https://registry.npmjs.org/lodash-es/-/lodash-es-4.17.21.tgz", + "integrity": "sha512-mKnC+QJ9pWVzv+C4/U3rRsHapFfHvQFoFB92e52xeyGMcX6/OlIl78je1u8vePzYZSkkogMPJ2yjxxsb89cxyw==", + "dev": true + }, "node_modules/lodash.camelcase": { "version": "4.3.0", "resolved": "https://registry.npmjs.org/lodash.camelcase/-/lodash.camelcase-4.3.0.tgz", @@ -9646,24 +11020,54 @@ "integrity": "sha512-FT1yDzDYEoYWhnSGnpE/4Kj1fLZkDFyqRb7fNt6FdYOSxlUWAtp42Eh6Wb0rGIv/m9Bgo7x4GhQbm5Ys4SG5ow==", "dev": true }, + "node_modules/lodash.includes": { + "version": "4.3.0", + "resolved": "https://registry.npmjs.org/lodash.includes/-/lodash.includes-4.3.0.tgz", + "integrity": "sha512-W3Bx6mdkRTGtlJISOvVD/lbqjTlPPUDTMnlXZFnVwi9NKJ6tiAk6LVdlhZMm17VZisqhKcgzpO5Wz91PCt5b0w==", + "dev": true + }, + "node_modules/lodash.isboolean": { + "version": "3.0.3", + "resolved": "https://registry.npmjs.org/lodash.isboolean/-/lodash.isboolean-3.0.3.tgz", + "integrity": "sha512-Bz5mupy2SVbPHURB98VAcw+aHh4vRV5IPNhILUCsOzRmsTmSQ17jIuqopAentWoehktxGd9e/hbIXq980/1QJg==", + "dev": true + }, "node_modules/lodash.isfunction": { "version": "3.0.9", "resolved": "https://registry.npmjs.org/lodash.isfunction/-/lodash.isfunction-3.0.9.tgz", "integrity": "sha512-AirXNj15uRIMMPihnkInB4i3NHeb4iBtNg9WRWuK2o31S+ePwwNmDPaTL3o7dTJ+VXNZim7rFs4rxN4YU1oUJw==", "dev": true }, + "node_modules/lodash.isinteger": { + "version": "4.0.4", + "resolved": "https://registry.npmjs.org/lodash.isinteger/-/lodash.isinteger-4.0.4.tgz", + "integrity": "sha512-DBwtEWN2caHQ9/imiNeEA5ys1JoRtRfY3d7V9wkqtbycnAmTvRRmbHKDV4a0EYc678/dia0jrte4tjYwVBaZUA==", + "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.isnumber": { + "version": "3.0.3", + "resolved": "https://registry.npmjs.org/lodash.isnumber/-/lodash.isnumber-3.0.3.tgz", + "integrity": "sha512-QYqzpfwO3/CWf3XP+Z+tkQsfaLL/EnUlXWVkIk5FUPc4sBdTehEqZONuyRt2P67PXAk+NXmTBcc97zw9t1FQrw==", + "dev": true + }, "node_modules/lodash.isplainobject": { "version": "4.0.6", "resolved": "https://registry.npmjs.org/lodash.isplainobject/-/lodash.isplainobject-4.0.6.tgz", "integrity": "sha512-oSXzaWypCMHkPC3NvBEaPHf0KsA5mvPrOPgQWDsbg8n7orZ290M0BmC/jgRZ4vcJ6DTAhjrsSYgdsW/F+MFOBA==", "dev": true }, + "node_modules/lodash.isstring": { + "version": "4.0.1", + "resolved": "https://registry.npmjs.org/lodash.isstring/-/lodash.isstring-4.0.1.tgz", + "integrity": "sha512-0wJxfxH1wgO3GrbuP+dTTk7op+6L41QCXbGINEmD+ny/G/eCqGzxyCsh7159S+mgDDcoarnBw6PC1PS5+wUGgw==", + "dev": true + }, "node_modules/lodash.kebabcase": { "version": "4.1.1", "resolved": "https://registry.npmjs.org/lodash.kebabcase/-/lodash.kebabcase-4.1.1.tgz", @@ -9694,6 +11098,12 @@ "integrity": "sha512-GK3g5RPZWTRSeLSpgP8Xhra+pnjBC56q9FZYe1d5RN3TJ35dbkGy3YqBSMbyCrlbi+CM9Z3Jk5yTL7RCsqboyQ==", "dev": true }, + "node_modules/lodash.once": { + "version": "4.1.1", + "resolved": "https://registry.npmjs.org/lodash.once/-/lodash.once-4.1.1.tgz", + "integrity": "sha512-Sb487aTOCr9drQVL8pIxOzVhafOjZN9UU54hiN8PU3uAiSV7lx1yYNpbNmex2PK6dSJoNTSJUUswT651yww3Mg==", + "dev": true + }, "node_modules/lodash.snakecase": { "version": "4.1.1", "resolved": "https://registry.npmjs.org/lodash.snakecase/-/lodash.snakecase-4.1.1.tgz", @@ -9743,6 +11153,31 @@ "node": ">=0.10.0" } }, + "node_modules/lowdb": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/lowdb/-/lowdb-1.0.0.tgz", + "integrity": "sha512-2+x8esE/Wb9SQ1F9IHaYWfsC9FIecLOPrK4g17FGEayjUWH172H6nwicRovGvSE2CPZouc2MCIqCI7h9d+GftQ==", + "dev": true, + "dependencies": { + "graceful-fs": "^4.1.3", + "is-promise": "^2.1.0", + "lodash": "4", + "pify": "^3.0.0", + "steno": "^0.4.1" + }, + "engines": { + "node": ">=4" + } + }, + "node_modules/lowdb/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/lowercase-keys": { "version": "2.0.0", "resolved": "https://registry.npmjs.org/lowercase-keys/-/lowercase-keys-2.0.0.tgz", @@ -9803,6 +11238,15 @@ "url": "https://github.com/sponsors/sindresorhus" } }, + "node_modules/media-typer": { + "version": "0.3.0", + "resolved": "https://registry.npmjs.org/media-typer/-/media-typer-0.3.0.tgz", + "integrity": "sha512-dq+qelQ9akHpcOl/gUVRTxVIOkAJ1wR3QAvb4RsVjS8oVoFjDGTc679wJYmUmknUF5HwMLOgb5O+a3KxfWapPQ==", + "dev": true, + "engines": { + "node": ">= 0.6" + } + }, "node_modules/meow": { "version": "8.1.2", "resolved": "https://registry.npmjs.org/meow/-/meow-8.1.2.tgz", @@ -9984,6 +11428,12 @@ "integrity": "sha512-jz+Cfrg9GWOZbQAnDQ4hlVnQky+341Yk5ru8bZSe6sIDTCIg8n9i/u7hSQGSVOF3C7lH6mGtqjkiT9G4wFLL0w==", "dev": true }, + "node_modules/merge-descriptors": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/merge-descriptors/-/merge-descriptors-1.0.1.tgz", + "integrity": "sha512-cCi6g3/Zr1iqQi6ySbseM1Xvooa98N0w31jzUYrXPX2xqObmFGHJ0tQ5u74H3mVh7wLouTseZyYIq39g8cNp1w==", + "dev": true + }, "node_modules/merge-stream": { "version": "2.0.0", "resolved": "https://registry.npmjs.org/merge-stream/-/merge-stream-2.0.0.tgz", @@ -9999,6 +11449,15 @@ "node": ">= 8" } }, + "node_modules/methods": { + "version": "1.1.2", + "resolved": "https://registry.npmjs.org/methods/-/methods-1.1.2.tgz", + "integrity": "sha512-iclAHeNqNm68zFtnZ0e+1L2yUIdvzNoauKU4WBA3VvH/vPFieF7qfRlwUZU+DA9P9bPXIS90ulxoUoCH23sV2w==", + "dev": true, + "engines": { + "node": ">= 0.6" + } + }, "node_modules/micromatch": { "version": "4.0.5", "resolved": "https://registry.npmjs.org/micromatch/-/micromatch-4.0.5.tgz", @@ -10012,6 +11471,18 @@ "node": ">=8.6" } }, + "node_modules/mime": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/mime/-/mime-3.0.0.tgz", + "integrity": "sha512-jSCU7/VB1loIWBZe14aEYHU/+1UMEHoaO7qxCOVJOw9GgH72VAWppxNcjU+x9a2k3GSIBXNKxXQFqRvvZ7vr3A==", + "dev": true, + "bin": { + "mime": "cli.js" + }, + "engines": { + "node": ">=10.0.0" + } + }, "node_modules/mime-db": { "version": "1.52.0", "resolved": "https://registry.npmjs.org/mime-db/-/mime-db-1.52.0.tgz", @@ -10095,6 +11566,18 @@ "node": ">= 6" } }, + "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/modify-values": { "version": "1.0.1", "resolved": "https://registry.npmjs.org/modify-values/-/modify-values-1.0.1.tgz", @@ -10150,18 +11633,138 @@ "integrity": "sha512-nnbWWOkoWyUsTjKrhgD0dcz22mdkSnpYqbEjIm2nhwhuxlSkpywJmBo8h0ZqJdkp73mb90SssHkN4rsRaBAfAA==", "dev": true }, + "node_modules/mv": { + "version": "2.1.1", + "resolved": "https://registry.npmjs.org/mv/-/mv-2.1.1.tgz", + "integrity": "sha512-at/ZndSy3xEGJ8i0ygALh8ru9qy7gWW1cmkaqBN29JmMlIvM//MEO9y1sk/avxuwnPcfhkejkLsuPxH81BrkSg==", + "dev": true, + "dependencies": { + "mkdirp": "~0.5.1", + "ncp": "~2.0.0", + "rimraf": "~2.4.0" + }, + "engines": { + "node": ">=0.8.0" + } + }, + "node_modules/mv/node_modules/glob": { + "version": "6.0.4", + "resolved": "https://registry.npmjs.org/glob/-/glob-6.0.4.tgz", + "integrity": "sha512-MKZeRNyYZAVVVG1oZeLaWie1uweH40m9AZwIwxyPbTSX4hHrVYSzLg0Ro5Z5R7XKkIX+Cc6oD1rqeDJnwsB8/A==", + "dev": true, + "dependencies": { + "inflight": "^1.0.4", + "inherits": "2", + "minimatch": "2 || 3", + "once": "^1.3.0", + "path-is-absolute": "^1.0.0" + }, + "engines": { + "node": "*" + } + }, + "node_modules/mv/node_modules/mkdirp": { + "version": "0.5.6", + "resolved": "https://registry.npmjs.org/mkdirp/-/mkdirp-0.5.6.tgz", + "integrity": "sha512-FP+p8RB8OWpF3YZBCrP5gtADmtXApB5AMLn+vdyA+PyxCjrCs00mjyUozssO33cwDeT3wNGdLxJ5M//YqtHAJw==", + "dev": true, + "dependencies": { + "minimist": "^1.2.6" + }, + "bin": { + "mkdirp": "bin/cmd.js" + } + }, + "node_modules/mv/node_modules/rimraf": { + "version": "2.4.5", + "resolved": "https://registry.npmjs.org/rimraf/-/rimraf-2.4.5.tgz", + "integrity": "sha512-J5xnxTyqaiw06JjMftq7L9ouA448dw/E7dKghkP9WpKNuwmARNNg+Gk8/u5ryb9N/Yo2+z3MCwuqFK/+qPOPfQ==", + "dev": true, + "dependencies": { + "glob": "^6.0.1" + }, + "bin": { + "rimraf": "bin.js" + } + }, + "node_modules/nanoclone": { + "version": "0.2.1", + "resolved": "https://registry.npmjs.org/nanoclone/-/nanoclone-0.2.1.tgz", + "integrity": "sha512-wynEP02LmIbLpcYw8uBKpcfF6dmg2vcpKqxeH5UcoKEYdExslsdUA4ugFauuaeYdTB76ez6gJW8XAZ6CgkXYxA==", + "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/ncp": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/ncp/-/ncp-2.0.0.tgz", + "integrity": "sha512-zIdGUrPRFTUELUvr3Gmc7KZ2Sw/h1PiVM0Af/oHB6zgnV1ikqSfRk+TOufi79aHYCW3NiOXmr1BP5nWbzojLaA==", + "dev": true, + "bin": { + "ncp": "bin/ncp" + } + }, + "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-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-fetch/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/node-fetch/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/node-fetch/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/node-int64": { "version": "0.4.0", "resolved": "https://registry.npmjs.org/node-int64/-/node-int64-0.4.0.tgz", @@ -10341,6 +11944,60 @@ "js-yaml": "bin/js-yaml.js" } }, + "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==", + "dev": true, + "engines": { + "node": "*" + } + }, + "node_modules/object-assign": { + "version": "4.1.1", + "resolved": "https://registry.npmjs.org/object-assign/-/object-assign-4.1.1.tgz", + "integrity": "sha512-rJgTQnkUnH1sFw8yT6VSU3zD3sWmu6sZhIseY8VX+GRu3P6F7Fu+JNDoXfklElbLJSnc3FUQHVe4cU5hj+BcUg==", + "dev": true, + "engines": { + "node": ">=0.10.0" + } + }, + "node_modules/object-inspect": { + "version": "1.13.1", + "resolved": "https://registry.npmjs.org/object-inspect/-/object-inspect-1.13.1.tgz", + "integrity": "sha512-5qoj1RUiKOMsCCNLV1CBiPYE10sziTsnmNxkAI/rZhiD63CF7IqdFGC/XzjWjpSgLf0LxXX3bDFIh0E18f6UhQ==", + "dev": true, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/on-exit-leak-free": { + "version": "0.2.0", + "resolved": "https://registry.npmjs.org/on-exit-leak-free/-/on-exit-leak-free-0.2.0.tgz", + "integrity": "sha512-dqaz3u44QbRXQooZLTUKU41ZrzYrcvLISVgbrzbyCMxpmSLJvZ3ZamIJIZ29P6OhZIkNIQKosdeM6t1LYbA9hg==", + "dev": true + }, + "node_modules/on-finished": { + "version": "2.4.1", + "resolved": "https://registry.npmjs.org/on-finished/-/on-finished-2.4.1.tgz", + "integrity": "sha512-oVlzkg3ENAhCk2zdv7IJwd/QUD4z2RxRwpkcGY8psCVcCYZNq4wYnVWALHM+brtuJjePWiYF/ClmuDr8Ch5+kg==", + "dev": true, + "dependencies": { + "ee-first": "1.1.1" + }, + "engines": { + "node": ">= 0.8" + } + }, + "node_modules/on-headers": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/on-headers/-/on-headers-1.0.2.tgz", + "integrity": "sha512-pZAE+FJLoyITytdqK0U5s+FIpjN0JP3OzFi/u8Rx+EV5/W+JTWGXG8xFzevE7AjBfDqHv/8vL8qQsIhHnqRkrA==", + "dev": true, + "engines": { + "node": ">= 0.8" + } + }, "node_modules/once": { "version": "1.4.0", "resolved": "https://registry.npmjs.org/once/-/once-1.4.0.tgz", @@ -10557,6 +12214,15 @@ "url": "https://github.com/inikulin/parse5?sponsor=1" } }, + "node_modules/parseurl": { + "version": "1.3.3", + "resolved": "https://registry.npmjs.org/parseurl/-/parseurl-1.3.3.tgz", + "integrity": "sha512-CiyeOxFT/JZyN5m0z9PfXw4SCBJ6Sygz1Dpl0wqjlhDEGGBP1GnsUVEL0p63hoG1fcj3fHynXi9NYO4nWOL+qQ==", + "dev": true, + "engines": { + "node": ">= 0.8" + } + }, "node_modules/path-exists": { "version": "4.0.0", "resolved": "https://registry.npmjs.org/path-exists/-/path-exists-4.0.0.tgz", @@ -10590,6 +12256,12 @@ "integrity": "sha512-LDJzPVEEEPR+y48z93A0Ed0yXb8pAByGWo/k5YYdYgpY2/2EsOsksJrq7lOHxryrVOn1ejG6oAp8ahvOIQD8sw==", "dev": true }, + "node_modules/path-to-regexp": { + "version": "0.1.7", + "resolved": "https://registry.npmjs.org/path-to-regexp/-/path-to-regexp-0.1.7.tgz", + "integrity": "sha512-5DFkuoqlv1uYQKxy8omFBeJPQcdoE07Kv2sferDCrAq1ohOU+MSDswDIbnx3YAM60qIOnYa53wBhXW0EbMonrQ==", + "dev": true + }, "node_modules/path-type": { "version": "4.0.0", "resolved": "https://registry.npmjs.org/path-type/-/path-type-4.0.0.tgz", @@ -10612,6 +12284,12 @@ "url": "https://github.com/sponsors/Borewit" } }, + "node_modules/performance-now": { + "version": "2.1.0", + "resolved": "https://registry.npmjs.org/performance-now/-/performance-now-2.1.0.tgz", + "integrity": "sha512-7EAHlyLHI56VEIdK57uwHdHKIaAGbnXPiw0yWbarQZOKaKpvUIgW0jWRVLiatnM+XXlSwsanIBH/hzGMJulMow==", + "dev": true + }, "node_modules/picocolors": { "version": "1.0.0", "resolved": "https://registry.npmjs.org/picocolors/-/picocolors-1.0.0.tgz", @@ -10639,6 +12317,121 @@ "node": ">=0.10.0" } }, + "node_modules/pino": { + "version": "7.11.0", + "resolved": "https://registry.npmjs.org/pino/-/pino-7.11.0.tgz", + "integrity": "sha512-dMACeu63HtRLmCG8VKdy4cShCPKaYDR4youZqoSWLxl5Gu99HUw8bw75thbPv9Nip+H+QYX8o3ZJbTdVZZ2TVg==", + "dev": true, + "dependencies": { + "atomic-sleep": "^1.0.0", + "fast-redact": "^3.0.0", + "on-exit-leak-free": "^0.2.0", + "pino-abstract-transport": "v0.5.0", + "pino-std-serializers": "^4.0.0", + "process-warning": "^1.0.0", + "quick-format-unescaped": "^4.0.3", + "real-require": "^0.1.0", + "safe-stable-stringify": "^2.1.0", + "sonic-boom": "^2.2.1", + "thread-stream": "^0.15.1" + }, + "bin": { + "pino": "bin.js" + } + }, + "node_modules/pino-abstract-transport": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/pino-abstract-transport/-/pino-abstract-transport-1.0.0.tgz", + "integrity": "sha512-c7vo5OpW4wIS42hUVcT5REsL8ZljsUfBjqV/e2sFxmFEFZiq1XLUp5EYLtuDH6PEHq9W1egWqRbnLUP5FuZmOA==", + "dev": true, + "dependencies": { + "readable-stream": "^4.0.0", + "split2": "^4.0.0" + } + }, + "node_modules/pino-abstract-transport/node_modules/buffer": { + "version": "6.0.3", + "resolved": "https://registry.npmjs.org/buffer/-/buffer-6.0.3.tgz", + "integrity": "sha512-FTiCpNxtwiZZHEZbcbTIcZjERVICn9yq/pDFkTl95/AxzD1naBctN7YO68riM/gLSDY7sdrMby8hofADYuuqOA==", + "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.2.1" + } + }, + "node_modules/pino-abstract-transport/node_modules/readable-stream": { + "version": "4.4.2", + "resolved": "https://registry.npmjs.org/readable-stream/-/readable-stream-4.4.2.tgz", + "integrity": "sha512-Lk/fICSyIhodxy1IDK2HazkeGjSmezAWX2egdtJnYhtzKEsBPJowlI6F6LPb5tqIQILrMbx22S5o3GuJavPusA==", + "dev": true, + "dependencies": { + "abort-controller": "^3.0.0", + "buffer": "^6.0.3", + "events": "^3.3.0", + "process": "^0.11.10", + "string_decoder": "^1.3.0" + }, + "engines": { + "node": "^12.22.0 || ^14.17.0 || >=16.0.0" + } + }, + "node_modules/pino-abstract-transport/node_modules/split2": { + "version": "4.2.0", + "resolved": "https://registry.npmjs.org/split2/-/split2-4.2.0.tgz", + "integrity": "sha512-UcjcJOWknrNkF6PLX83qcHM6KHgVKNkV62Y8a5uYDVv9ydGQVwAHMKqHdJje1VTWpljG0WYpCDhrCdAOYH4TWg==", + "dev": true, + "engines": { + "node": ">= 10.x" + } + }, + "node_modules/pino-std-serializers": { + "version": "4.0.0", + "resolved": "https://registry.npmjs.org/pino-std-serializers/-/pino-std-serializers-4.0.0.tgz", + "integrity": "sha512-cK0pekc1Kjy5w9V2/n+8MkZwusa6EyyxfeQCB799CQRhRt/CqYKiWs5adeu8Shve2ZNffvfC/7J64A2PJo1W/Q==", + "dev": true + }, + "node_modules/pino/node_modules/pino-abstract-transport": { + "version": "0.5.0", + "resolved": "https://registry.npmjs.org/pino-abstract-transport/-/pino-abstract-transport-0.5.0.tgz", + "integrity": "sha512-+KAgmVeqXYbTtU2FScx1XS3kNyfZ5TrXY07V96QnUSFqo2gAqlvmaxH67Lj7SWazqsMabf+58ctdTcBgnOLUOQ==", + "dev": true, + "dependencies": { + "duplexify": "^4.1.2", + "split2": "^4.0.0" + } + }, + "node_modules/pino/node_modules/sonic-boom": { + "version": "2.8.0", + "resolved": "https://registry.npmjs.org/sonic-boom/-/sonic-boom-2.8.0.tgz", + "integrity": "sha512-kuonw1YOYYNOve5iHdSahXPOK49GqwA+LZhI6Wz/l0rP57iKyXXIHaRagOBHAPmGwJC6od2Z9zgvZ5loSgMlVg==", + "dev": true, + "dependencies": { + "atomic-sleep": "^1.0.0" + } + }, + "node_modules/pino/node_modules/split2": { + "version": "4.2.0", + "resolved": "https://registry.npmjs.org/split2/-/split2-4.2.0.tgz", + "integrity": "sha512-UcjcJOWknrNkF6PLX83qcHM6KHgVKNkV62Y8a5uYDVv9ydGQVwAHMKqHdJje1VTWpljG0WYpCDhrCdAOYH4TWg==", + "dev": true, + "engines": { + "node": ">= 10.x" + } + }, "node_modules/pirates": { "version": "4.0.6", "resolved": "https://registry.npmjs.org/pirates/-/pirates-4.0.6.tgz", @@ -10712,6 +12505,15 @@ "node": ">=8" } }, + "node_modules/pkginfo": { + "version": "0.4.1", + "resolved": "https://registry.npmjs.org/pkginfo/-/pkginfo-0.4.1.tgz", + "integrity": "sha512-8xCNE/aT/EXKenuMDZ+xTVwkT8gsoHN2z/Q29l80u0ppGEXVvsKRzNMbtKhg8LS8k1tJLAHHylf6p4VFmP6XUQ==", + "dev": true, + "engines": { + "node": ">= 0.4.0" + } + }, "node_modules/prelude-ls": { "version": "1.2.1", "resolved": "https://registry.npmjs.org/prelude-ls/-/prelude-ls-1.2.1.tgz", @@ -10906,12 +12708,27 @@ "node": "^14.17.0 || ^16.13.0 || >=18.0.0" } }, + "node_modules/process": { + "version": "0.11.10", + "resolved": "https://registry.npmjs.org/process/-/process-0.11.10.tgz", + "integrity": "sha512-cdGef/drWFoydD1JsMzuFf8100nZl+GT+yacc2bEced5f9Rjk4z+WtFUTBu9PhOi9j/jfmBPu0mMEY4wIdAF8A==", + "dev": true, + "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==", "dev": true }, + "node_modules/process-warning": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/process-warning/-/process-warning-1.0.0.tgz", + "integrity": "sha512-du4wfLyj4yCZq1VupnVSZmRsPJsNuxoDQFdCFHLaYiEbFBD7QE0a+I4D7hOxrVnh78QE/YipFAj9lXHiXocV+Q==", + "dev": true + }, "node_modules/prompts": { "version": "2.4.2", "resolved": "https://registry.npmjs.org/prompts/-/prompts-2.4.2.tgz", @@ -10925,6 +12742,25 @@ "node": ">= 6" } }, + "node_modules/property-expr": { + "version": "2.0.6", + "resolved": "https://registry.npmjs.org/property-expr/-/property-expr-2.0.6.tgz", + "integrity": "sha512-SVtmxhRE/CGkn3eZY1T6pC8Nln6Fr/lu1mKSgRud0eC73whjGfoAogbn78LkD8aFL0zz3bAFerKSnOl7NlErBA==", + "dev": true + }, + "node_modules/proxy-addr": { + "version": "2.0.7", + "resolved": "https://registry.npmjs.org/proxy-addr/-/proxy-addr-2.0.7.tgz", + "integrity": "sha512-llQsMLSUDUPT44jdrU/O37qlnifitDP+ZwrmmZcoSKyLKvtZxpyV0n2/bD/N4tBAAZ/gJEdZU7KMraoK1+XYAg==", + "dev": true, + "dependencies": { + "forwarded": "0.2.0", + "ipaddr.js": "1.9.1" + }, + "engines": { + "node": ">= 0.10" + } + }, "node_modules/proxy-from-env": { "version": "1.1.0", "resolved": "https://registry.npmjs.org/proxy-from-env/-/proxy-from-env-1.1.0.tgz", @@ -10988,6 +12824,21 @@ "teleport": ">=0.2.0" } }, + "node_modules/qs": { + "version": "6.11.0", + "resolved": "https://registry.npmjs.org/qs/-/qs-6.11.0.tgz", + "integrity": "sha512-MvjoMCJwEarSbUYk5O+nmoSzSutSsTwF85zcHPQ9OrlFoZOYIjaqBAJIqIXjptyD5vThxGq52Xu/MaJzRkIk4Q==", + "dev": true, + "dependencies": { + "side-channel": "^1.0.4" + }, + "engines": { + "node": ">=0.6" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, "node_modules/querystringify": { "version": "2.2.0", "resolved": "https://registry.npmjs.org/querystringify/-/querystringify-2.2.0.tgz", @@ -11014,6 +12865,12 @@ } ] }, + "node_modules/quick-format-unescaped": { + "version": "4.0.4", + "resolved": "https://registry.npmjs.org/quick-format-unescaped/-/quick-format-unescaped-4.0.4.tgz", + "integrity": "sha512-tYC1Q1hgyRuHgloV/YXs2w15unPVh8qfu/qCTfhTYamaw7fyhumKa2yGpdSo87vY32rIclj+4fWYQXUMs9EHvg==", + "dev": true + }, "node_modules/quick-lru": { "version": "5.1.1", "resolved": "https://registry.npmjs.org/quick-lru/-/quick-lru-5.1.1.tgz", @@ -11026,6 +12883,39 @@ "url": "https://github.com/sponsors/sindresorhus" } }, + "node_modules/range-parser": { + "version": "1.2.1", + "resolved": "https://registry.npmjs.org/range-parser/-/range-parser-1.2.1.tgz", + "integrity": "sha512-Hrgsx+orqoygnmhFbKaHE6c296J+HTAQXoxEF6gNupROmmGJRoyzfG3ccAveqCBrwr/2yxQ5BVd/GTl5agOwSg==", + "dev": true, + "engines": { + "node": ">= 0.6" + } + }, + "node_modules/raw-body": { + "version": "2.5.1", + "resolved": "https://registry.npmjs.org/raw-body/-/raw-body-2.5.1.tgz", + "integrity": "sha512-qqJBtEyVgS0ZmPGdCFPWJ3FreoqvG4MVQln/kCgF7Olq95IbOp0/BWyMwbdtn4VTvkM8Y7khCQ2Xgk/tcrCXig==", + "dev": true, + "dependencies": { + "bytes": "3.1.2", + "http-errors": "2.0.0", + "iconv-lite": "0.4.24", + "unpipe": "1.0.0" + }, + "engines": { + "node": ">= 0.8" + } + }, + "node_modules/raw-body/node_modules/bytes": { + "version": "3.1.2", + "resolved": "https://registry.npmjs.org/bytes/-/bytes-3.1.2.tgz", + "integrity": "sha512-/Nf7TyzTx6S3yRJObOAV7956r8cr2+Oj8AC5dt8wSP3BQAoeX58NoHyCU8P8zGkNXStjTSi6fzO6F0pBdcYbEg==", + "dev": true, + "engines": { + "node": ">= 0.8" + } + }, "node_modules/react-is": { "version": "18.2.0", "resolved": "https://registry.npmjs.org/react-is/-/react-is-18.2.0.tgz", @@ -11204,6 +13094,15 @@ "url": "https://github.com/sponsors/Borewit" } }, + "node_modules/real-require": { + "version": "0.1.0", + "resolved": "https://registry.npmjs.org/real-require/-/real-require-0.1.0.tgz", + "integrity": "sha512-r/H9MzAWtrv8aSVjPCMFpDMl5q66GqtmmRkRjpHTsp4zBAa+snZyiQNlMONiUmEJcsnaw0wCauJ2GWODr/aFkg==", + "dev": true, + "engines": { + "node": ">= 12.13.0" + } + }, "node_modules/redent": { "version": "3.0.0", "resolved": "https://registry.npmjs.org/redent/-/redent-3.0.0.tgz", @@ -11288,6 +13187,74 @@ "jsesc": "bin/jsesc" } }, + "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/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==", + "dev": true, + "dependencies": { + "asynckit": "^0.4.0", + "combined-stream": "^1.0.6", + "mime-types": "^2.1.12" + }, + "engines": { + "node": ">= 0.12" + } + }, + "node_modules/request/node_modules/qs": { + "version": "6.5.3", + "resolved": "https://registry.npmjs.org/qs/-/qs-6.5.3.tgz", + "integrity": "sha512-qxXIEh4pCGfHICj1mAJQ2/2XVZkjCDTcEgfoSQxc/fYivUZxTkk7L3bDBJSoNrEzXI17oUO5Dp07ktqE5KzczA==", + "dev": true, + "engines": { + "node": ">=0.6" + } + }, + "node_modules/request/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/require-directory": { "version": "2.1.1", "resolved": "https://registry.npmjs.org/require-directory/-/require-directory-2.1.1.tgz", @@ -11492,6 +13459,15 @@ } ] }, + "node_modules/safe-stable-stringify": { + "version": "2.4.3", + "resolved": "https://registry.npmjs.org/safe-stable-stringify/-/safe-stable-stringify-2.4.3.tgz", + "integrity": "sha512-e2bDA2WJT0wxseVd4lsDP4+3ONX6HpMXQa1ZhFQ7SU+GjvORCmShbCMltrtIDfkYhVHrOcPtj+KhmDBdPdZD1g==", + "dev": true, + "engines": { + "node": ">=10" + } + }, "node_modules/safer-buffer": { "version": "2.1.2", "resolved": "https://registry.npmjs.org/safer-buffer/-/safer-buffer-2.1.2.tgz", @@ -11530,44 +13506,137 @@ "resolved": "https://registry.npmjs.org/semver-regex/-/semver-regex-4.0.5.tgz", "integrity": "sha512-hunMQrEy1T6Jr2uEVjrAIqjwWcQTgOAcIM52C8MY1EZSD3DDNft04XzvYKPqjED65bNVVko0YI38nYeEHCX3yw==", "dev": true, - "engines": { - "node": ">=12" + "engines": { + "node": ">=12" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" + } + }, + "node_modules/semver-truncate": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/semver-truncate/-/semver-truncate-3.0.0.tgz", + "integrity": "sha512-LJWA9kSvMolR51oDE6PN3kALBNaUdkxzAGcexw8gjMA8xr5zUqK0JiR3CgARSqanYF3Z1YHvsErb1KDgh+v7Rg==", + "dev": true, + "dependencies": { + "semver": "^7.3.5" + }, + "engines": { + "node": ">=12" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" + } + }, + "node_modules/semver/node_modules/lru-cache": { + "version": "6.0.0", + "resolved": "https://registry.npmjs.org/lru-cache/-/lru-cache-6.0.0.tgz", + "integrity": "sha512-Jo6dJ04CmSjuznwJSS3pUeWmd/H0ffTlkXXgwZi+eq1UCmqQwCh+eLsYOYCwY991i2Fah4h1BEMCx4qThGbsiA==", + "dev": true, + "dependencies": { + "yallist": "^4.0.0" + }, + "engines": { + "node": ">=10" + } + }, + "node_modules/semver/node_modules/yallist": { + "version": "4.0.0", + "resolved": "https://registry.npmjs.org/yallist/-/yallist-4.0.0.tgz", + "integrity": "sha512-3wdGidZyq5PB084XLES5TpOSRA3wjXAlIWMhum2kRcv/41Sn2emQ0dycQW4uZXLejwKvg6EsvbdlVL+FYEct7A==", + "dev": true + }, + "node_modules/send": { + "version": "0.18.0", + "resolved": "https://registry.npmjs.org/send/-/send-0.18.0.tgz", + "integrity": "sha512-qqWzuOjSFOuqPjFe4NOsMLafToQQwBSOEpS+FwEt3A2V3vKubTquT3vmLTQpFgMXp8AlFWFuP1qKaJZOtPpVXg==", + "dev": true, + "dependencies": { + "debug": "2.6.9", + "depd": "2.0.0", + "destroy": "1.2.0", + "encodeurl": "~1.0.2", + "escape-html": "~1.0.3", + "etag": "~1.8.1", + "fresh": "0.5.2", + "http-errors": "2.0.0", + "mime": "1.6.0", + "ms": "2.1.3", + "on-finished": "2.4.1", + "range-parser": "~1.2.1", + "statuses": "2.0.1" + }, + "engines": { + "node": ">= 0.8.0" + } + }, + "node_modules/send/node_modules/debug": { + "version": "2.6.9", + "resolved": "https://registry.npmjs.org/debug/-/debug-2.6.9.tgz", + "integrity": "sha512-bC7ElrdJaJnPbAP+1EotYvqZsb3ecl5wi6Bfi6BJTUcNowp6cvspg0jXznRTKDjm/E7AdgFBVeAPVMNcKGsHMA==", + "dev": true, + "dependencies": { + "ms": "2.0.0" + } + }, + "node_modules/send/node_modules/debug/node_modules/ms": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/ms/-/ms-2.0.0.tgz", + "integrity": "sha512-Tpp60P6IUJDTuOq/5Z8cdskzJujfwqfOTkrwIwj7IRISpnkJnT6SyJ4PCPnGMoFjC9ddhal5KVIYtAt97ix05A==", + "dev": true + }, + "node_modules/send/node_modules/mime": { + "version": "1.6.0", + "resolved": "https://registry.npmjs.org/mime/-/mime-1.6.0.tgz", + "integrity": "sha512-x0Vn8spI+wuJ1O6S7gnbaQg8Pxh4NNHb7KSINmEWKiPE4RKOplvijn+NkmYmmRgP68mc70j2EbeTFRsrswaQeg==", + "dev": true, + "bin": { + "mime": "cli.js" }, - "funding": { - "url": "https://github.com/sponsors/sindresorhus" + "engines": { + "node": ">=4" } }, - "node_modules/semver-truncate": { - "version": "3.0.0", - "resolved": "https://registry.npmjs.org/semver-truncate/-/semver-truncate-3.0.0.tgz", - "integrity": "sha512-LJWA9kSvMolR51oDE6PN3kALBNaUdkxzAGcexw8gjMA8xr5zUqK0JiR3CgARSqanYF3Z1YHvsErb1KDgh+v7Rg==", + "node_modules/send/node_modules/ms": { + "version": "2.1.3", + "resolved": "https://registry.npmjs.org/ms/-/ms-2.1.3.tgz", + "integrity": "sha512-6FlzubTLZG3J2a/NVCAleEhjzq5oxgHyaCU9yYXvcLsvoVaHJq/s5xXI6/XXP6tz7R9xAOtHnSO/tXtF3WRTlA==", + "dev": true + }, + "node_modules/serve-static": { + "version": "1.15.0", + "resolved": "https://registry.npmjs.org/serve-static/-/serve-static-1.15.0.tgz", + "integrity": "sha512-XGuRDNjXUijsUL0vl6nSD7cwURuzEgglbOaFuZM9g3kwDXOWVTck0jLzjPzGD+TazWbboZYu52/9/XPdUgne9g==", "dev": true, "dependencies": { - "semver": "^7.3.5" + "encodeurl": "~1.0.2", + "escape-html": "~1.0.3", + "parseurl": "~1.3.3", + "send": "0.18.0" }, "engines": { - "node": ">=12" - }, - "funding": { - "url": "https://github.com/sponsors/sindresorhus" + "node": ">= 0.8.0" } }, - "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==", + "node_modules/set-function-length": { + "version": "1.1.1", + "resolved": "https://registry.npmjs.org/set-function-length/-/set-function-length-1.1.1.tgz", + "integrity": "sha512-VoaqjbBJKiWtg4yRcKBQ7g7wnGnLV3M8oLvVWwOk2PdYY6PEFegR1vezXR0tw6fZGF9csVakIRjrJiy2veSBFQ==", "dev": true, "dependencies": { - "yallist": "^4.0.0" + "define-data-property": "^1.1.1", + "get-intrinsic": "^1.2.1", + "gopd": "^1.0.1", + "has-property-descriptors": "^1.0.0" }, "engines": { - "node": ">=10" + "node": ">= 0.4" } }, - "node_modules/semver/node_modules/yallist": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/yallist/-/yallist-4.0.0.tgz", - "integrity": "sha512-3wdGidZyq5PB084XLES5TpOSRA3wjXAlIWMhum2kRcv/41Sn2emQ0dycQW4uZXLejwKvg6EsvbdlVL+FYEct7A==", + "node_modules/setprototypeof": { + "version": "1.2.0", + "resolved": "https://registry.npmjs.org/setprototypeof/-/setprototypeof-1.2.0.tgz", + "integrity": "sha512-E5LDX7Wrp85Kil5bhZv46j8jOeboKq5JMmYM3gVGdGH8xFpPWXUMsNrlODCrkoxMEeNi/XZIwuRvY4XNwYMJpw==", "dev": true }, "node_modules/shebang-command": { @@ -11591,6 +13660,20 @@ "node": ">=8" } }, + "node_modules/side-channel": { + "version": "1.0.4", + "resolved": "https://registry.npmjs.org/side-channel/-/side-channel-1.0.4.tgz", + "integrity": "sha512-q5XPytqFEIKHkGdiMIrY10mvLRvnQh42/+GoBlFW3b2LXLE2xxJpZFdm94we0BaoV3RwJyGqg5wS7epxTv0Zvw==", + "dev": true, + "dependencies": { + "call-bind": "^1.0.0", + "get-intrinsic": "^1.0.2", + "object-inspect": "^1.9.0" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, "node_modules/signal-exit": { "version": "3.0.7", "resolved": "https://registry.npmjs.org/signal-exit/-/signal-exit-3.0.7.tgz", @@ -11612,6 +13695,15 @@ "node": ">=8" } }, + "node_modules/sonic-boom": { + "version": "3.3.0", + "resolved": "https://registry.npmjs.org/sonic-boom/-/sonic-boom-3.3.0.tgz", + "integrity": "sha512-LYxp34KlZ1a2Jb8ZQgFCK3niIHzibdwtwNUWKg0qQRzsDoJ3Gfgkf8KdBTFU3SkejDEIlWwnSnpVdOZIhFMl/g==", + "dev": true, + "dependencies": { + "atomic-sleep": "^1.0.0" + } + }, "node_modules/sort-keys": { "version": "1.1.2", "resolved": "https://registry.npmjs.org/sort-keys/-/sort-keys-1.1.2.tgz", @@ -11723,6 +13815,31 @@ "integrity": "sha512-D9cPgkvLlV3t3IzL0D0YLvGA9Ahk4PcvVwUbN0dSGr1aP0Nrt4AEnTUbuGvquEC0mA64Gqt1fzirlRs5ibXx8g==", "dev": true }, + "node_modules/sshpk": { + "version": "1.18.0", + "resolved": "https://registry.npmjs.org/sshpk/-/sshpk-1.18.0.tgz", + "integrity": "sha512-2p2KJZTSqQ/I3+HX42EpYOa2l3f8Erv8MWKsy2I9uf4wA7yFIkXRffYdsx86y6z4vHtV8u7g+pPlr8/4ouAxsQ==", + "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/stack-utils": { "version": "2.0.6", "resolved": "https://registry.npmjs.org/stack-utils/-/stack-utils-2.0.6.tgz", @@ -11744,6 +13861,30 @@ "node": ">=8" } }, + "node_modules/statuses": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/statuses/-/statuses-2.0.1.tgz", + "integrity": "sha512-RwNA9Z/7PrK06rYLIzFMlaF+l73iwpzsqRIFgbMLbTcLD6cOao82TaWefPXQvB2fOC4AjuYSEndS7N/mTCbkdQ==", + "dev": true, + "engines": { + "node": ">= 0.8" + } + }, + "node_modules/steno": { + "version": "0.4.4", + "resolved": "https://registry.npmjs.org/steno/-/steno-0.4.4.tgz", + "integrity": "sha512-EEHMVYHNXFHfGtgjNITnka0aHhiAlo93F7z2/Pwd+g0teG9CnM3JIINM7hVVB5/rhw9voufD7Wukwgtw2uqh6w==", + "dev": true, + "dependencies": { + "graceful-fs": "^4.1.3" + } + }, + "node_modules/stream-shift": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/stream-shift/-/stream-shift-1.0.1.tgz", + "integrity": "sha512-AiisoFqQ0vbGcZgQPY1cdP2I76glaVA/RauYR4G4thNFgkTqr90yXTo4LYX60Jl+sIlPNHHdGSwo01AvbKUSVQ==", + "dev": true + }, "node_modules/string_decoder": { "version": "1.3.0", "resolved": "https://registry.npmjs.org/string_decoder/-/string_decoder-1.3.0.tgz", @@ -11964,6 +14105,15 @@ "integrity": "sha512-N+8UisAXDGk8PFXP4HAzVR9nbfmVJ3zYLAWiTIoqC5v5isinhr+r5uaO8+7r3BMfuNIufIsA7RdpVgacC2cSpw==", "dev": true }, + "node_modules/thread-stream": { + "version": "0.15.2", + "resolved": "https://registry.npmjs.org/thread-stream/-/thread-stream-0.15.2.tgz", + "integrity": "sha512-UkEhKIg2pD+fjkHQKyJO3yoIvAP3N6RlNFt2dUhcS1FGvCD1cQa1M/PGknCLFIyZdtJOWQjejp7bdNqmN7zwdA==", + "dev": true, + "dependencies": { + "real-require": "^0.1.0" + } + }, "node_modules/through": { "version": "2.3.8", "resolved": "https://registry.npmjs.org/through/-/through-2.3.8.tgz", @@ -12049,6 +14199,15 @@ "node": ">=8.0" } }, + "node_modules/toidentifier": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/toidentifier/-/toidentifier-1.0.1.tgz", + "integrity": "sha512-o5sSPKEkg/DIQNmH43V0/uerLrpzVedkUh8tGNvaeXpfpuwjKenlSox/2O/BTlZUtEe+JG7s5YhEz608PlAHRA==", + "dev": true, + "engines": { + "node": ">=0.6" + } + }, "node_modules/token-types": { "version": "5.0.1", "resolved": "https://registry.npmjs.org/token-types/-/token-types-5.0.1.tgz", @@ -12066,6 +14225,12 @@ "url": "https://github.com/sponsors/Borewit" } }, + "node_modules/toposort": { + "version": "2.0.2", + "resolved": "https://registry.npmjs.org/toposort/-/toposort-2.0.2.tgz", + "integrity": "sha512-0a5EOkAUp8D4moMi2W8ZF8jcga7BgZd91O/yabJCFY8az+XSzeGyTKs0Aoo897iV1Nj6guFq8orWDS96z91oGg==", + "dev": true + }, "node_modules/tough-cookie": { "version": "4.1.3", "resolved": "https://registry.npmjs.org/tough-cookie/-/tough-cookie-4.1.3.tgz", @@ -12261,6 +14426,39 @@ "resolved": "https://registry.npmjs.org/tslib/-/tslib-2.6.2.tgz", "integrity": "sha512-AEYxH93jGFPn/a2iVAwW87VuUIkR1FVUKB77NwMF7nBTDkDrrT/Hpt/IrCJ0QXhW27jTBDcf5ZY7w6RiqTMw2Q==" }, + "node_modules/tsscmp": { + "version": "1.0.6", + "resolved": "https://registry.npmjs.org/tsscmp/-/tsscmp-1.0.6.tgz", + "integrity": "sha512-LxhtAkPDTkVCMQjt2h6eBVY28KCjikZqZfMcC15YBeNjkgUpdCfBu5HoiOTDu86v6smE8yOjyEktJ8hlbANHQA==", + "dev": true, + "engines": { + "node": ">=0.6.x" + } + }, + "node_modules/tunnel-agent": { + "version": "0.6.0", + "resolved": "https://registry.npmjs.org/tunnel-agent/-/tunnel-agent-0.6.0.tgz", + "integrity": "sha512-McnNiV1l8RYeY8tBgEpuodCC1mLUdbSN+CYBL7kJsJNInOP8UjDDEwdk6Mw60vdLLrr5NHKZhMAOSrR2NZuQ+w==", + "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": "sha512-KXXFFdAbFXY4geFIwoyNK+f5Z1b7swfXABfL7HXCmoIWMKU3dmS26672A4EeQtDzLKy7SXmfBu51JolvEKwtGA==", + "dev": true + }, + "node_modules/typanion": { + "version": "3.14.0", + "resolved": "https://registry.npmjs.org/typanion/-/typanion-3.14.0.tgz", + "integrity": "sha512-ZW/lVMRabETuYCd9O9ZvMhAh8GslSqaUjxmK/JLPCh6l73CvLBiuXswj/+7LdnWOgYsQ130FqLzFz5aGT4I3Ug==", + "dev": true + }, "node_modules/type-check": { "version": "0.4.0", "resolved": "https://registry.npmjs.org/type-check/-/type-check-0.4.0.tgz", @@ -12294,6 +14492,19 @@ "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==", + "dev": true, + "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", @@ -12381,6 +14592,21 @@ "node": ">= 10.0.0" } }, + "node_modules/unix-crypt-td-js": { + "version": "1.1.4", + "resolved": "https://registry.npmjs.org/unix-crypt-td-js/-/unix-crypt-td-js-1.1.4.tgz", + "integrity": "sha512-8rMeVYWSIyccIJscb9NdCfZKSRBKYTeVnwmiRYT2ulE3qd1RaDQ0xQDP+rI3ccIWbhu/zuo5cgN8z73belNZgw==", + "dev": true + }, + "node_modules/unpipe": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/unpipe/-/unpipe-1.0.0.tgz", + "integrity": "sha512-pjy2bYhSsufwWlKwPc+l3cN7+wuJlK6uz0YdJEOlQDbl6jo/YlPi4mb8agUkVC8BF7V8NuzeyPNqRksA3hztKQ==", + "dev": true, + "engines": { + "node": ">= 0.8" + } + }, "node_modules/update-browserslist-db": { "version": "1.0.13", "resolved": "https://registry.npmjs.org/update-browserslist-db/-/update-browserslist-db-1.0.13.tgz", @@ -12436,6 +14662,25 @@ "integrity": "sha512-EPD5q1uXyFxJpCrLnCc1nHnq3gOa6DZBocAIiI2TaSCA7VCJ1UJDMagCzIkXNsUYfD1daK//LTEQ8xiIbrHtcw==", "dev": true }, + "node_modules/utils-merge": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/utils-merge/-/utils-merge-1.0.1.tgz", + "integrity": "sha512-pMZTvIkT1d+TFGvDOqodOclx0QWkkgi6Tdoa8gC8ffGAAqz9pzPTZWAybbsHHoED/ztMtkv/VoYTYyShUn81hA==", + "dev": true, + "engines": { + "node": ">= 0.4.0" + } + }, + "node_modules/uuid": { + "version": "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/v8-compile-cache": { "version": "2.3.0", "resolved": "https://registry.npmjs.org/v8-compile-cache/-/v8-compile-cache-2.3.0.tgz", @@ -12484,6 +14729,234 @@ "node": "^14.17.0 || ^16.13.0 || >=18.0.0" } }, + "node_modules/validator": { + "version": "13.11.0", + "resolved": "https://registry.npmjs.org/validator/-/validator-13.11.0.tgz", + "integrity": "sha512-Ii+sehpSfZy+At5nPdnyMhx78fEoPDkR2XW/zimHEL3MyGJQOCQ7WeP20jPYRz7ZCpcKLB21NxuXHF3bxjStBQ==", + "dev": true, + "engines": { + "node": ">= 0.10" + } + }, + "node_modules/vary": { + "version": "1.1.2", + "resolved": "https://registry.npmjs.org/vary/-/vary-1.1.2.tgz", + "integrity": "sha512-BNGbWLfd0eUPabhkXUVm0j8uuvREyTh5ovRa/dyow/BqAbZJyC+5fU+IzQOzmAKzYqYRAISoRhdQr3eIZ/PXqg==", + "dev": true, + "engines": { + "node": ">= 0.8" + } + }, + "node_modules/verdaccio": { + "version": "5.27.0", + "resolved": "https://registry.npmjs.org/verdaccio/-/verdaccio-5.27.0.tgz", + "integrity": "sha512-S0XCNgy+s8O3+Prm1uYMYR58WbvsnhUgAm6qk64suZs0YyBrTh/YJSRLYgsjAIiIpO/c2gnvNaDwz2EcX/C7nQ==", + "dev": true, + "dependencies": { + "@verdaccio/config": "7.0.0-next.3", + "@verdaccio/core": "7.0.0-next.3", + "@verdaccio/local-storage": "10.3.3", + "@verdaccio/logger-7": "7.0.0-next.3", + "@verdaccio/middleware": "7.0.0-next.3", + "@verdaccio/search": "7.0.0-next.2", + "@verdaccio/signature": "7.0.0-next.1", + "@verdaccio/streams": "10.2.1", + "@verdaccio/tarball": "12.0.0-next.3", + "@verdaccio/ui-theme": "7.0.0-next.3", + "@verdaccio/url": "12.0.0-next.3", + "@verdaccio/utils": "7.0.0-next.3", + "async": "3.2.4", + "clipanion": "3.2.1", + "compression": "1.7.4", + "cookies": "0.8.0", + "cors": "2.8.5", + "debug": "^4.3.4", + "envinfo": "7.10.0", + "express": "4.18.2", + "express-rate-limit": "5.5.1", + "fast-safe-stringify": "2.1.1", + "handlebars": "4.7.8", + "js-yaml": "4.1.0", + "JSONStream": "1.3.5", + "jsonwebtoken": "9.0.2", + "kleur": "4.1.5", + "lodash": "4.17.21", + "lru-cache": "7.18.3", + "mime": "3.0.0", + "mkdirp": "1.0.4", + "mv": "2.1.1", + "pkginfo": "0.4.1", + "request": "2.88.2", + "semver": "7.5.4", + "validator": "13.11.0", + "verdaccio-audit": "12.0.0-next.3", + "verdaccio-htpasswd": "12.0.0-next.3" + }, + "bin": { + "verdaccio": "bin/verdaccio" + }, + "engines": { + "node": ">=12.18" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/verdaccio" + } + }, + "node_modules/verdaccio-audit": { + "version": "12.0.0-next.3", + "resolved": "https://registry.npmjs.org/verdaccio-audit/-/verdaccio-audit-12.0.0-next.3.tgz", + "integrity": "sha512-LdiCh0fG3u7lsVGxIWZFxZ7ZStsc8u+129T3Rt3wgYOnEn4+NsYGuZJZzoXTBJ+F1ymCjOg77+kpDFHECHxsYA==", + "dev": true, + "dependencies": { + "@verdaccio/config": "7.0.0-next.3", + "@verdaccio/core": "7.0.0-next.3", + "express": "4.18.2", + "https-proxy-agent": "5.0.1", + "node-fetch": "cjs" + }, + "engines": { + "node": ">=12" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/verdaccio" + } + }, + "node_modules/verdaccio-htpasswd": { + "version": "12.0.0-next.3", + "resolved": "https://registry.npmjs.org/verdaccio-htpasswd/-/verdaccio-htpasswd-12.0.0-next.3.tgz", + "integrity": "sha512-/jdfaGQy0ry2gcQiUB6JsKr2esPZtj5ITuYar+NaFIfIOHrUk+NRdmPNHr1XQyofCzwEyENlgtdZMs1K+yeI4w==", + "dev": true, + "dependencies": { + "@verdaccio/core": "7.0.0-next.3", + "@verdaccio/file-locking": "12.0.0-next.1", + "apache-md5": "1.1.8", + "bcryptjs": "2.4.3", + "core-js": "3.30.2", + "debug": "4.3.4", + "http-errors": "2.0.0", + "unix-crypt-td-js": "1.1.4" + }, + "engines": { + "node": ">=12" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/verdaccio" + } + }, + "node_modules/verdaccio-htpasswd/node_modules/@verdaccio/file-locking": { + "version": "12.0.0-next.1", + "resolved": "https://registry.npmjs.org/@verdaccio/file-locking/-/file-locking-12.0.0-next.1.tgz", + "integrity": "sha512-Zb5G2HEhVRB0jCq4z7QA4dqTdRv/2kIsw2Nkm3j2HqC1OeJRxas3MJAF/OxzbAb1IN32lbg1zycMSk6NcbQkgQ==", + "dev": true, + "dependencies": { + "lockfile": "1.0.4" + }, + "engines": { + "node": ">=12" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/verdaccio" + } + }, + "node_modules/verdaccio/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/verdaccio/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/verdaccio/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/verdaccio/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/verdaccio/node_modules/lru-cache": { + "version": "7.18.3", + "resolved": "https://registry.npmjs.org/lru-cache/-/lru-cache-7.18.3.tgz", + "integrity": "sha512-jumlc0BIUrS3qJGgIkWZsyfAM7NCWiBcCDhnd+3NNM5KbBmLTgHVfWBcg6W+rLUsIpzpERPsvwUP7CckAQSOoA==", + "dev": true, + "engines": { + "node": ">=12" + } + }, + "node_modules/verdaccio/node_modules/semver": { + "version": "7.5.4", + "resolved": "https://registry.npmjs.org/semver/-/semver-7.5.4.tgz", + "integrity": "sha512-1bCSESV6Pv+i21Hvpxp3Dx+pSD8lIPt8uVjRrxAUt/nbswYc+tK6Y2btiULjd4+fnq15PX+nqQDC7Oft7WkwcA==", + "dev": true, + "dependencies": { + "lru-cache": "^6.0.0" + }, + "bin": { + "semver": "bin/semver.js" + }, + "engines": { + "node": ">=10" + } + }, + "node_modules/verdaccio/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/verdaccio/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/verror": { + "version": "1.10.0", + "resolved": "https://registry.npmjs.org/verror/-/verror-1.10.0.tgz", + "integrity": "sha512-ZZKSmDAEFOijERBLkmYfJ+vmk3w+7hOLYDNkRCuRuMJGEmqYNCNLyBBFwWKVMhfwaEF3WOd0Zlw86U/WC/+nYw==", + "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/verror/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": "sha512-3lqz5YjWTYnW6dlDa5TLaTCcShfar1e40rmcJVwCBJC6mWlFuj0eCHIElmG1g5kyuJ/GD+8Wn4FFCcz4gJPfaQ==", + "dev": true + }, "node_modules/w3c-xmlserializer": { "version": "4.0.0", "resolved": "https://registry.npmjs.org/w3c-xmlserializer/-/w3c-xmlserializer-4.0.0.tgz", @@ -12751,6 +15224,24 @@ "funding": { "url": "https://github.com/sponsors/sindresorhus" } + }, + "node_modules/yup": { + "version": "0.32.11", + "resolved": "https://registry.npmjs.org/yup/-/yup-0.32.11.tgz", + "integrity": "sha512-Z2Fe1bn+eLstG8DRR6FTavGD+MeAwyfmouhHsIUgaADz8jvFKbO/fXc2trJKZg+5EBjh4gGm3iU/t3onKlXHIg==", + "dev": true, + "dependencies": { + "@babel/runtime": "^7.15.4", + "@types/lodash": "^4.14.175", + "lodash": "^4.17.21", + "lodash-es": "^4.17.21", + "nanoclone": "^0.2.1", + "property-expr": "^2.0.4", + "toposort": "^2.0.2" + }, + "engines": { + "node": ">=10" + } } } } diff --git a/package.json b/package.json index df09e777..76f4ec15 100644 --- a/package.json +++ b/package.json @@ -3,10 +3,9 @@ "version": "0.0.0", "license": "MIT", "scripts": { - "start": "nx serve", - "build": "nx build", - "test": "nx test", - "release": "nx version", + "build": "nx build ngx-deploy-npm", + "test": "nx test ngx-deploy-npm", + "release": "nx version ngx-deploy-npm", "commit": "cz", "prepare": "husky install", "sonar:init-server": "docker-compose up", @@ -45,7 +44,8 @@ "pretty-quick": "^3.1.3", "ts-jest": "29.1.0", "ts-node": "10.9.1", - "typescript": "5.2.2" + "typescript": "5.2.2", + "verdaccio": "^5.0.4" }, "dependencies": { "@swc/helpers": "0.5.3", @@ -60,5 +60,8 @@ "extends": [ "@commitlint/config-conventional" ] + }, + "nx": { + "includedScripts": [] } } diff --git a/packages/ngx-deploy-npm/.eslintrc.json b/packages/ngx-deploy-npm/.eslintrc.json index 9d9c0db5..adbe7ae2 100644 --- a/packages/ngx-deploy-npm/.eslintrc.json +++ b/packages/ngx-deploy-npm/.eslintrc.json @@ -13,6 +13,13 @@ { "files": ["*.js", "*.jsx"], "rules": {} + }, + { + "files": ["*.json"], + "parser": "jsonc-eslint-parser", + "rules": { + "@nx/dependency-checks": "error" + } } ] } diff --git a/packages/ngx-deploy-npm/jest.config.js b/packages/ngx-deploy-npm/jest.config.js index 67b530bc..ccbcfa38 100644 --- a/packages/ngx-deploy-npm/jest.config.js +++ b/packages/ngx-deploy-npm/jest.config.js @@ -12,4 +12,5 @@ module.exports = { }, moduleFileExtensions: ['ts', 'tsx', 'js', 'jsx'], coverageDirectory: '../../coverage/packages/ngx-deploy-npm', + coverageReporters: [['lcov', { projectRoot: 'packages/ngx-deploy-npm' }]], }; diff --git a/packages/ngx-deploy-npm/migrations.json b/packages/ngx-deploy-npm/migrations.json new file mode 100644 index 00000000..a42a3988 --- /dev/null +++ b/packages/ngx-deploy-npm/migrations.json @@ -0,0 +1,14 @@ +{ + "generators": { + "write-dist-folder-path-on-deploy-target-options": { + "version": "8.0.0", + "description": "Sets the distFolderPath option on the deploy target. distFolderPath is now required.", + "implementation": "./src/migrations/8.0.0/write-dist-folder-path-on-deploy-target-options" + }, + "replace-buildtarget-for-depends-on": { + "version": "8.0.0", + "description": "Remove the option `buildTarget` and `noBuild` from the deploy target. If the option `buildTarget` was set, the migration will create a new target to build the library with the desired configuration and create a `dependsOn` on the deploy target to build the library using the just-created target.", + "implementation": "./src/migrations/8.0.0/replace-buildtarget-for-depends-on" + } + } +} diff --git a/packages/ngx-deploy-npm/package.json b/packages/ngx-deploy-npm/package.json index 01b0a6ad..e49c309f 100644 --- a/packages/ngx-deploy-npm/package.json +++ b/packages/ngx-deploy-npm/package.json @@ -37,5 +37,8 @@ "bugs": { "url": "https://github.com/bikecoders/ngx-deploy-npm/issues" }, - "homepage": "https://github.com/bikecoders/ngx-deploy-npm/#readme" + "homepage": "https://github.com/bikecoders/ngx-deploy-npm/#readme", + "nx-migrations": { + "migrations": "./migrations.json" + } } diff --git a/packages/ngx-deploy-npm/project.json b/packages/ngx-deploy-npm/project.json index 74f4bc1b..b9f18f5e 100644 --- a/packages/ngx-deploy-npm/project.json +++ b/packages/ngx-deploy-npm/project.json @@ -10,9 +10,15 @@ "options": { "lintFilePatterns": [ "packages/ngx-deploy-npm/**/*.ts", - "packages/ngx-deploy-npm/package.json" - ], - "outputFile": "reports/ngx-deploy-npm/lint-report" + "packages/ngx-deploy-npm/package.json", + "packages/ngx-deploy-npm/migrations.json" + ] + } + }, + "lint-report": { + "executor": "nx:run-commands", + "options": { + "command": "npx nx lint ngx-deploy-npm --outputFile reports/ngx-deploy-npm/lint-report --format=./tools/sonarqube-linter-reporter.js || true" } }, "test": { @@ -57,6 +63,11 @@ "input": "./packages/ngx-deploy-npm", "glob": "executors.json", "output": "." + }, + { + "input": "./packages/ngx-deploy-npm", + "glob": "migrations.json", + "output": "." } ] } @@ -64,8 +75,10 @@ "deploy": { "executor": "./dist/packages/ngx-deploy-npm:deploy", "options": { + "distFolderPath": "dist/packages/ngx-deploy-npm", "access": "public" - } + }, + "dependsOn": ["build"] }, "version": { "executor": "@jscutlery/semver:version", @@ -81,6 +94,20 @@ }, "dependsOn": ["build"] }, + "yarn-link-it": { + "executor": "nx:run-commands", + "options": { + "command": "cd dist/packages/ngx-deploy-npm && npx --yes yarn link" + }, + "dependsOn": ["build"] + }, + "yarn-unlink-it": { + "executor": "nx:run-commands", + "options": { + "command": "cd dist/packages/ngx-deploy-npm && npx --yes yarn unlink" + }, + "dependsOn": ["build"] + }, "create-nx-workspace": { "executor": "nx:run-commands", "outputs": ["{workspaceRoot}/tmp/nx-workspace"], diff --git a/packages/ngx-deploy-npm/src/__mocks__/generators/index.ts b/packages/ngx-deploy-npm/src/__mocks__/generators/index.ts deleted file mode 100644 index 0ee3596d..00000000 --- a/packages/ngx-deploy-npm/src/__mocks__/generators/index.ts +++ /dev/null @@ -1,290 +0,0 @@ -import * as path from 'path'; -import { ProjectConfiguration } from '@nx/devkit'; - -export const getLibPublishable = (libName: string): ProjectConfiguration => { - const uniqName = `react-lib-${libName}`; - - return { - root: `libs/${uniqName}`, - sourceRoot: `libs/${uniqName}/src`, - projectType: 'library', - tags: [], - targets: { - build: { - executor: '@nx/web:rollup', - outputs: ['{options.outputPath}'], - options: { - outputPath: `dist/libs/${uniqName}`, - tsConfig: `libs/${uniqName}/tsconfig.lib.json`, - project: `libs/${uniqName}/package.json`, - entryFile: `libs/${uniqName}/src/index.ts`, - external: ['react/jsx-runtime'], - rollupConfig: '@nx/react/plugins/bundle-rollup', - compiler: 'babel', - assets: [ - { - glob: `libs/${uniqName}/README.md`, - input: '.', - output: '.', - }, - ], - }, - }, - lint: { - executor: '@nx/eslint:eslint', - outputs: ['{options.outputFile}'], - options: { - lintFilePatterns: [`libs/${uniqName}/**/*.{ts,tsx,js,jsx}`], - }, - }, - test: { - executor: '@nx/jest:jest', - outputs: [`coverage/libs/${uniqName}`], - options: { - jestConfig: `libs/${uniqName}/jest.config.js`, - passWithNoTests: true, - }, - }, - }, - }; -}; - -export const getLibPublishableWithProdMode = ( - libName: string -): ProjectConfiguration => { - const uniqLibName = `angular-lib1-${libName}`; - - return { - projectType: 'library', - root: `packages/${uniqLibName}`, - sourceRoot: `packages/${uniqLibName}/src`, - // prefix: 'proj', - targets: { - build: { - executor: '@nx/angular:package', - outputs: [`dist/packages/${uniqLibName}`], - options: { - project: `packages/${uniqLibName}/ng-package.json`, - }, - configurations: { - production: { - tsConfig: `packages/${uniqLibName}/tsconfig.lib.prod.json`, - }, - development: { - tsConfig: `packages/${uniqLibName}/tsconfig.lib.json`, - }, - }, - defaultConfiguration: 'production', - }, - test: { - executor: '@nx/jest:jest', - outputs: [`coverage/packages/${uniqLibName}`], - options: { - jestConfig: `packages/${uniqLibName}/jest.config.js`, - passWithNoTests: true, - }, - }, - lint: { - executor: '@nx/eslint:eslint', - options: { - lintFilePatterns: [ - `packages/${uniqLibName}/src/**/*.ts`, - `packages/${uniqLibName}/src/**/*.html`, - ], - }, - }, - }, - tags: [], - }; -}; - -export const getApplication = (appName: string): ProjectConfiguration => { - const uniqAppName = `angular-app-${appName}`; - - return { - projectType: 'application', - root: `apps/${uniqAppName}`, - sourceRoot: `apps/${uniqAppName}/src`, - // prefix: 'proj', - targets: { - build: { - executor: '@angular-devkit/build-angular:browser', - outputs: ['{options.outputPath}'], - options: { - outputPath: `dist/apps/${uniqAppName}`, - index: `apps/${uniqAppName}/src/index.html`, - main: `apps/${uniqAppName}/src/main.ts`, - polyfills: `apps/${uniqAppName}/src/polyfills.ts`, - tsConfig: `apps/${uniqAppName}/tsconfig.app.json`, - assets: [ - `apps/${uniqAppName}/src/favicon.ico`, - `apps/${uniqAppName}/src/assets`, - ], - styles: `apps/${uniqAppName}/src/styles.css`, - scripts: [], - }, - configurations: { - production: { - budgets: [ - { - type: 'initial', - maximumWarning: '500kb', - maximumError: '1mb', - }, - { - type: 'anyComponentStyle', - maximumWarning: '2kb', - maximumError: '4kb', - }, - ], - fileReplacements: [ - { - replace: `apps/${uniqAppName}/src/environments/environment.ts`, - with: `apps/${uniqAppName}/src/environments/environment.prod.ts`, - }, - ], - outputHashing: 'all', - }, - development: { - buildOptimizer: false, - optimization: false, - vendorChunk: true, - extractLicenses: false, - sourceMap: true, - namedChunks: true, - }, - }, - defaultConfiguration: 'production', - }, - serve: { - executor: '@angular-devkit/build-angular:dev-server', - configurations: { - production: { - browserTarget: `${uniqAppName}:build:production`, - }, - development: { - browserTarget: `${uniqAppName}:build:development`, - }, - }, - defaultConfiguration: 'development', - }, - 'extract-i18n': { - executor: '@angular-devkit/build-angular:extract-i18n', - options: { - browserTarget: `${uniqAppName}:build`, - }, - }, - lint: { - executor: '@nx/eslint:eslint', - options: { - lintFilePatterns: [ - `apps/${uniqAppName}/src/**/*.ts`, - `apps/${uniqAppName}/src/**/*.html`, - ], - }, - }, - test: { - executor: '@nx/jest:jest', - outputs: [`coverage/apps/${uniqAppName}`], - options: { - jestConfig: `apps/${uniqAppName}/jest.config.js`, - passWithNoTests: true, - }, - }, - }, - tags: [], - }; -}; - -export const getNonPublishableLib = (libName: string): ProjectConfiguration => { - const uniqAppName = `angular-non-buildable-${libName}`; - return { - projectType: 'library', - root: `packages/${uniqAppName}`, - sourceRoot: `packages/${uniqAppName}/src`, - // prefix: 'proj', - targets: { - test: { - executor: '@nx/jest:jest', - outputs: [`coverage/packages/${uniqAppName}`], - options: { - jestConfig: `packages/${uniqAppName}/jest.config.js`, - passWithNoTests: true, - }, - }, - lint: { - executor: '@nx/eslint:eslint', - options: { - lintFilePatterns: [ - `packages/${uniqAppName}/src/**/*.ts`, - `packages/${uniqAppName}/src/**/*.html`, - ], - }, - }, - }, - tags: [], - }; -}; - -export const getLibWithNoSpecification = ( - libName: string -): ProjectConfiguration => { - const uniqLibName = `nx-plugin-${libName}`; - - return { - root: `packages/${uniqLibName}`, - sourceRoot: `packages/${uniqLibName}/src`, - targets: { - build: { - executor: '@nx/js:tsc', - outputs: ['{options.outputPath}'], - options: { - outputPath: `dist/packages/${uniqLibName}`, - main: `packages/${uniqLibName}/src/index.ts`, - tsConfig: `packages/${uniqLibName}/tsconfig.lib.json`, - assets: [ - 'packages/${uniqLibName}/*.md', - { - input: `./packages/${uniqLibName}/src`, - glob: '**/!(*.ts)', - output: './src', - }, - { - input: `./packages/${uniqLibName}/src`, - glob: '**/*.d.ts', - output: './src', - }, - { - input: `./packages/${uniqLibName}`, - glob: 'generators.json', - output: '.', - }, - { - input: `./packages/${uniqLibName}`, - glob: 'executors.json', - output: '.', - }, - ], - }, - }, - lint: { - executor: '@nx/eslint:eslint', - outputs: ['{options.outputFile}'], - options: { - lintFilePatterns: [`packages/${uniqLibName}/**/*.ts`], - }, - }, - test: { - executor: '@nx/jest:jest', - outputs: [`coverage/packages/${uniqLibName}`], - options: { - jestConfig: `packages/${uniqLibName}/jest.config.js`, - passWithNoTests: true, - }, - }, - }, - tags: [], - }; -}; - -export const mockProjectRoot = path.join('some', 'fake', 'root', 'folder'); diff --git a/packages/ngx-deploy-npm/src/__mocks__/mocks.ts b/packages/ngx-deploy-npm/src/__mocks__/mocks.ts new file mode 100644 index 00000000..ce0de2ff --- /dev/null +++ b/packages/ngx-deploy-npm/src/__mocks__/mocks.ts @@ -0,0 +1,116 @@ +import { ProjectConfiguration } from '@nx/devkit'; + +export const getLib = (libName: string): ProjectConfiguration => { + return { + root: `libs/${libName}`, + name: libName, + sourceRoot: `libs/${libName}/src`, + projectType: 'library', + tags: [], + targets: { + build: { + executor: '@mocks/compiler:rollup', + outputs: ['{options.outputPath}'], + options: { + outputPath: `dist/libs/${libName}`, + }, + }, + ...mockLintTarget, + ...mockTestTarget, + }, + }; +}; + +export const getTargetlessLib = (libName: string): ProjectConfiguration => { + return { + root: `libs/${libName}`, + name: libName, + sourceRoot: `libs/${libName}/src`, + projectType: 'library', + tags: [], + }; +}; + +// ? should we remove this since we are no longer building the library? +export const getLibWithoutBuildTarget = ( + libName: string +): ProjectConfiguration => { + return { + root: `libs/${libName}`, + name: libName, + sourceRoot: `libs/${libName}/src`, + projectType: 'library', + tags: [], + targets: { + ...mockLintTarget, + ...mockTestTarget, + }, + }; +}; + +export const getApplication = (appName: string): ProjectConfiguration => { + return { + projectType: 'application', + root: `apps/${appName}`, + name: appName, + sourceRoot: `apps/${appName}/src`, + targets: { + build: { + executor: '@mocks/build:browser', + outputs: ['{options.outputPath}'], + options: { + outputPath: `dist/apps/${appName}`, + index: `apps/${appName}/src/index.html`, + main: `apps/${appName}/src/main.ts`, + tsConfig: `apps/${appName}/tsconfig.app.json`, + scripts: [], + }, + configurations: { + production: { + foo: 'bar', + randomOptions: true, + production: true, + }, + development: { + foo: 'bar', + randomOptions: false, + production: false, + sourceMap: true, + }, + }, + defaultConfiguration: 'production', + }, + serve: { + executor: '@mocks/build:dev-server', + configurations: { + production: { + browserTarget: `${appName}:build:production`, + }, + development: { + browserTarget: `${appName}:build:development`, + }, + }, + defaultConfiguration: 'development', + }, + ...mockLintTarget, + ...mockTestTarget, + }, + tags: [], + }; +}; + +export const mockProjectRoot = 'some/fake/root/folder'; +export const mockProjectDist = (projectName = 'project') => + `dist/lib/${projectName}`; + +const mockLintTarget = { + lint: { + executor: '@mocks/linter:eslint', + }, +}; + +const mockTestTarget = { + test: { + executor: '@mocks/test:simple-test', + }, +}; diff --git a/packages/ngx-deploy-npm/src/executors/deploy/actions.spec.ts b/packages/ngx-deploy-npm/src/executors/deploy/actions.spec.ts index 72641b06..679f2abc 100644 --- a/packages/ngx-deploy-npm/src/executors/deploy/actions.spec.ts +++ b/packages/ngx-deploy-npm/src/executors/deploy/actions.spec.ts @@ -1,149 +1,45 @@ import * as nxDevKit from '@nx/devkit'; +import * as path from 'path'; -import deploy, { - CouldNotBuildTheLibraryError, - NotAbleToGetDistFolderPathError, -} from './actions'; -import type { BuildTarget } from './utils'; -import * as utilsModule from './utils'; +import deploy from './actions'; +import { mockProjectRoot } from '../../__mocks__/mocks'; +import { DeployExecutorOptions } from './schema'; -describe('Deploy Angular apps', () => { - let context: nxDevKit.ExecutorContext; - let outputPath: string; - let runExecutorSpy: jest.SpyInstance; +describe('Deploy', () => { + const setup = () => { + const PROJECT = 'RANDOM-PROJECT'; + const mockEngine = { + run: jest.fn().mockImplementation(() => () => Promise.resolve()), + } as unknown as Parameters[0]; - // Set this to false if you want to cause an error when building - let shouldBuilderSuccess: boolean; - - const PROJECT = 'RANDOM-PROJECT'; - const mockEngine = { - run: jest.fn().mockImplementation(() => () => Promise.resolve()), - } as unknown as Parameters[0]; - const getMockBuildTarget = (customConf = 'production'): BuildTarget => ({ - name: `${PROJECT}:build:${customConf}`, - }); - - afterEach(() => { - jest.clearAllMocks(); - }); - - beforeEach(() => { - context = { - root: '/absolute/mock/project-root', + const context: nxDevKit.ExecutorContext = { + root: mockProjectRoot, projectName: PROJECT, target: { - executor: 'ngx-deploy-npm', + executor: 'ngx-deploy-npm:deploy', }, projectGraph: {}, } as nxDevKit.ExecutorContext; - outputPath = `${context.root}/dist/path/to/project/${PROJECT}`; - - shouldBuilderSuccess = true; - }); - - // Spyes - beforeEach(() => { - jest.spyOn(nxDevKit, 'readTargetOptions').mockImplementation(() => ({})); - - jest - .spyOn(utilsModule, 'getLibOutPutPath') - .mockImplementation(() => Promise.resolve(outputPath)); - - runExecutorSpy = jest - .spyOn(nxDevKit, 'runExecutor') - .mockImplementation(() => - Promise.resolve({ - async *[Symbol.asyncIterator]() { - yield { - success: shouldBuilderSuccess, - }; - }, - } as AsyncIterableIterator<{ success: boolean }>) - ); - - jest - .spyOn(nxDevKit, 'parseTargetString') - .mockImplementation(targetString => { - const targetArr = targetString.split(':'); - - return { - project: targetArr[0], - target: targetArr[1], - configuration: targetArr[2], - }; - }); - }); - - it('should invoke the builder', async () => { - await deploy(mockEngine, context, getMockBuildTarget(), {}); - - expect(runExecutorSpy).toHaveBeenCalledWith( - { - configuration: 'production', - target: 'build', - project: PROJECT, - }, - {}, - context - ); - }); - - it('should invoke the builder with the right configuration', async () => { - const customConf = 'my-custom-conf'; - - await deploy(mockEngine, context, getMockBuildTarget(customConf), { - buildTarget: customConf, - }); - - expect(runExecutorSpy).toHaveBeenCalledWith( - { - target: 'build', - project: PROJECT, - configuration: customConf, - }, - expect.anything(), - expect.anything() + return { + PROJECT, + context, + mockEngine, + }; + }; + + it('should invoke the engine', async () => { + const { mockEngine, context } = setup(); + const options: DeployExecutorOptions = { + distFolderPath: 'dist/libs/project', + access: 'public', + }; + + await deploy(mockEngine, context, options); + + expect(mockEngine.run).toHaveBeenCalledWith( + path.join(context.root, options.distFolderPath), + options ); }); - - describe('option --no-build', () => { - it('should not invoke the builder if the option --no-build is passed', async () => { - await deploy(mockEngine, context, getMockBuildTarget(), { - noBuild: true, - }); - - expect(runExecutorSpy).not.toHaveBeenCalled(); - }); - }); - - describe('Error Handling', () => { - it('should throw error if app building fails', async () => { - shouldBuilderSuccess = false; - - await expect(() => - deploy(mockEngine, context, getMockBuildTarget(), {}) - ).rejects.toThrowError(CouldNotBuildTheLibraryError); - }); - - it('should throw if getLibOutPutPath fails', async () => { - jest - .spyOn(utilsModule, 'getLibOutPutPath') - .mockImplementation(async () => { - throw new Error('any error'); - }); - - await expect(() => - deploy(mockEngine, context, getMockBuildTarget(), {}) - ).rejects.toThrowError(NotAbleToGetDistFolderPathError); - }); - - it('should throw if context.projectGraph is undefined', async () => { - delete context.projectGraph; - - await expect(() => - deploy(mockEngine, context, getMockBuildTarget(), {}) - ).rejects.toThrowError('context.projectGraph is undefined'); - }); - }); }); diff --git a/packages/ngx-deploy-npm/src/executors/deploy/actions.ts b/packages/ngx-deploy-npm/src/executors/deploy/actions.ts index 78a2d603..6deba39f 100644 --- a/packages/ngx-deploy-npm/src/executors/deploy/actions.ts +++ b/packages/ngx-deploy-npm/src/executors/deploy/actions.ts @@ -1,96 +1,14 @@ -import { - ExecutorContext, - logger, - parseTargetString, - readTargetOptions, - runExecutor, - Target, -} from '@nx/devkit'; +import { ExecutorContext } from '@nx/devkit'; import { DeployExecutorOptions } from './schema'; -import { BuildTarget, getLibOutPutPath } from './utils'; +import * as path from 'path'; export default async function deploy( engine: { run: (dir: string, options: DeployExecutorOptions) => Promise; }, context: ExecutorContext, - buildTarget: BuildTarget, options: DeployExecutorOptions ) { - // This should be removed on V17. context.projectGraph is going to be required - if (!context.projectGraph) { - throw new Error('context.projectGraph is undefined'); - } - - const targetDescription = parseTargetString( - buildTarget.name, - context.projectGraph - ); - - if (options.noBuild) { - logger.info(`📦 Skipping build`); - } else { - await buildLibrary(context, buildTarget, targetDescription); - } - - const buildOptions = readTargetOptions(targetDescription, context); - - let outputPath: string; - try { - outputPath = await getLibOutPutPath(context.root, buildOptions, options); - } catch (error) { - logger.error(error); - throw new NotAbleToGetDistFolderPathError(); - } - - await engine.run(outputPath, options); -} - -async function buildLibrary( - context: ExecutorContext, - buildTarget: BuildTarget, - targetDescription: Target -) { - if (!context.target) { - throw new Error('Cannot execute the build target'); - } - - logger.info(`📦 Building "${context.projectName}"`); - logger.info(`📦 Build target "${buildTarget.name}"`); - - const buildResult = await runExecutor(targetDescription, {}, context); - - for await (const output of buildResult) { - if (!output.success) { - throw new CouldNotBuildTheLibraryError(); - } - } -} - -export class CouldNotBuildTheLibraryError extends Error { - constructor() { - const errorMsg = 'Could not build the library'; - super(errorMsg); - // Ensure the name of this error is the same as the class name - this.name = this.constructor.name; - - // It does make the stack trace a little nicer. - // @see Node.js reference (bottom) - Error.captureStackTrace(this, this.constructor); - } -} - -export class NotAbleToGetDistFolderPathError extends Error { - constructor() { - const errorMsg = - "There is an error trying to locate the library's dist path"; - super(errorMsg); - // Ensure the name of this error is the same as the class name - this.name = this.constructor.name; - - // It does make the stack trace a little nicer. - // @see Node.js reference (bottom) - Error.captureStackTrace(this, this.constructor); - } + await engine.run(path.join(context.root, options.distFolderPath), options); } diff --git a/packages/ngx-deploy-npm/src/executors/deploy/engine/engine.spec.ts b/packages/ngx-deploy-npm/src/executors/deploy/engine/engine.spec.ts index 20464563..be2257ae 100644 --- a/packages/ngx-deploy-npm/src/executors/deploy/engine/engine.spec.ts +++ b/packages/ngx-deploy-npm/src/executors/deploy/engine/engine.spec.ts @@ -3,9 +3,12 @@ import { npmAccess } from '../../../core'; import * as engine from './engine'; import * as spawn from '../utils/spawn-async'; import * as setPackage from '../utils/set-package-version'; +import { mockProjectDist, mockProjectRoot } from '../../../__mocks__/mocks'; +// TODO Migrate to SIFERS approach describe('engine', () => { let dir: string; + let distFolderPath: string; let options: DeployExecutorOptions; afterEach(() => { @@ -19,15 +22,16 @@ describe('engine', () => { // Data beforeEach(() => { - dir = '/absolute/custom/path'; + dir = mockProjectRoot; + distFolderPath = mockProjectDist(); }); it('should call NPM Publish with the right options', async () => { options = { + distFolderPath, access: npmAccess.restricted, tag: 'next', otp: 'someValue', - buildTarget: 'production', registry: 'http://localhost:4873', dryRun: true, }; @@ -64,7 +68,10 @@ describe('engine', () => { describe('Options Management', () => { it('should set the default options', async () => { - const options: DeployExecutorOptions = {}; + const options: DeployExecutorOptions = { + distFolderPath, + access: npmAccess.public, + }; const optionsArray = ['--access', npmAccess.public]; await engine.run(dir, options); @@ -78,6 +85,7 @@ describe('engine', () => { it('should overwrite the default option access', async () => { const options = { + distFolderPath: 'dist/libs/project', tag: 'random-tag', access: npmAccess.restricted, }; @@ -114,7 +122,9 @@ describe('engine', () => { version = '1.0.1-next0'; options = { + distFolderPath, packageVersion: version, + access: 'public', }; }); diff --git a/packages/ngx-deploy-npm/src/executors/deploy/engine/engine.ts b/packages/ngx-deploy-npm/src/executors/deploy/engine/engine.ts index c6ee88c6..3c4708a6 100644 --- a/packages/ngx-deploy-npm/src/executors/deploy/engine/engine.ts +++ b/packages/ngx-deploy-npm/src/executors/deploy/engine/engine.ts @@ -8,7 +8,10 @@ import { } from '../utils'; import { DeployExecutorOptions } from '../schema'; -export async function run(dir: string, options: DeployExecutorOptions) { +export async function run( + distFolderPath: string, + options: DeployExecutorOptions +) { try { options = prepareOptions(options); @@ -22,14 +25,14 @@ export async function run(dir: string, options: DeployExecutorOptions) { when the option is removed */ if (options.packageVersion && !options.dryRun) { - await setPackageVersion(dir, options.packageVersion); + await setPackageVersion(distFolderPath, options.packageVersion); } const npmOptions = extractOnlyNPMOptions(options); await spawnAsync('npm', [ 'publish', - dir, + distFolderPath, ...getOptionsStringArr(npmOptions), ]); diff --git a/packages/ngx-deploy-npm/src/executors/deploy/executor.ts b/packages/ngx-deploy-npm/src/executors/deploy/executor.ts index cfd73ebd..29ca4e2a 100644 --- a/packages/ngx-deploy-npm/src/executors/deploy/executor.ts +++ b/packages/ngx-deploy-npm/src/executors/deploy/executor.ts @@ -8,13 +8,8 @@ export default async function runExecutor( options: DeployExecutorOptions, context: ExecutorContext ) { - const configuration = options.buildTarget ? `:${options.buildTarget}` : ''; - const buildTarget = { - name: `${context.projectName}:build${configuration}`, - }; - try { - await deploy(engine, context, buildTarget, options); + await deploy(engine, context, options); } catch (e) { logger.error(e); logger.error('Error when trying to publish the library'); diff --git a/packages/ngx-deploy-npm/src/executors/deploy/schema.d.ts b/packages/ngx-deploy-npm/src/executors/deploy/schema.d.ts index e58d19e7..ad39215e 100644 --- a/packages/ngx-deploy-npm/src/executors/deploy/schema.d.ts +++ b/packages/ngx-deploy-npm/src/executors/deploy/schema.d.ts @@ -1,16 +1,8 @@ export interface DeployExecutorOptions { /** - * Indicate the dist folder path. This is useful when ngx-deploy-npm can not detect your library dist folder automatically. The path should be relative to the project's root + * The dist folder path. The path should be relative to the project's root */ - distFolderPath?: string; - /** - * A named build target, as specified in the `configurations`. Each named target is accompanied by a configuration of option defaults for that target. This is equivalent to calling the command `nx build --configuration=XXX`. - */ - buildTarget?: string; - /** - * Skip build process during deployment. - */ - noBuild?: boolean; + distFolderPath: string; /** * The version that your package is going to be published. Ex: '1.3.5' '2.0.0-next.0' */ @@ -22,7 +14,7 @@ export interface DeployExecutorOptions { /** * Tells the registry whether this package should be published as public or restricted. Only applies to scoped packages, which default to restricted. If you don’t have a paid account, you must publish with --access public to publish scoped packages. */ - access?: 'public' | 'restricted'; + access: 'public' | 'restricted'; /** * If you have two-factor authentication enabled in auth-and-writes mode then you can provide a code from your authenticator with this. If you don’t include this and you’re running from a TTY then you’ll be prompted. */ diff --git a/packages/ngx-deploy-npm/src/executors/deploy/schema.json b/packages/ngx-deploy-npm/src/executors/deploy/schema.json index 49638358..5e13f068 100644 --- a/packages/ngx-deploy-npm/src/executors/deploy/schema.json +++ b/packages/ngx-deploy-npm/src/executors/deploy/schema.json @@ -8,16 +8,7 @@ "properties": { "distFolderPath": { "type": "string", - "description": "Indicate the dist folder path. This is useful when ngx-deploy-npm can not detect your library dist folder automatically. The path should be relative to the project's root" - }, - "buildTarget": { - "type": "string", - "description": "A named build target, as specified in the `configurations`. Each named target is accompanied by a configuration of option defaults for that target. This is equivalent to calling the command `nx build --configuration=XXX`" - }, - "noBuild": { - "type": "boolean", - "default": false, - "description": "Skip build process during deployment." + "description": "The dist folder path. The path should be relative to the project's root" }, "packageVersion": { "type": "string", @@ -47,5 +38,5 @@ "default": false } }, - "required": [] + "required": ["distFolderPath"] } diff --git a/packages/ngx-deploy-npm/src/executors/deploy/utils/file-utils.ts b/packages/ngx-deploy-npm/src/executors/deploy/utils/file-utils.ts deleted file mode 100644 index 26667dcc..00000000 --- a/packages/ngx-deploy-npm/src/executors/deploy/utils/file-utils.ts +++ /dev/null @@ -1,6 +0,0 @@ -import { promisify } from 'util'; -import { readFile, writeFile } from 'fs'; - -export const readFileAsync = promisify(readFile); - -export const writeFileAsync = promisify(writeFile); diff --git a/packages/ngx-deploy-npm/src/executors/deploy/utils/get-lib-output-path/index.ts b/packages/ngx-deploy-npm/src/executors/deploy/utils/get-lib-output-path/index.ts deleted file mode 100644 index 0770877c..00000000 --- a/packages/ngx-deploy-npm/src/executors/deploy/utils/get-lib-output-path/index.ts +++ /dev/null @@ -1 +0,0 @@ -export { getLibOutPutPath } from './strategy-selector'; diff --git a/packages/ngx-deploy-npm/src/executors/deploy/utils/get-lib-output-path/shared/index.ts b/packages/ngx-deploy-npm/src/executors/deploy/utils/get-lib-output-path/shared/index.ts deleted file mode 100644 index 3b8e9106..00000000 --- a/packages/ngx-deploy-npm/src/executors/deploy/utils/get-lib-output-path/shared/index.ts +++ /dev/null @@ -1,4 +0,0 @@ -export type IBuildOptions = { - project?: string; - outputPath?: string; -}; diff --git a/packages/ngx-deploy-npm/src/executors/deploy/utils/get-lib-output-path/strategies/dist-folder-path/dist-folder-path-option.spec.ts b/packages/ngx-deploy-npm/src/executors/deploy/utils/get-lib-output-path/strategies/dist-folder-path/dist-folder-path-option.spec.ts deleted file mode 100644 index ef8e8cd8..00000000 --- a/packages/ngx-deploy-npm/src/executors/deploy/utils/get-lib-output-path/strategies/dist-folder-path/dist-folder-path-option.spec.ts +++ /dev/null @@ -1,64 +0,0 @@ -import * as path from 'path'; - -import { UnapplicableStrategyError } from '../shared'; -import { customDistPathStrategy } from './dist-folder-path-option'; -import { mockProjectRoot } from '../../../../../../__mocks__/generators'; - -describe('distFolderPathStrategy', () => { - const projectRoot = mockProjectRoot; - const distFolderPath = path.join('my', 'custom-folder'); - - it('should return the right dist path', () => { - const expectedPath = path.join(projectRoot, distFolderPath); - - const customPath = customDistPathStrategy.executor( - projectRoot, - { - outputPath: 'some/path', - }, - { - distFolderPath, - } - ); - - expect(customPath).toBe(expectedPath); - }); - - it('should throw an error if trying the execute the strategy when it is not applicable', () => { - expect(() => - customDistPathStrategy.executor( - projectRoot, - { - outputPath: 'some/path', - }, - {} - ) - ).toThrowError(UnapplicableStrategyError); - }); - - describe('isStrategyApplicable', () => { - it('should indicate positively if the strategy is applicable', () => { - const isApplicable = customDistPathStrategy.isStrategyApplicable( - { - outputPath: 'some/path', - }, - { - distFolderPath, - } - ); - - expect(isApplicable).toBe(true); - }); - - it('should indicate negatively if the strategy is not applicable', () => { - const isApplicable = customDistPathStrategy.isStrategyApplicable( - { - outputPath: 'some/path', - }, - {} - ); - - expect(isApplicable).toBe(false); - }); - }); -}); diff --git a/packages/ngx-deploy-npm/src/executors/deploy/utils/get-lib-output-path/strategies/dist-folder-path/dist-folder-path-option.ts b/packages/ngx-deploy-npm/src/executors/deploy/utils/get-lib-output-path/strategies/dist-folder-path/dist-folder-path-option.ts deleted file mode 100644 index 4b3a79d7..00000000 --- a/packages/ngx-deploy-npm/src/executors/deploy/utils/get-lib-output-path/strategies/dist-folder-path/dist-folder-path-option.ts +++ /dev/null @@ -1,39 +0,0 @@ -import * as path from 'path'; - -import { DeployExecutorOptions } from '../../../../schema'; -import { IBuildOptions } from '../../shared'; -import { IStrategy, UnapplicableStrategyError } from '../shared'; - -/** - * Use this strategy when we don't have a strategy to locate the dist folder for that library. - * - * Apply it using the option --dist-folder-path - * - * @example - * ```bash - * nx deploy YOUR_LIB --dist-folder-path ./YOUR/CUSTOM/PATH - * ``` - */ -export const customDistPathStrategy: IStrategy = { - name: 'custom dist path', - isStrategyApplicable: ( - _: IBuildOptions, - publishOptions: DeployExecutorOptions - ) => - publishOptions.distFolderPath != undefined && - typeof publishOptions.distFolderPath === 'string', - executor: ( - projectRoot: string, - buildOptions: IBuildOptions, - publishOptions: DeployExecutorOptions - ) => { - if ( - !customDistPathStrategy.isStrategyApplicable(buildOptions, publishOptions) - ) { - throw new UnapplicableStrategyError(customDistPathStrategy.name); - } - - // eslint-disable-next-line @typescript-eslint/no-non-null-assertion - return path.join(projectRoot, publishOptions.distFolderPath!); - }, -}; diff --git a/packages/ngx-deploy-npm/src/executors/deploy/utils/get-lib-output-path/strategies/index.ts b/packages/ngx-deploy-npm/src/executors/deploy/utils/get-lib-output-path/strategies/index.ts deleted file mode 100644 index 680dab3f..00000000 --- a/packages/ngx-deploy-npm/src/executors/deploy/utils/get-lib-output-path/strategies/index.ts +++ /dev/null @@ -1,3 +0,0 @@ -export { customDistPathStrategy } from './dist-folder-path/dist-folder-path-option'; -export { outputPathOptionStrategy } from './output-path-build-option/output-path-build-option'; -export { ngPackageStrategy } from './ng-package/ng-package'; diff --git a/packages/ngx-deploy-npm/src/executors/deploy/utils/get-lib-output-path/strategies/ng-package/ng-package.spec.ts b/packages/ngx-deploy-npm/src/executors/deploy/utils/get-lib-output-path/strategies/ng-package/ng-package.spec.ts deleted file mode 100644 index 5b120591..00000000 --- a/packages/ngx-deploy-npm/src/executors/deploy/utils/get-lib-output-path/strategies/ng-package/ng-package.spec.ts +++ /dev/null @@ -1,107 +0,0 @@ -import * as path from 'path'; - -import { mockProjectRoot } from '../../../../../../__mocks__/generators'; -import * as fileUtils from '../../../../utils/file-utils'; -import { IBuildOptions } from '../../shared'; -import { UnapplicableStrategyError } from '../shared'; -import { - CanNotReadDestOnNGPackageError, - CanNotReadNGPackageError, - ngPackageStrategy, -} from './ng-package'; - -describe('ngPackageStrategy', () => { - const projectRoot = mockProjectRoot; - let buildOptions: IBuildOptions; - let destValue: string; - - beforeEach(() => { - buildOptions = { - project: 'libs/angular-lib/ng-package.json', - }; - - destValue = '../../dist/my-project'; - }); - - beforeEach(() => { - jest - .spyOn(fileUtils, 'readFileAsync') - .mockImplementation(() => - Promise.resolve(`{ "dest": ${JSON.stringify(destValue)} }`) - ); - }); - - afterAll(() => { - jest.clearAllMocks(); - }); - - it('should return the right dist path', async () => { - const expectedPath = path.join(projectRoot, 'dist', 'my-project'); - - const distPath = await ngPackageStrategy.executor( - projectRoot, - buildOptions, - {} - ); - - expect(distPath).toEqual(expectedPath); - }); - - it('should try to read the the ng-package.json file on the right path', async () => { - await ngPackageStrategy.executor(projectRoot, buildOptions, {}); - - expect(fileUtils.readFileAsync).toBeCalledWith( - // eslint-disable-next-line @typescript-eslint/no-non-null-assertion - path.join(projectRoot, buildOptions.project!), - expect.anything() - ); - }); - - it('should throw an error if there is not possible to read the ng-package.json file', async () => { - jest - .spyOn(fileUtils, 'readFileAsync') - .mockImplementation(() => Promise.reject('file not found')); - - await expect(() => - ngPackageStrategy.executor(projectRoot, buildOptions, {}) - ).rejects.toThrowError(CanNotReadNGPackageError); - }); - - it('should throw an error if the `dest` option on `ngPackage.json` is invalid', async () => { - destValue = 123 as unknown as string; - - await expect(() => - ngPackageStrategy.executor(projectRoot, buildOptions, {}) - ).rejects.toThrowError(CanNotReadDestOnNGPackageError); - }); - - it('should throw an error if trying the execute the strategy when it is not applicable', async () => { - await expect(() => - ngPackageStrategy.executor(projectRoot, {}, {}) - ).rejects.toThrowError(UnapplicableStrategyError); - }); - - describe('isStrategyApplicable', () => { - it('should indicate positively if the strategy is applicable', () => { - const project = 'my/custom-folder'; - - const isApplicable = ngPackageStrategy.isStrategyApplicable( - { - project, - }, - {} - ); - - expect(isApplicable).toBe(true); - }); - - it('should indicate negatively if the strategy is not applicable', () => { - const isApplicable = ngPackageStrategy.isStrategyApplicable( - { outputPath: 'something/random' }, - {} - ); - - expect(isApplicable).toBe(false); - }); - }); -}); diff --git a/packages/ngx-deploy-npm/src/executors/deploy/utils/get-lib-output-path/strategies/ng-package/ng-package.ts b/packages/ngx-deploy-npm/src/executors/deploy/utils/get-lib-output-path/strategies/ng-package/ng-package.ts deleted file mode 100644 index 57b7ad68..00000000 --- a/packages/ngx-deploy-npm/src/executors/deploy/utils/get-lib-output-path/strategies/ng-package/ng-package.ts +++ /dev/null @@ -1,93 +0,0 @@ -import { logger } from '@nx/devkit'; -import * as path from 'path'; - -import { DeployExecutorOptions } from '../../../../schema'; -import { readFileAsync } from '../../../file-utils'; -import { IBuildOptions } from '../../shared'; -import { IStrategy, UnapplicableStrategyError } from '../shared'; - -/** - * The strategy applied for Angular Libraries. - * Angular libraries have a file called `ng-package.json`. - * Inside that JSON file, there is a property called `dest`, which will indicate where - * the dist folder path is - * - * @example ```json - * // ng-package.json - * { - * "$schema": "../../node_modules/ng-packagr/ng-package.schema.json", - * "dest": "../../dist/angular-lib", // <---- dist folder path - * "lib": { - * "entryFile": "src/public-api.ts" - * } - * } - * ``` - */ -export const ngPackageStrategy: IStrategy = { - name: 'ngPackage.json file', - isStrategyApplicable: (buildOptions: IBuildOptions) => - buildOptions.project != undefined && - typeof buildOptions.project === 'string', - executor: async ( - projectRoot: string, - buildOptions: IBuildOptions, - publishOptions: DeployExecutorOptions - ) => { - if (!ngPackageStrategy.isStrategyApplicable(buildOptions, publishOptions)) { - throw new UnapplicableStrategyError(ngPackageStrategy.name); - } - - // eslint-disable-next-line @typescript-eslint/no-non-null-assertion - const ngPackagePath = path.join(projectRoot, buildOptions.project!); - - let ngPackageContentStr: string; - try { - ngPackageContentStr = await readFileAsync(ngPackagePath, { - encoding: 'utf8', - }); - } catch (error) { - logger.error(error); - throw new CanNotReadNGPackageError(); - } - - const ngPackageContent = JSON.parse(ngPackageContentStr); - - if (!ngPackageContent.dest || typeof ngPackageContent.dest !== 'string') { - throw new CanNotReadDestOnNGPackageError(); - } - - const outputPath = path.join( - path.dirname(ngPackagePath), - ngPackageContent.dest - ); - - return outputPath; - }, -}; - -export class CanNotReadNGPackageError extends Error { - constructor() { - const errorMsg = 'Error reading the ng-package.json'; - super(errorMsg); - // Ensure the name of this error is the same as the class name - this.name = this.constructor.name; - - // It does make the stack trace a little nicer. - // @see Node.js reference (bottom) - Error.captureStackTrace(this, this.constructor); - } -} - -export class CanNotReadDestOnNGPackageError extends Error { - constructor() { - const errorMsg = - "'dest' option on ng-package.json doesn't exists or it's not a string"; - super(errorMsg); - // Ensure the name of this error is the same as the class name - this.name = this.constructor.name; - - // It does make the stack trace a little nicer. - // @see Node.js reference (bottom) - Error.captureStackTrace(this, this.constructor); - } -} diff --git a/packages/ngx-deploy-npm/src/executors/deploy/utils/get-lib-output-path/strategies/output-path-build-option/output-path-build-option.spec.ts b/packages/ngx-deploy-npm/src/executors/deploy/utils/get-lib-output-path/strategies/output-path-build-option/output-path-build-option.spec.ts deleted file mode 100644 index d6fb22be..00000000 --- a/packages/ngx-deploy-npm/src/executors/deploy/utils/get-lib-output-path/strategies/output-path-build-option/output-path-build-option.spec.ts +++ /dev/null @@ -1,52 +0,0 @@ -import * as path from 'path'; - -import { UnapplicableStrategyError } from '../shared'; -import { outputPathOptionStrategy } from './output-path-build-option'; -import { mockProjectRoot } from '../../../../../../__mocks__/generators'; - -describe('outputPathOptionStrategy', () => { - const projectRoot = mockProjectRoot; - - it('should return the right dist path', () => { - const outputPath = 'my/custom-folder'; - const expectedPath = path.join(projectRoot, outputPath); - - const gottenPath = outputPathOptionStrategy.executor( - projectRoot, - { outputPath }, - {} - ); - - expect(gottenPath).toBe(expectedPath); - }); - - it('should throw an error if trying the execute the strategy when it is not applicable', () => { - expect(() => - outputPathOptionStrategy.executor(projectRoot, {}, {}) - ).toThrowError(UnapplicableStrategyError); - }); - - describe('isStrategyApplicable', () => { - it('should indicate positively if the strategy is applicable', () => { - const outputPath = 'my/custom-folder'; - - const isApplicable = outputPathOptionStrategy.isStrategyApplicable( - { - outputPath, - }, - {} - ); - - expect(isApplicable).toBe(true); - }); - - it('should indicate negatively if the strategy is not applicable', () => { - const isApplicable = outputPathOptionStrategy.isStrategyApplicable( - { project: 'path/to/ng-package.json' }, - {} - ); - - expect(isApplicable).toBe(false); - }); - }); -}); diff --git a/packages/ngx-deploy-npm/src/executors/deploy/utils/get-lib-output-path/strategies/output-path-build-option/output-path-build-option.ts b/packages/ngx-deploy-npm/src/executors/deploy/utils/get-lib-output-path/strategies/output-path-build-option/output-path-build-option.ts deleted file mode 100644 index 71e0e712..00000000 --- a/packages/ngx-deploy-npm/src/executors/deploy/utils/get-lib-output-path/strategies/output-path-build-option/output-path-build-option.ts +++ /dev/null @@ -1,49 +0,0 @@ -import * as path from 'path'; - -import { DeployExecutorOptions } from '../../../../schema'; -import { IBuildOptions } from '../../shared'; -import { IStrategy, UnapplicableStrategyError } from '../shared'; - -/** - * This strategy is the common one across Nx Official Plugins. - * We get the dist path from the option `outputPath` from the `build` target's options. - * - * @example ```json - * // project.json - * { - * "build": { - * "executor": "@nx/js:tsc", - * "outputs": ["{options.outputPath}"], - * "options": { - * "outputPath": "dist/packages/ngx-deploy-npm", // <------- outputPath Option - * "tsConfig": "packages/ngx-deploy-npm/tsconfig.lib.json", - * "packageJson": "packages/ngx-deploy-npm/package.json", - * "main": "packages/ngx-deploy-npm/src/index.ts", - * } - * } - * } - *``` - */ -export const outputPathOptionStrategy: IStrategy = { - name: 'outputPath option', - isStrategyApplicable: (buildOptions: IBuildOptions) => - buildOptions.outputPath != undefined && - typeof buildOptions.outputPath === 'string', - executor: ( - projectRoot: string, - buildOptions: IBuildOptions, - publishOptions: DeployExecutorOptions - ) => { - if ( - !outputPathOptionStrategy.isStrategyApplicable( - buildOptions, - publishOptions - ) - ) { - throw new UnapplicableStrategyError(outputPathOptionStrategy.name); - } - - // eslint-disable-next-line @typescript-eslint/no-non-null-assertion - return path.join(projectRoot, buildOptions.outputPath!); - }, -}; diff --git a/packages/ngx-deploy-npm/src/executors/deploy/utils/get-lib-output-path/strategies/shared/common-errors.ts b/packages/ngx-deploy-npm/src/executors/deploy/utils/get-lib-output-path/strategies/shared/common-errors.ts deleted file mode 100644 index 4aa428a9..00000000 --- a/packages/ngx-deploy-npm/src/executors/deploy/utils/get-lib-output-path/strategies/shared/common-errors.ts +++ /dev/null @@ -1,12 +0,0 @@ -export class UnapplicableStrategyError extends Error { - constructor(strategyName: string) { - const errorMsg = `Trying to apply the strategy '${strategyName}' when it's not possible`; - super(errorMsg); - // Ensure the name of this error is the same as the class name - this.name = this.constructor.name; - - // It does make the stack trace a little nicer. - // @see Node.js reference (bottom) - Error.captureStackTrace(this, this.constructor); - } -} diff --git a/packages/ngx-deploy-npm/src/executors/deploy/utils/get-lib-output-path/strategies/shared/index.ts b/packages/ngx-deploy-npm/src/executors/deploy/utils/get-lib-output-path/strategies/shared/index.ts deleted file mode 100644 index f95e22d8..00000000 --- a/packages/ngx-deploy-npm/src/executors/deploy/utils/get-lib-output-path/strategies/shared/index.ts +++ /dev/null @@ -1,2 +0,0 @@ -export * from './interfaces'; -export * from './common-errors'; diff --git a/packages/ngx-deploy-npm/src/executors/deploy/utils/get-lib-output-path/strategies/shared/interfaces.ts b/packages/ngx-deploy-npm/src/executors/deploy/utils/get-lib-output-path/strategies/shared/interfaces.ts deleted file mode 100644 index c8b0ba1c..00000000 --- a/packages/ngx-deploy-npm/src/executors/deploy/utils/get-lib-output-path/strategies/shared/interfaces.ts +++ /dev/null @@ -1,15 +0,0 @@ -import { DeployExecutorOptions } from '../../../../schema'; -import { IBuildOptions } from '../../shared'; - -export type IStrategy = { - name: string; - isStrategyApplicable: ( - buildOptions: IBuildOptions, - publishOptions: DeployExecutorOptions - ) => boolean; - executor: ( - projectRoot: string, - buildOptions: IBuildOptions, - publishOptions: DeployExecutorOptions - ) => string | Promise; -}; diff --git a/packages/ngx-deploy-npm/src/executors/deploy/utils/get-lib-output-path/strategy-selector.spec.ts b/packages/ngx-deploy-npm/src/executors/deploy/utils/get-lib-output-path/strategy-selector.spec.ts deleted file mode 100644 index 9a499454..00000000 --- a/packages/ngx-deploy-npm/src/executors/deploy/utils/get-lib-output-path/strategy-selector.spec.ts +++ /dev/null @@ -1,91 +0,0 @@ -import * as strategies from './strategies'; -import { - getLibOutPutPath, - NotAbleToDetermineDistPathError, -} from './strategy-selector'; - -describe('strategy selector', () => { - let projectRoot: string; - const pathFoundForStrategy = (strategy: keyof typeof strategies) => - `${projectRoot}/path/to/${strategy}/dist`; - - const setIsStrategyApplicable = ( - isStrategyApplicable: (strategy: keyof typeof strategies) => boolean - ) => - Object.keys(strategies).forEach(async strategy => { - const currentStrategyKey = strategy as keyof typeof strategies; - jest - .spyOn(strategies[currentStrategyKey], 'isStrategyApplicable') - .mockImplementation(() => isStrategyApplicable(currentStrategyKey)); - }); - - beforeEach(() => { - projectRoot = '/mock/absolute/path'; - }); - - beforeEach(() => { - // Set all executors to return a path - Object.keys(strategies).forEach(async strategy => { - const currentStrategyKey = strategy as keyof typeof strategies; - - jest - .spyOn(strategies[currentStrategyKey], 'executor') - .mockImplementation(() => pathFoundForStrategy(currentStrategyKey)); - }); - }); - - afterEach(() => { - jest.clearAllMocks(); - }); - - it('should launch an error if no strategy is applicable', async () => { - // Make return false all the isStrategyApplicable strategies methods - setIsStrategyApplicable(() => false); - - await expect(() => - getLibOutPutPath(projectRoot, {}, {}) - ).rejects.toThrowError(NotAbleToDetermineDistPathError); - }); - - it('should the strategy custom dist path have maximum priority', async () => { - setIsStrategyApplicable(() => true); - - const path = await getLibOutPutPath(projectRoot, {}, {}); - - expect(path).toEqual(pathFoundForStrategy('customDistPathStrategy')); - }); - - it('should the strategy outputPath have priority over ngPackage strategy', async () => { - setIsStrategyApplicable( - strategy => - strategy === 'outputPathOptionStrategy' || - strategy === 'ngPackageStrategy' - ); - - const path = await getLibOutPutPath(projectRoot, {}, {}); - - expect(path).toEqual(pathFoundForStrategy('outputPathOptionStrategy')); - }); - - it('should the strategy ngPackage have the least of the priorities', async () => { - setIsStrategyApplicable(strategy => strategy === 'ngPackageStrategy'); - - const path = await getLibOutPutPath(projectRoot, {}, {}); - - expect(path).toEqual(pathFoundForStrategy('ngPackageStrategy')); - }); - - const testStrategy = (strategy: keyof typeof strategies) => { - it(`should execute ${strategy} strategy`, async () => { - setIsStrategyApplicable(str => str === strategy); - - const path = await getLibOutPutPath(projectRoot, {}, {}); - - expect(path).toEqual(pathFoundForStrategy(strategy)); - }); - }; - - testStrategy('customDistPathStrategy'); - testStrategy('outputPathOptionStrategy'); - testStrategy('ngPackageStrategy'); -}); diff --git a/packages/ngx-deploy-npm/src/executors/deploy/utils/get-lib-output-path/strategy-selector.ts b/packages/ngx-deploy-npm/src/executors/deploy/utils/get-lib-output-path/strategy-selector.ts deleted file mode 100644 index 9664c9fd..00000000 --- a/packages/ngx-deploy-npm/src/executors/deploy/utils/get-lib-output-path/strategy-selector.ts +++ /dev/null @@ -1,63 +0,0 @@ -import { DeployExecutorOptions } from '../../schema'; -import { IBuildOptions } from './shared'; -import * as strategies from './strategies'; -import { IStrategy } from './strategies/shared'; - -export async function getLibOutPutPath( - projectRoot: string, - buildOptions: IBuildOptions, - publishOptions: DeployExecutorOptions -): Promise { - const strategyChosen = chooseStrategy(buildOptions, publishOptions); - - return strategyChosen(projectRoot, buildOptions, publishOptions); -} - -function chooseStrategy( - buildOptions: IBuildOptions, - publishOptions: DeployExecutorOptions -): IStrategy['executor'] { - if ( - strategies.customDistPathStrategy.isStrategyApplicable( - buildOptions, - publishOptions - ) - ) { - return strategies.customDistPathStrategy.executor; - } - - if ( - strategies.outputPathOptionStrategy.isStrategyApplicable( - buildOptions, - publishOptions - ) - ) { - return strategies.outputPathOptionStrategy.executor; - } - - if ( - strategies.ngPackageStrategy.isStrategyApplicable( - buildOptions, - publishOptions - ) - ) { - return strategies.ngPackageStrategy.executor; - } - - throw new NotAbleToDetermineDistPathError(); -} - -export class NotAbleToDetermineDistPathError extends Error { - constructor() { - const errorMsg = `ngx-deploy-npm was not able to detect the dist path.\n -Use the option --dist-folder-path to indicate where is the dist folder of your library\n -Write us an issue to add support to your library -> https://github.com/bikecoders/ngx-deploy-npm/issues/new`; - super(errorMsg); - // Ensure the name of this error is the same as the class name - this.name = this.constructor.name; - - // It does make the stack trace a little nicer. - // @see Node.js reference (bottom) - Error.captureStackTrace(this, this.constructor); - } -} diff --git a/packages/ngx-deploy-npm/src/executors/deploy/utils/index.ts b/packages/ngx-deploy-npm/src/executors/deploy/utils/index.ts index 6a44ea7a..87b4b082 100644 --- a/packages/ngx-deploy-npm/src/executors/deploy/utils/index.ts +++ b/packages/ngx-deploy-npm/src/executors/deploy/utils/index.ts @@ -1,6 +1,4 @@ export * from './default-options'; -export * from './file-utils'; -export * from './get-lib-output-path'; export * from './interfaces'; export * from './set-default-options'; export * from './set-package-version'; diff --git a/packages/ngx-deploy-npm/src/executors/deploy/utils/interfaces.ts b/packages/ngx-deploy-npm/src/executors/deploy/utils/interfaces.ts index 573d1d29..edfb529e 100644 --- a/packages/ngx-deploy-npm/src/executors/deploy/utils/interfaces.ts +++ b/packages/ngx-deploy-npm/src/executors/deploy/utils/interfaces.ts @@ -4,8 +4,3 @@ export type NpmPublishOptions = Pick< DeployExecutorOptions, 'access' | 'tag' | 'otp' | 'dryRun' | 'registry' >; - -export interface BuildTarget { - name: string; - options?: Record; -} diff --git a/packages/ngx-deploy-npm/src/executors/deploy/utils/set-package-version.spec.ts b/packages/ngx-deploy-npm/src/executors/deploy/utils/set-package-version.spec.ts index 271533f1..2f86b600 100644 --- a/packages/ngx-deploy-npm/src/executors/deploy/utils/set-package-version.spec.ts +++ b/packages/ngx-deploy-npm/src/executors/deploy/utils/set-package-version.spec.ts @@ -1,21 +1,28 @@ -import * as fs from '../utils/file-utils'; +import * as fileUtils from '../../../utils'; import { setPackageVersion } from './set-package-version'; +jest.mock('../../../utils', () => { + return { + __esModule: true, // <----- this __esModule: true is important + ...jest.requireActual('../../../utils'), + }; +}); + describe('setPackageVersion', () => { let myPackageJSON: Record; let expectedPackage: Record; let version: string; let dir: string; - let valueWriten: Parameters[1]; + let valueWriten: Parameters[1]; // Spies beforeEach(() => { jest - .spyOn(fs, 'readFileAsync') + .spyOn(fileUtils, 'readFileAsync') .mockImplementation(() => Promise.resolve(JSON.stringify(myPackageJSON))); - jest.spyOn(fs, 'writeFileAsync').mockImplementation((_, data) => { + jest.spyOn(fileUtils, 'writeFileAsync').mockImplementation((_, data) => { valueWriten = data; return Promise.resolve(); }); diff --git a/packages/ngx-deploy-npm/src/executors/deploy/utils/set-package-version.ts b/packages/ngx-deploy-npm/src/executors/deploy/utils/set-package-version.ts index 03977fb8..75dabe14 100644 --- a/packages/ngx-deploy-npm/src/executors/deploy/utils/set-package-version.ts +++ b/packages/ngx-deploy-npm/src/executors/deploy/utils/set-package-version.ts @@ -1,8 +1,8 @@ -import * as fs from './file-utils'; +import * as fileUtils from '../../../utils'; import * as path from 'path'; export async function setPackageVersion(dir: string, packageVersion: string) { - const packageContent: string = await fs.readFileAsync( + const packageContent: string = await fileUtils.readFileAsync( path.join(dir, 'package.json'), { encoding: 'utf8' } ); @@ -11,7 +11,7 @@ export async function setPackageVersion(dir: string, packageVersion: string) { packageObj.version = packageVersion; - await fs.writeFileAsync( + await fileUtils.writeFileAsync( path.join(dir, 'package.json'), JSON.stringify(packageObj, null, 4), { encoding: 'utf8' } diff --git a/packages/ngx-deploy-npm/src/generators/install/generator.spec.ts b/packages/ngx-deploy-npm/src/generators/install/generator.spec.ts index 97aad3bf..5ac33439 100644 --- a/packages/ngx-deploy-npm/src/generators/install/generator.spec.ts +++ b/packages/ngx-deploy-npm/src/generators/install/generator.spec.ts @@ -1,6 +1,5 @@ import { createTreeWithEmptyWorkspace } from '@nx/devkit/testing'; import { - Tree, addProjectConfiguration, ProjectConfiguration, getProjects, @@ -11,245 +10,273 @@ import generator from './generator'; import { InstallGeneratorOptions } from './schema'; import { DeployExecutorOptions } from '../../executors/deploy/schema'; import { npmAccess } from '../../core'; -import { buildInvalidProjectsErrorMessage } from './utils'; -import { - getApplication, - getLibPublishable, - getLibPublishableWithProdMode, - getNonPublishableLib, - getLibWithNoSpecification, -} from '../../__mocks__/generators'; +import * as mocks from '../../__mocks__/mocks'; +import * as utils from '../../utils'; -describe('install generator', () => { - let appTree: Tree; - let rawOptions: InstallGeneratorOptions; +jest.mock('../../utils', () => { + return { + __esModule: true, // <----- this __esModule: true is important + ...jest.requireActual('../../utils'), + }; +}); - type publishableLibConfig = { - key: string; - projectConfig: ProjectConfiguration; +describe('install generator', () => { + enum PUBLISHABLE_LIBS { + lib1 = 'lib1', + lib2 = 'lib2', + withoutBuildLib = 'withoutBuildLib', + } + enum NON_PUBLISHABLE_LIBS { + app = 'app', + nonPublishable = 'nonPublishable', + nonPublishable2 = 'nonPublishable2', + } + + const allKindsOfProjects: Record< + PUBLISHABLE_LIBS | NON_PUBLISHABLE_LIBS, + ProjectConfiguration + > = { + lib1: mocks.getLib('lib1'), + lib2: mocks.getLib('lib2'), + withoutBuildLib: mocks.getLibWithoutBuildTarget('withoutBuildLib'), + app: mocks.getApplication('app'), + nonPublishable: mocks.getLibWithoutBuildTarget('nonPublishable'), + nonPublishable2: mocks.getLibWithoutBuildTarget('nonPublishable2'), }; - let workspaceConfig: Map; - let libPublisable: publishableLibConfig; - let libPublisable2: publishableLibConfig; - let libPublisableWithProdMode: publishableLibConfig; - let expectedSimpleTarget: TargetConfiguration; - let expectedTargetWithProductionMode: TargetConfiguration; + const setup = ({ + workspaceProjects = allKindsOfProjects, + workspacePublishableLibs = Object.keys(PUBLISHABLE_LIBS) + .filter(v => isNaN(Number(v))) + .reduce((acc, key) => { + acc[key] = true; + + return acc; + }, {} as Record), + }: { + workspaceProjects?: Record; + workspacePublishableLibs?: Record; + }) => { + const workspaceConfig = new Map(); + const appTree = createTreeWithEmptyWorkspace(); + + Object.entries(workspaceProjects).forEach(([key, project]) => { + workspaceConfig.set(key, project); + }); + + jest + .spyOn(utils, 'isProjectAPublishableLib') + .mockImplementation(project => { + const isAPublishableLib = project.name + ? !!workspacePublishableLibs[project.name] + : false; - const createWorkspace = () => + return Promise.resolve(isAPublishableLib); + }); + + // Create workspace Array.from(workspaceConfig.entries()).forEach(([key, projectConfig]) => addProjectConfiguration(appTree, key, projectConfig) ); - beforeEach(() => { - rawOptions = {}; - - appTree = createTreeWithEmptyWorkspace(); - }); - - beforeEach(() => { - workspaceConfig = new Map(); - - libPublisable = { - key: 'libPublishable1', - projectConfig: getLibPublishable('libPublishable1'), - }; + return { appTree }; + }; - libPublisable2 = { - key: 'libPublishableWithNoSpecification', - projectConfig: getLibWithNoSpecification( - 'libPublishableWithNoSpecification' - ), - }; + const buildMockDistPath = (projectName: string) => { + return `dist/libs/${projectName}`; + }; - libPublisableWithProdMode = { - key: 'libPublisableWithProd', - projectConfig: getLibPublishableWithProdMode('libPublisableWithProd'), + const buildExpectedDeployTarget = ( + projectName: string, + isBuildable = true + ): TargetConfiguration => { + const options: TargetConfiguration = { + executor: 'ngx-deploy-npm:deploy', + options: { + access: npmAccess.public, + distFolderPath: buildMockDistPath(projectName), + }, }; - workspaceConfig.set(libPublisable.key, libPublisable.projectConfig); - workspaceConfig.set(libPublisable2.key, libPublisable2.projectConfig); - workspaceConfig.set( - libPublisableWithProdMode.key, - libPublisableWithProdMode.projectConfig - ); - }); + if (isBuildable) { + options.dependsOn = ['build']; + } - describe('generating files', () => { - beforeEach(() => { - expectedSimpleTarget = { - executor: 'ngx-deploy-npm:deploy', - options: { - access: npmAccess.public, - } as DeployExecutorOptions, - }; + return options; + }; - expectedTargetWithProductionMode = { - executor: 'ngx-deploy-npm:deploy', - options: { - buildTarget: 'production', - access: npmAccess.public, - } as DeployExecutorOptions, - }; + afterEach(jest.restoreAllMocks); + it('should create the target with the right structure for a buildable lib', async () => { + const projectName = 'buildableLib'; + const { appTree } = setup({ + workspaceProjects: { + [projectName]: mocks.getLib(projectName), + }, + workspacePublishableLibs: { + [projectName]: true, + }, + }); - workspaceConfig.set('project', getApplication('project')); - workspaceConfig.set( - 'non-publishable', - getNonPublishableLib('non-publishable') - ); - workspaceConfig.set( - 'non-publishable2', - getNonPublishableLib('non-publishable2') - ); + await generator(appTree, { + project: projectName, + distFolderPath: buildMockDistPath(projectName), + access: npmAccess.public, }); - // create workspace - beforeEach(createWorkspace); + const allProjects = getProjects(appTree); + const config = allProjects.get(projectName); + const targetDeploy = config?.targets?.deploy; - describe('default Options', () => { - // install - beforeEach(async () => { - await generator(appTree, rawOptions); - }); + expect(targetDeploy).toStrictEqual( + buildExpectedDeployTarget(projectName, true) + ); + }); - it('should set the deployer only on publishable libraries', async () => { - const allProjects = getProjects(appTree); + it('should create the target with the right structure for a non-buildable lib', async () => { + const projectName = 'nonBuildableLib'; + const { appTree } = setup({ + workspaceProjects: { + [projectName]: mocks.getLibWithoutBuildTarget(projectName), + }, + workspacePublishableLibs: { + [projectName]: true, + }, + }); - const projectsAffected = Array.from(allProjects.entries()) - .filter(([, config]) => !!config.targets?.deploy) - .map(([key]) => key); + await generator(appTree, { + project: projectName, + distFolderPath: buildMockDistPath(projectName), + access: npmAccess.public, + }); - expect(projectsAffected.sort()).toEqual( - [ - libPublisable.key, - libPublisable2.key, - libPublisableWithProdMode.key, - ].sort() - ); - }); + const allProjects = getProjects(appTree); + const config = allProjects.get(projectName); + const targetDeploy = config?.targets?.deploy; - it('should create the target with the right structure for simple libs', () => { - const allProjects = getProjects(appTree); - const config = allProjects.get(libPublisable.key); + expect(targetDeploy).toStrictEqual( + buildExpectedDeployTarget(projectName, false) + ); + }); - const targetDeploy = config?.targets?.deploy; + it('should add the target only to the specified project', async () => { + const { appTree } = setup({}); - expect(targetDeploy).toEqual(expectedSimpleTarget); - }); + await generator(appTree, { + project: PUBLISHABLE_LIBS.lib1, + distFolderPath: buildMockDistPath(PUBLISHABLE_LIBS.lib1), + access: npmAccess.public, + }); - it('should create the target with the right configuration for libs with prod configuration', () => { - const allProjects = getProjects(appTree); - const config = allProjects.get(libPublisableWithProdMode.key); + const allProjects = getProjects(appTree); + const config = allProjects.get(PUBLISHABLE_LIBS.lib2); + const targetDeploy = config?.targets?.deploy; - const targetDeploy = config?.targets?.deploy; + expect(targetDeploy).toStrictEqual(undefined); + }); - expect(targetDeploy).toEqual(expectedTargetWithProductionMode); - }); + it('should create the target with the right structure for a lib without targets', async () => { + const projectName = 'targetLess'; + const { appTree } = setup({ + workspaceProjects: { + [projectName]: mocks.getTargetlessLib(projectName), + }, + workspacePublishableLibs: { [projectName]: true }, + }); - it('should set the `access` option as `public` by default', async () => { - const allProjects = getProjects(appTree); - const project = allProjects.get(libPublisable.key); + await generator(appTree, { + project: projectName, + distFolderPath: buildMockDistPath(projectName), + access: npmAccess.public, + }); - const setOptions: InstallGeneratorOptions = - project?.targets?.deploy.options; + const allProjects = getProjects(appTree); + const project = allProjects.get(projectName); + const setOptions: InstallGeneratorOptions = + project?.targets?.deploy.options; - expect(setOptions.access).toEqual(npmAccess.public); - }); - }); + expect(setOptions.access).toEqual(npmAccess.public); + }); - describe('--projects', () => { - it('should add config only to specified projects', async () => { - rawOptions = { - projects: [libPublisable.key, libPublisable2.key], - }; - // install - await generator(appTree, rawOptions); - const allProjects = getProjects(appTree); - - const projectsAffected = Array.from(allProjects.entries()) - .filter(([, config]) => !!config.targets?.deploy) - .map(([key]) => key); - - expect(projectsAffected.sort()).toEqual( - [libPublisable.key, libPublisable2.key].sort() - ); - }); + describe('--access', () => { + const setupAccess = (access: npmAccess) => { + const projectName = 'lib1'; + const rawOptions: InstallGeneratorOptions = { + project: projectName, + distFolderPath: buildMockDistPath(projectName), + access, + }; - it('should add config to all projects if --projects option is empty', async () => { - rawOptions = { - projects: [], - }; - // install - await generator(appTree, rawOptions); - const allProjects = getProjects(appTree); - - const projectsAffected = Array.from(allProjects.entries()) - .filter(([, config]) => !!config.targets?.deploy) - .map(([key]) => key); - - expect(projectsAffected.sort()).toEqual( - [ - libPublisable.key, - libPublisable2.key, - libPublisableWithProdMode.key, - ].sort() - ); + const { appTree } = setup({ + workspaceProjects: { + [projectName]: mocks.getLib(projectName), + }, + workspacePublishableLibs: { [projectName]: true }, }); - }); - describe('--access', () => { - it('should set the `access` option as `public` when is set to `public` on rawoption', async () => { - rawOptions = { - projects: [libPublisable.key], - access: npmAccess.public, - }; - // install - await generator(appTree, rawOptions); + return { appTree, rawOptions, projectName }; + }; - const allProjects = getProjects(appTree); - const project = allProjects.get(libPublisable.key); + it('should set the `access` option as `public` when is set to `public` on rawoption', async () => { + const { appTree, rawOptions, projectName } = setupAccess( + npmAccess.public + ); - const setOptions: InstallGeneratorOptions = - project?.targets?.deploy.options; + // install + await generator(appTree, rawOptions); - expect(setOptions.access).toEqual(npmAccess.public); - }); + const allProjects = getProjects(appTree); + const project = allProjects.get(projectName); + const targetOptions: InstallGeneratorOptions = + project?.targets?.deploy.options; - it('should set the `access` option as `public` when is set to `restricted` on rawoption', async () => { - rawOptions = { - projects: [libPublisable.key], - access: npmAccess.restricted, - }; - // install - await generator(appTree, rawOptions); + expect(targetOptions.access).toEqual(npmAccess.public); + }); - const allProjects = getProjects(appTree); - const project = allProjects.get(libPublisable.key); + it('should set the `access` option as `restricted` when is set to `restricted` on rawoption', async () => { + const { appTree, rawOptions, projectName } = setupAccess( + npmAccess.restricted + ); - const setOptions: InstallGeneratorOptions = - project?.targets?.deploy.options; + // install + await generator(appTree, rawOptions); - expect(setOptions.access).toEqual(npmAccess.restricted); - }); + const allProjects = getProjects(appTree); + const project = allProjects.get(projectName); + const targetOptions: InstallGeneratorOptions = + project?.targets?.deploy.options; + + expect(targetOptions.access).toEqual(npmAccess.restricted); }); }); describe('error handling', () => { - it('should throw an error if there is no publishable library', () => { - expect(generator(appTree, rawOptions)).rejects.toEqual( - new Error('There is no publishable libraries in this workspace') + it('should throw an error if the project is not a publishable library', async () => { + const project = NON_PUBLISHABLE_LIBS.app; + const rawOptions: InstallGeneratorOptions = { + project, + distFolderPath: buildMockDistPath(project), + access: npmAccess.public, + }; + const { appTree } = setup({}); + + await expect(generator(appTree, rawOptions)).rejects.toThrow( + new Error(`The project ${project} is not a publishable library`) ); }); - it('should throw an error if invalid projects are pass on --projects', () => { - const invalidProjects = ['i', 'dont', 'exists']; - rawOptions = { - projects: [libPublisable.key, ...invalidProjects], + it('should throw an error if invalid project is pass on --project', async () => { + const invalidProjects = 'i-dont-exists'; + const rawOptions: InstallGeneratorOptions = { + project: invalidProjects, + distFolderPath: buildMockDistPath(invalidProjects), + access: npmAccess.public, }; - createWorkspace(); + const { appTree } = setup({}); - expect(generator(appTree, rawOptions)).rejects.toEqual( - new Error(buildInvalidProjectsErrorMessage(invalidProjects)) + await expect(generator(appTree, rawOptions)).rejects.toThrow( + new Error( + `The project ${invalidProjects} doesn't exist on your workspace` + ) ); }); }); diff --git a/packages/ngx-deploy-npm/src/generators/install/generator.ts b/packages/ngx-deploy-npm/src/generators/install/generator.ts index e4b6aa72..e395d6ba 100644 --- a/packages/ngx-deploy-npm/src/generators/install/generator.ts +++ b/packages/ngx-deploy-npm/src/generators/install/generator.ts @@ -2,102 +2,50 @@ import { getProjects, formatFiles, updateProjectConfiguration, - ProjectConfiguration, } from '@nx/devkit'; import type { Tree } from '@nx/devkit'; import type { InstallGeneratorOptions } from './schema'; import { DeployExecutorOptions } from '../../executors/deploy/schema'; -import { - allProjectsAreValid, - buildInvalidProjectsErrorMessage, - determineWhichProjectsAreInvalid, - isProjectAPublishableLib, - normalizeOptions, -} from './utils'; +import { isProjectAPublishableLib } from '../../utils'; export default async function install( tree: Tree, rawOptions: InstallGeneratorOptions ) { - let libs = getBuildableLibraries(tree); - const options = normalizeOptions(rawOptions); - - // If there is no libraries to install throw an exception - if (libs.size === 0) { - throw new Error('There is no publishable libraries in this workspace'); - } + const options = rawOptions; - if (options.projects && options.projects.length > 0) { - // if there is projects that doesn't exists, throw an error indicating which projects are invalid - if (!allProjectsAreValid(options.projects, libs)) { - const invalidProjects = determineWhichProjectsAreInvalid( - options.projects, - libs - ); + const selectedLib = getProjects(tree).get(options.project); - throw new Error(buildInvalidProjectsErrorMessage(invalidProjects)); - } + if (selectedLib === undefined) { + throw new Error( + `The project ${options.project} doesn't exist on your workspace` + ); + } - const selectedLibs = new Map(); - options.projects.forEach(project => { - const lib = libs.get(project); + if ((await isProjectAPublishableLib(selectedLib)) === false) { + throw new Error( + `The project ${options.project} is not a publishable library` + ); + } - if (lib) { - selectedLibs.set(project, lib); - } - }); + const executorOptions: DeployExecutorOptions = { + distFolderPath: options.distFolderPath, + access: options.access, + }; - libs = selectedLibs; + // Create targets in case that they doesn't already exists + if (!selectedLib.targets) { + selectedLib.targets = {}; } - Array.from(libs.entries()).forEach(([libKey, libConfig]) => { - if (libConfig.targets) { - const executorOptions: DeployExecutorOptions = { - access: options.access, - ...setUpProductionModeIfHasIt(libConfig), - }; - - libConfig.targets.deploy = { - executor: 'ngx-deploy-npm:deploy', - options: executorOptions, - }; + selectedLib.targets.deploy = { + executor: 'ngx-deploy-npm:deploy', + options: executorOptions, + ...(selectedLib.targets.build ? { dependsOn: ['build'] } : {}), + }; - updateProjectConfiguration(tree, libKey, libConfig); - } - }); + updateProjectConfiguration(tree, options.project, selectedLib); - /* Supports Angular CLI workspace definition format, see https://github.com/nrwl/nx/discussions/6955#discussioncomment-1341893 */ await formatFiles(tree); } - -/** - * Get the libraries present in the workspace - * @param workspace - */ -function getBuildableLibraries(tree: Tree): ReturnType { - const allProjects = getProjects(tree); - - // remove all the non libiraries - Array.from(allProjects.entries()).forEach(([key, project]) => { - if (isProjectAPublishableLib(project) === false) { - allProjects.delete(key); - } - }); - - return allProjects; -} - -/** - * Returns the configuration production if the library has a production mode on its build - * @param lib The workspace of the library - */ -function setUpProductionModeIfHasIt( - lib: ProjectConfiguration -): Pick { - return lib.targets?.build?.configurations?.production - ? { - buildTarget: 'production', - } - : {}; -} diff --git a/packages/ngx-deploy-npm/src/generators/install/schema.d.ts b/packages/ngx-deploy-npm/src/generators/install/schema.d.ts index b1db1786..ac29222c 100644 --- a/packages/ngx-deploy-npm/src/generators/install/schema.d.ts +++ b/packages/ngx-deploy-npm/src/generators/install/schema.d.ts @@ -1,10 +1,14 @@ export interface InstallGeneratorOptions { + /** + * The dist folder path. The path should be relative to the project's root + */ + distFolderPath: string; /** * Which library should configure */ - projects?: string[]; + project: string; /** * Tells the registry whether this package should be published as public or restricted. Only applies to scoped packages, which default to restricted. If you don’t have a paid account, you must publish with --access public to publish scoped packages. */ - access?: 'public' | 'restricted'; + access: 'public' | 'restricted'; } diff --git a/packages/ngx-deploy-npm/src/generators/install/schema.json b/packages/ngx-deploy-npm/src/generators/install/schema.json index 87351a8c..fdc41595 100644 --- a/packages/ngx-deploy-npm/src/generators/install/schema.json +++ b/packages/ngx-deploy-npm/src/generators/install/schema.json @@ -4,22 +4,22 @@ "title": "", "type": "object", "properties": { - "projects": { - "description": "Which libraries should configure", - "type": "array", - "items": { - "type": "string" - } + "project": { + "description": "Which library should configure. This will add the target deploy to that project. It must be a publishable library.", + "type": "string", + "x-prompt": "Which library should configure?" + }, + "distFolderPath": { + "type": "string", + "description": "The dist folder path. The path should be relative to the project's root", + "x-prompt": "Which is the dist folder path?" }, "access": { "type": "string", "description": "Tells the registry whether this package should be published as public or restricted. Only applies to scoped packages, which default to restricted. If you don't have a npm paid account, you must publish with --access public to publish scoped packages.", - "enum": [ - "public", - "restricted" - ], + "enum": ["public", "restricted"], "default": "public" } }, - "required": [] + "required": ["project", "distFolderPath"] } diff --git a/packages/ngx-deploy-npm/src/generators/install/utils/index.ts b/packages/ngx-deploy-npm/src/generators/install/utils/index.ts deleted file mode 100644 index a0e2fe7a..00000000 --- a/packages/ngx-deploy-npm/src/generators/install/utils/index.ts +++ /dev/null @@ -1,3 +0,0 @@ -export * from './normalize-options'; -export * from './validate-projects'; -export * from './is-a-lib'; diff --git a/packages/ngx-deploy-npm/src/generators/install/utils/is-a-lib.ts b/packages/ngx-deploy-npm/src/generators/install/utils/is-a-lib.ts deleted file mode 100644 index be7fd255..00000000 --- a/packages/ngx-deploy-npm/src/generators/install/utils/is-a-lib.ts +++ /dev/null @@ -1,28 +0,0 @@ -import { ProjectConfiguration } from '@nx/devkit'; - -export const isProjectAPublishableLib = ( - project: ProjectConfiguration -): boolean => { - return ( - isPublishableProjectTypeLibray(project) || - doesntHaveProjectTypeLibButIsPublishableLib(project) - ); -}; - -function isPublishableProjectTypeLibray(project: ProjectConfiguration) { - return project.projectType === 'library' && isBuildable(project); -} - -function doesntHaveProjectTypeLibButIsPublishableLib( - project: ProjectConfiguration -) { - return ( - project.projectType === undefined && - isBuildable(project) && - typeof project?.targets?.build.options.main === 'string' - ); -} - -function isBuildable(project: ProjectConfiguration) { - return typeof project.targets?.build === 'object'; -} diff --git a/packages/ngx-deploy-npm/src/generators/install/utils/normalize-options.ts b/packages/ngx-deploy-npm/src/generators/install/utils/normalize-options.ts deleted file mode 100644 index 15ab6ef1..00000000 --- a/packages/ngx-deploy-npm/src/generators/install/utils/normalize-options.ts +++ /dev/null @@ -1,11 +0,0 @@ -import type { InstallGeneratorOptions } from '../schema'; -import { npmAccess } from '../../../core'; - -export function normalizeOptions( - rawOptions: InstallGeneratorOptions -): InstallGeneratorOptions { - return { - ...rawOptions, - access: rawOptions.access ?? npmAccess.public, - }; -} diff --git a/packages/ngx-deploy-npm/src/generators/install/utils/validate-projects.ts b/packages/ngx-deploy-npm/src/generators/install/utils/validate-projects.ts deleted file mode 100644 index cbd5389b..00000000 --- a/packages/ngx-deploy-npm/src/generators/install/utils/validate-projects.ts +++ /dev/null @@ -1,23 +0,0 @@ -import { getProjects } from '@nx/devkit'; - -export function allProjectsAreValid( - projects: string[], - allLibs: ReturnType -): boolean { - return projects.every(project => !!allLibs.get(project)); -} - -export function determineWhichProjectsAreInvalid( - projects: string[], - allLibs: ReturnType -): string[] { - return projects.filter(project => !allLibs.get(project)); -} - -export function buildInvalidProjectsErrorMessage( - invalidProjects: string[] -): string { - return `There are libraries that doesn't exits on this workspace: ${invalidProjects.join( - ', ' - )}`; -} diff --git a/packages/ngx-deploy-npm/src/migrations/8.0.0/replace-buildtarget-for-depends-on.spec.ts b/packages/ngx-deploy-npm/src/migrations/8.0.0/replace-buildtarget-for-depends-on.spec.ts new file mode 100644 index 00000000..76571fbd --- /dev/null +++ b/packages/ngx-deploy-npm/src/migrations/8.0.0/replace-buildtarget-for-depends-on.spec.ts @@ -0,0 +1,463 @@ +import { createTreeWithEmptyWorkspace } from '@nx/devkit/testing'; +import { + ProjectConfiguration, + TargetConfiguration, + TargetDependencyConfig, + Tree, + addProjectConfiguration, + getProjects, +} from '@nx/devkit'; + +import * as mocks from '../../__mocks__/mocks'; + +import update, { + DeprecatedDeployExecutorOptions, + RemovedDeployExecutorOptions, +} from './replace-buildtarget-for-depends-on'; +import { DeployExecutorOptions } from '../../executors/deploy/schema'; + +describe('replace-configuration-param-for-depends-on migration', () => { + const expectedDeployTarget = ( + name: string, + dependsOn: (TargetDependencyConfig | string)[] = [] + ): TargetConfiguration => { + const target: TargetConfiguration = { + executor: 'ngx-deploy-npm:deploy', + options: { + distFolderPath: `dist/libs/${name}`, + access: 'public', + }, + }; + + if (dependsOn.length > 0) { + target.dependsOn = dependsOn; + } + + return target; + }; + + const setUp = ( + projects: Record< + string, + { + project: ProjectConfiguration; + config: { + build: { + buildConfigs?: string[]; + }; + deploy: Record< + string, + { + preExistedDependsOn?: (TargetDependencyConfig | string)[]; + options?: RemovedDeployExecutorOptions; + } + >; + }; + } + > + ) => { + const addConfig = ( + project: ProjectConfiguration, + config: { + build: { + buildConfigs?: string[]; + }; + deploy: Record< + string, + { + options?: RemovedDeployExecutorOptions; + preExistedDependsOn?: (TargetDependencyConfig | string)[]; + } + >; + } + ) => { + // Add build configs + if (config.build.buildConfigs && project.targets?.build) { + project.targets.build.options = { + ...(project.targets.build.options ?? {}), + configurations: { + ...(project.targets.build.options.configurations ?? {}), + ...config.build.buildConfigs, + }, + }; + } + + // Add deploy configs + Object.entries(config.deploy).forEach( + ([targetKey, { options, preExistedDependsOn }]) => { + const deployTarget: TargetConfiguration = + { + executor: 'ngx-deploy-npm:deploy', + options: { + distFolderPath: `dist/libs/${project.name}`, + access: 'public', + ...options, + }, + }; + + if (preExistedDependsOn) { + deployTarget.dependsOn = preExistedDependsOn; + } + + if (!project.targets) { + project.targets = {}; + } + + project.targets[targetKey] = deployTarget; + } + ); + + return project; + }; + + const nonMigratedProjects: Record = { + app: mocks.getApplication('app'), + nonPublishable: mocks.getLibWithoutBuildTarget('nonPublishable'), + }; + + Object.entries(projects).forEach(([key, { project, config }]) => { + nonMigratedProjects[key] = addConfig(project, config); + }); + + const tree: Tree = createTreeWithEmptyWorkspace(); + + Object.entries(nonMigratedProjects).forEach(([key, projectConfig]) => + addProjectConfiguration(tree, key, projectConfig) + ); + + return { tree, nonMigratedProjects }; + }; + + it('should migrate anything', async () => { + const { tree } = setUp({}); + + const allProjectsBeforeMigration = getProjects(tree); + await update(tree); + const allProjectsAfterMigration = getProjects(tree); + + expect(allProjectsBeforeMigration).toStrictEqual(allProjectsAfterMigration); + }); + + describe('Remove Deprecated Options', () => { + const setupRemoveDep = ({ + deployConfig = [ + { + noBuild: true, + buildTarget: 'staging', + }, + { + noBuild: true, + buildTarget: 'production', + }, + { + noBuild: true, + buildTarget: 'staging', + }, + { + noBuild: true, + buildTarget: 'production', + }, + ], + }: { + deployConfig?: [ + RemovedDeployExecutorOptions, + RemovedDeployExecutorOptions, + RemovedDeployExecutorOptions, + RemovedDeployExecutorOptions + ]; + }) => { + const PROJECT_NAME = 'PROJECT_NAME'; + const PROJECT_NAME2 = 'PROJECT_NAME2'; + + const projectConfig = (offset = 0) => ({ + build: { + buildConfigs: ['staging', 'production'], + }, + deploy: { + publishStaging: { + options: deployConfig[offset + 0], + }, + publishProd: { + options: deployConfig[offset + 1], + }, + }, + }); + + const { tree } = setUp({ + PROJECT_NAME: { + project: mocks.getLib(PROJECT_NAME), + config: projectConfig(), + }, + PROJECT_NAME2: { + project: mocks.getLib(PROJECT_NAME2), + config: projectConfig(1), + }, + }); + + const expectedDeployTargets = () => ({ + PROJECT_NAME: [ + expectedDeployTarget(PROJECT_NAME), + expectedDeployTarget(PROJECT_NAME), + ], + PROJECT_NAME2: [ + expectedDeployTarget(PROJECT_NAME2), + expectedDeployTarget(PROJECT_NAME2), + ], + }); + + return { tree, PROJECT_NAME, PROJECT_NAME2, expectedDeployTargets }; + }; + + // this is not filtering the projects with the executor + const getAllNgxDeployNPMTargets = (tree: Tree) => + Array.from(getProjects(tree)).reduce((acc, [projectName, project]) => { + const everyDeployTargets = Object.entries(project.targets ?? {}) + .filter(([, target]) => target.executor === 'ngx-deploy-npm:deploy') + .map( + ([, targetConfig]) => + targetConfig as TargetConfiguration + ); + + if (everyDeployTargets.length > 0) { + acc[projectName] = everyDeployTargets; + } + + return acc; + }, {} as Record[]>); + + it("should remove the `noBuild` option when it's set to `true`", async () => { + const { tree, expectedDeployTargets } = setupRemoveDep({ + deployConfig: [ + { noBuild: true }, + { noBuild: true }, + { noBuild: true }, + { noBuild: true }, + ], + }); + + await update(tree); + const allDeployTargets = getAllNgxDeployNPMTargets(tree); + + expect(allDeployTargets).toStrictEqual(expectedDeployTargets()); + }); + + it('should remove if the target has `buildTarget` option and `noBuild` is set to `true`', async () => { + const { tree, expectedDeployTargets } = setupRemoveDep({}); + + await update(tree); + const allDeployTargets = getAllNgxDeployNPMTargets(tree); + + expect(allDeployTargets).toStrictEqual(expectedDeployTargets()); + }); + }); + + describe('Migrate Deprecated Options', () => { + describe('`buildTarget` should be migrated to use a `dependsOn` instead', () => { + it('should migrate anything if `noBuild` is set to true', async () => { + const setupOptions: Parameters[0] = { + shouldNotBeTouchedLib: { + project: mocks.getLib('shouldNotBeTouchedLib'), + config: { + build: { + buildConfigs: ['local', 'staging'], + }, + deploy: { + publishLocal: { + preExistedDependsOn: [ + 'prePublish:local', + { target: 'random-project:thing-to-do' }, + ], + options: { + noBuild: true, + buildTarget: 'local', + }, + }, + publishStaging: { + options: { + noBuild: true, + }, + }, + }, + }, + }, + shouldNotBeTouchedLib2: { + project: mocks.getLib('shouldNotBeTouchedLib2'), + config: { + build: { + buildConfigs: ['staging', 'production'], + }, + deploy: { + publishLocal: { + preExistedDependsOn: ['prePublish:local'], + options: { + noBuild: true, + }, + }, + }, + }, + }, + }; + const { tree } = setUp(setupOptions); + + await update(tree); + const allProjectsAfterMigration = getProjects(tree); + + const allDeployTargetsAfterMigration = []; + allDeployTargetsAfterMigration.push( + allProjectsAfterMigration.get('shouldNotBeTouchedLib')?.targets?.[ + 'publishLocal' + ], + allProjectsAfterMigration.get('shouldNotBeTouchedLib')?.targets?.[ + 'publishStaging' + ], + allProjectsAfterMigration.get('shouldNotBeTouchedLib2')?.targets?.[ + 'publishLocal' + ] + ); + + const expectedDeployTargets = [ + expectedDeployTarget('shouldNotBeTouchedLib', [ + 'prePublish:local', + { target: 'random-project:thing-to-do' }, + ]), + expectedDeployTarget('shouldNotBeTouchedLib'), + expectedDeployTarget('shouldNotBeTouchedLib2', ['prePublish:local']), + ]; + + expect(allDeployTargetsAfterMigration).toStrictEqual( + expectedDeployTargets + ); + }); + + it('should migration put the `dependsOn` for packages that are being built', async () => { + const setupOptions: Parameters[0] = { + shouldCreateDependsOn: { + project: mocks.getLib('shouldCreateDependsOn'), + config: { + build: { + buildConfigs: ['local', 'staging'], + }, + deploy: { + publishLocal: { + preExistedDependsOn: ['existingDependsOn'], + options: { + noBuild: false, + }, + }, + publishStaging: { + options: { + noBuild: undefined, + }, + }, + }, + }, + }, + }; + const { tree } = setUp(setupOptions); + + await update(tree); + const allProjectsAfterMigration = getProjects(tree); + + const allTargetsAfterMigration: Record< + string, + TargetConfiguration | undefined + > = { + publishLocal: allProjectsAfterMigration.get('shouldCreateDependsOn') + ?.targets?.['publishLocal'], + publishStaging: allProjectsAfterMigration.get('shouldCreateDependsOn') + ?.targets?.['publishStaging'], + }; + + const expectedDeployTargets: Record< + string, + TargetConfiguration | undefined + > = { + publishLocal: expectedDeployTarget('shouldCreateDependsOn', [ + 'existingDependsOn', + 'build', + ]), + publishStaging: expectedDeployTarget('shouldCreateDependsOn', [ + 'build', + ]), + }; + + expect(allTargetsAfterMigration).toStrictEqual(expectedDeployTargets); + }); + + it('should create a pre-deploy target when the option `buildTarget` is present', async () => { + const setupOptions: Parameters[0] = { + shouldCreateDependsOn: { + project: mocks.getLib('shouldCreateDependsOn'), + config: { + build: { + buildConfigs: ['local', 'staging'], + }, + deploy: { + publishLocal: { + preExistedDependsOn: ['existingPrePublish-local'], + options: { + noBuild: false, + buildTarget: 'local', + }, + }, + publishStaging: { + options: { + noBuild: undefined, + buildTarget: 'staging', + }, + }, + }, + }, + }, + }; + const { tree } = setUp(setupOptions); + + await update(tree); + const allProjectsAfterMigration = getProjects(tree); + + const allTargetsAfterMigration: Record< + string, + TargetConfiguration | undefined + > = { + 'pre-publishLocal-build-local': allProjectsAfterMigration.get( + 'shouldCreateDependsOn' + )?.targets?.['pre-publishLocal-build-local'], + 'pre-publishStaging-build-staging': allProjectsAfterMigration.get( + 'shouldCreateDependsOn' + )?.targets?.['pre-publishStaging-build-staging'], + publishLocal: allProjectsAfterMigration.get('shouldCreateDependsOn') + ?.targets?.['publishLocal'], + publishStaging: allProjectsAfterMigration.get('shouldCreateDependsOn') + ?.targets?.['publishStaging'], + }; + + const expectedDeployTargets: Record< + string, + TargetConfiguration | undefined + > = { + 'pre-publishLocal-build-local': { + executor: 'nx:run-commands', + options: { + command: `nx run shouldCreateDependsOn:build:local`, + }, + }, + 'pre-publishStaging-build-staging': { + executor: 'nx:run-commands', + options: { + command: `nx run shouldCreateDependsOn:build:staging`, + }, + }, + publishLocal: expectedDeployTarget('shouldCreateDependsOn', [ + 'existingPrePublish-local', + 'pre-publishLocal-build-local', + ]), + publishStaging: expectedDeployTarget('shouldCreateDependsOn', [ + 'pre-publishStaging-build-staging', + ]), + }; + + expect(allTargetsAfterMigration).toStrictEqual(expectedDeployTargets); + }); + }); + }); +}); diff --git a/packages/ngx-deploy-npm/src/migrations/8.0.0/replace-buildtarget-for-depends-on.ts b/packages/ngx-deploy-npm/src/migrations/8.0.0/replace-buildtarget-for-depends-on.ts new file mode 100644 index 00000000..533a5ea3 --- /dev/null +++ b/packages/ngx-deploy-npm/src/migrations/8.0.0/replace-buildtarget-for-depends-on.ts @@ -0,0 +1,149 @@ +/* eslint-disable @typescript-eslint/no-unused-vars */ +/** + Remove the old `configuration` option and: + - create a new target to build the library with the right configuration + - create the `dependsOn` option on the deploy target + - Remove deprecated options `buildTarget` and `noBuild` +*/ +import { + ProjectConfiguration, + TargetConfiguration, + Tree, + formatFiles, + getProjects, + updateProjectConfiguration, +} from '@nx/devkit'; +import { DeployExecutorOptions } from '../../executors/deploy/schema'; + +export type RemovedDeployExecutorOptions = { + /** + * A named build target, as specified in the `configurations`. Each named target is accompanied by a configuration of option defaults for that target. This is equivalent to calling the command `nx build --configuration=XXX`. + */ + buildTarget?: string; + /** + * Skip build process during deployment. + * Default: false + */ + noBuild?: boolean; +}; + +export type DeprecatedDeployExecutorOptions = DeployExecutorOptions & + RemovedDeployExecutorOptions; + +export default async function update(host: Tree) { + dependsOnMigration(host); + removeDeprecatedOptionsMigration(host); + + await formatFiles(host); +} + +function dependsOnMigration(host: Tree) { + // Get projects that require creating of dependsOn + const projectToCreateDependsOn = Array.from(getProjects(host)) + // remove projects that doesn't have the our executor or already have the option distFolderPath + .filter(([_, project]) => { + const projectTargets: TargetConfiguration[] = + Object.values(project.targets ?? {}); + + return projectTargets.some(targetRequiresMigrationCreationDependsOn); + }); + + // Create the `dependencyOn` the deploy target + projectToCreateDependsOn.forEach(([projectKey, project]) => { + createDependsOn(projectKey, project); + updateProjectConfiguration(host, projectKey, project); + }); + + function targetRequiresMigrationCreationDependsOn( + target: TargetConfiguration + ) { + return ( + target.executor === 'ngx-deploy-npm:deploy' && // has the right executor + target.options?.noBuild !== true // the target will build the library + ); + } + + function createDependsOn(projectKey: string, project: ProjectConfiguration) { + const deployExecutors: [ + string, + TargetConfiguration + ][] = Object.entries(project.targets ?? {}).filter( + ([targetName, targetConfig]) => + targetRequiresMigrationCreationDependsOn(targetConfig) + ); + + deployExecutors.forEach(([targetName, targetConfig]) => { + // store the old buildTarget value + const buildTarget = targetConfig.options?.buildTarget; + + // Create targets in case that they doesn't already exists + if (!project.targets) { + project.targets = {}; + } + + // If our executor was building the library, it needs to depend on the build target + let newDependsOn = 'build'; + if (typeof buildTarget === 'string') { + const newPreDeployTargetName = `pre-${targetName}-build-${buildTarget}`; + newDependsOn = newPreDeployTargetName; + + project.targets[newPreDeployTargetName] = { + executor: 'nx:run-commands', + options: { + command: `nx run ${projectKey}:build:${buildTarget}`, + }, + }; + } + + const dependsOn = project.targets[targetName].dependsOn; + if (dependsOn === undefined) { + project.targets[targetName].dependsOn = []; + } + + project.targets[targetName].dependsOn?.push(newDependsOn); + }); + } +} + +async function removeDeprecatedOptionsMigration(host: Tree) { + // Get projects that require removing of buildTarget and noBuild + const projectToMigrate = Array.from(getProjects(host)) + // remove projects that doesn't have the our executor or already have the option distFolderPath + .filter(([_, project]) => { + const projectTargets: TargetConfiguration[] = + Object.values(project.targets ?? {}); + + return projectTargets.some(targetRequiresMigration); + }); + + // Remove Deprecated options the `dependencyOn` the deploy target + projectToMigrate.forEach(([projectKey, project]) => { + removeBuildTargetAndNoBuildOptions(project); + updateProjectConfiguration(host, projectKey, project); + }); + + function targetRequiresMigration( + target: TargetConfiguration + ) { + return ( + target.executor === 'ngx-deploy-npm:deploy' && // has the right executor + (target.options?.noBuild !== undefined || // the target will build the library + target?.options?.buildTarget !== undefined) // the target has the buildTarget option + ); + } + + function removeBuildTargetAndNoBuildOptions(project: ProjectConfiguration) { + const deployExecutors: [ + string, + TargetConfiguration + ][] = Object.entries(project.targets ?? {}).filter(([_, targetConfig]) => + targetRequiresMigration(targetConfig) + ); + + deployExecutors.forEach(([_, targetConfig]) => { + // Remove option build target + delete targetConfig.options?.buildTarget; + delete targetConfig.options?.noBuild; + }); + } +} diff --git a/packages/ngx-deploy-npm/src/migrations/8.0.0/write-dist-folder-path-on-deploy-target-options.spec.ts b/packages/ngx-deploy-npm/src/migrations/8.0.0/write-dist-folder-path-on-deploy-target-options.spec.ts new file mode 100644 index 00000000..ea3ecf73 --- /dev/null +++ b/packages/ngx-deploy-npm/src/migrations/8.0.0/write-dist-folder-path-on-deploy-target-options.spec.ts @@ -0,0 +1,132 @@ +import { createTreeWithEmptyWorkspace } from '@nx/devkit/testing'; +import { + ProjectConfiguration, + TargetConfiguration, + Tree, + addProjectConfiguration, + getProjects, +} from '@nx/devkit'; +import * as mocks from '../../__mocks__/mocks'; + +import update, { + DeprecatedDeployExecutorOptions, +} from './write-dist-folder-path-on-deploy-target-options'; + +describe('write-dist-folder-path-on-deploy-target-options migration', () => { + const setUp = () => { + const addTargets = ( + project: ProjectConfiguration, + addDistFolderPathOption = true + ) => { + if (!project.targets) { + project.targets = {}; + } + + const deployTarget: TargetConfiguration = + { + executor: 'ngx-deploy-npm:deploy', + options: { + distFolderPath: addDistFolderPathOption + ? `dist/libs/${project.name}` + : undefined, + access: 'public', + }, + }; + + project.targets.deploy = deployTarget; + project.targets.publish = deployTarget; + + return project; + }; + + const nonMigratedProjects: Record = { + WITH_distFolderPathOption: addTargets( + mocks.getLib('WITH_distFolderPathOption') + ), + WITHOUT_distFolderPathOption1: addTargets( + mocks.getLib('WITHOUT_distFolderPathOption1'), + false + ), + WITHOUT_distFolderPathOption2: addTargets( + mocks.getLib('WITHOUT_distFolderPathOption2'), + false + ), + + app: mocks.getApplication('app'), + nonPublishable: mocks.getLibWithoutBuildTarget('nonPublishable'), + }; + + const tree: Tree = createTreeWithEmptyWorkspace(); + + Object.entries(nonMigratedProjects).forEach(([key, projectConfig]) => + addProjectConfiguration(tree, key, projectConfig) + ); + + return { tree, nonMigratedProjects }; + }; + + it('should set up the distFolderPath option on the right projects', async () => { + const { tree } = setUp(); + + await update(tree); + + const allProjects = getProjects(tree); + const WITHOUT_distFolderPathOption1 = allProjects.get( + 'WITHOUT_distFolderPathOption1' + ); + const WITHOUT_distFolderPathOption2 = allProjects.get( + 'WITHOUT_distFolderPathOption2' + ); + + expect( + WITHOUT_distFolderPathOption1?.targets?.deploy.options.distFolderPath + ).toBeTruthy(); + expect( + WITHOUT_distFolderPathOption1?.targets?.publish.options.distFolderPath + ).toBeTruthy(); + expect( + WITHOUT_distFolderPathOption2?.targets?.deploy.options.distFolderPath + ).toBeTruthy(); + expect( + WITHOUT_distFolderPathOption2?.targets?.publish.options.distFolderPath + ).toBeTruthy(); + }); + + it('should set up the distFolderPath option with the right value', async () => { + const { tree } = setUp(); + + await update(tree); + + const allProjects = getProjects(tree); + const WITHOUT_distFolderPathOption1 = allProjects.get( + 'WITHOUT_distFolderPathOption1' + ); + + expect( + WITHOUT_distFolderPathOption1?.targets?.deploy.options.distFolderPath + ).toStrictEqual(`dist/libs/${WITHOUT_distFolderPathOption1?.name ?? ''}`); + expect( + WITHOUT_distFolderPathOption1?.targets?.publish.options.distFolderPath + ).toStrictEqual(`dist/libs/${WITHOUT_distFolderPathOption1?.name ?? ''}`); + }); + + it('should not touch other projects', async () => { + const { tree } = setUp(); + const getNonMigratedProjects = (tree: Tree) => { + const allProjects = getProjects(tree); + return { + projectBefore: allProjects.get('projectBefore'), + WITH_distFolderPathOption: allProjects.get('WITH_distFolderPathOption'), + app: allProjects.get('app'), + nonPublishable: allProjects.get('nonPublishable'), + }; + }; + const nonMigratedProjectsBefore = getNonMigratedProjects(tree); + + await update(tree); + + const nonMigratedProjectsAfter = getNonMigratedProjects(tree); + + expect(nonMigratedProjectsBefore).toStrictEqual(nonMigratedProjectsAfter); + }); +}); diff --git a/packages/ngx-deploy-npm/src/migrations/8.0.0/write-dist-folder-path-on-deploy-target-options.ts b/packages/ngx-deploy-npm/src/migrations/8.0.0/write-dist-folder-path-on-deploy-target-options.ts new file mode 100644 index 00000000..4d13b8ec --- /dev/null +++ b/packages/ngx-deploy-npm/src/migrations/8.0.0/write-dist-folder-path-on-deploy-target-options.ts @@ -0,0 +1,49 @@ +import { + TargetConfiguration, + Tree, + formatFiles, + getProjects, + updateProjectConfiguration, + logger, +} from '@nx/devkit'; +import { DeployExecutorOptions } from '../../executors/deploy/schema'; + +export type DeprecatedDeployExecutorOptions = Omit< + DeployExecutorOptions, + 'distFolderPath' +> & { distFolderPath?: string }; + +const targetNeedsMigration = ( + target: TargetConfiguration +) => + target.executor === 'ngx-deploy-npm:deploy' && + target.options?.distFolderPath === undefined; + +export default async function update(host: Tree) { + const projectToMigrate = Array.from(getProjects(host)) + // remove projects that doesn't have the our executor or already have the option distFolderPath + .filter(([, project]) => { + const projectTargets: TargetConfiguration[] = + Object.values(project.targets ?? {}); + return projectTargets.some(targetNeedsMigration); + }); + + projectToMigrate.forEach(([projectKey, project]) => { + if (project.name === undefined) { + logger.warn( + `Project ${projectKey} doesn't have a name\nIt was skipped, you will need to create the option distFolderPath manually` + ); + return; + } + + // Create the distFolderPath option + Object.values(project.targets ?? {}) + .filter(targetNeedsMigration) + .forEach(deployTarget => { + deployTarget.options.distFolderPath = `dist/${project.root}`; + }); + updateProjectConfiguration(host, project.name, project); + }); + + await formatFiles(host); +} diff --git a/packages/ngx-deploy-npm/src/utils/file-utils.spec.ts b/packages/ngx-deploy-npm/src/utils/file-utils.spec.ts new file mode 100644 index 00000000..f3460410 --- /dev/null +++ b/packages/ngx-deploy-npm/src/utils/file-utils.spec.ts @@ -0,0 +1,45 @@ +import * as fs from 'fs'; +import * as path from 'path'; +import { fileExists } from './file-utils'; + +describe('File Utils', () => { + describe('FileExists', () => { + let fakeFilePath: string; + + const setUp = ({ fileShouldExists }: { fileShouldExists: boolean }) => { + const accessSpy = jest + .spyOn(fs, 'access') + .mockImplementation((_: fs.PathLike, callback: fs.NoParamCallback) => { + if (fileShouldExists) { + callback(null); + } else { + callback(new Error('File not found')); + } + }); + + return { + accessSpy, + }; + }; + + beforeEach(() => { + fakeFilePath = path.join('random', 'path', 'file', 'package.json'); + }); + + it('should indicate that the file exists', async () => { + setUp({ fileShouldExists: true }); + + const response = await fileExists(fakeFilePath); + + expect(response).toBe(true); + }); + + it('should indicate that the file exists', async () => { + setUp({ fileShouldExists: false }); + + const response = await fileExists(fakeFilePath); + + expect(response).toBe(false); + }); + }); +}); diff --git a/packages/ngx-deploy-npm/src/utils/file-utils.ts b/packages/ngx-deploy-npm/src/utils/file-utils.ts new file mode 100644 index 00000000..9e9f19ce --- /dev/null +++ b/packages/ngx-deploy-npm/src/utils/file-utils.ts @@ -0,0 +1,15 @@ +import { promisify } from 'util'; +import { readFile, writeFile, access } from 'fs'; + +export const readFileAsync = promisify(readFile); + +export const writeFileAsync = promisify(writeFile); + +export async function fileExists(filePath: string) { + try { + await promisify(access)(filePath); + return true; + } catch { + return false; + } +} diff --git a/packages/ngx-deploy-npm/src/utils/index.ts b/packages/ngx-deploy-npm/src/utils/index.ts new file mode 100644 index 00000000..771069c4 --- /dev/null +++ b/packages/ngx-deploy-npm/src/utils/index.ts @@ -0,0 +1,2 @@ +export * from './file-utils'; +export * from './is-a-lib'; diff --git a/packages/ngx-deploy-npm/src/utils/is-a-lib.spec.ts b/packages/ngx-deploy-npm/src/utils/is-a-lib.spec.ts new file mode 100644 index 00000000..32e94f69 --- /dev/null +++ b/packages/ngx-deploy-npm/src/utils/is-a-lib.spec.ts @@ -0,0 +1,85 @@ +import { isProjectAPublishableLib } from './is-a-lib'; +import * as fileUtils from './file-utils'; +import { ProjectConfiguration } from '@nx/devkit'; +import * as mocks from '../__mocks__/mocks'; +import * as path from 'path'; + +describe('is-a-lib', () => { + const setUp = () => { + const projects: Record< + 'publishableLibrary' | 'nonPublishableLibrary' | 'app', + ProjectConfiguration + > = { + publishableLibrary: mocks.getLib('pub-lib'), + nonPublishableLibrary: mocks.getLib('non-pub-lib'), + app: mocks.getApplication('app'), + }; + + return { projects }; + }; + + describe('isProjectAPublishableLib', () => { + const setUpIsProjectAPublishableLib = ({ + shouldPackageJsonExists, + }: { + shouldPackageJsonExists: boolean; + }) => { + const { projects } = setUp(); + + const fileExistsMock = jest + .spyOn(fileUtils, 'fileExists') + .mockImplementation(() => Promise.resolve(shouldPackageJsonExists)); + + return { fileExistsMock, projects }; + }; + + afterEach(jest.restoreAllMocks); + + it('should indicate that the project is a publishable library', async () => { + const { projects } = setUpIsProjectAPublishableLib({ + shouldPackageJsonExists: true, + }); + + const response = await isProjectAPublishableLib( + projects.publishableLibrary + ); + + expect(response).toBe(true); + }); + + it('should indicate that the project is a non publishable library (app)', async () => { + const { projects } = setUpIsProjectAPublishableLib({ + shouldPackageJsonExists: true, + }); + + const response = await isProjectAPublishableLib(projects.app); + + expect(response).toBe(false); + }); + + it('should indicate that the project is a non publishable library (non publishable library)', async () => { + const { projects } = setUpIsProjectAPublishableLib({ + shouldPackageJsonExists: false, + }); + + const response = await isProjectAPublishableLib( + projects.nonPublishableLibrary + ); + + expect(response).toBe(false); + }); + + it('should look for package.json file', async () => { + const { fileExistsMock, projects } = setUpIsProjectAPublishableLib({ + shouldPackageJsonExists: false, + }); + const project = projects.nonPublishableLibrary; + + await isProjectAPublishableLib(project); + + expect(fileExistsMock.mock.calls[0][0]).toEqual( + path.join(project.root, 'package.json') + ); + }); + }); +}); diff --git a/packages/ngx-deploy-npm/src/utils/is-a-lib.ts b/packages/ngx-deploy-npm/src/utils/is-a-lib.ts new file mode 100644 index 00000000..9d0e5225 --- /dev/null +++ b/packages/ngx-deploy-npm/src/utils/is-a-lib.ts @@ -0,0 +1,15 @@ +import { ProjectConfiguration } from '@nx/devkit'; +import { fileExists } from './file-utils'; +import * as path from 'path'; + +export const isProjectAPublishableLib = async ( + project: ProjectConfiguration +): Promise => { + return ( + project.projectType === 'library' && (await hasProjectJsonFile(project)) + ); +}; + +function hasProjectJsonFile(project: ProjectConfiguration): Promise { + return fileExists(path.join(project.root, 'package.json')); +} diff --git a/project.json b/project.json new file mode 100644 index 00000000..12ef8ced --- /dev/null +++ b/project.json @@ -0,0 +1,14 @@ +{ + "name": "bikecoders", + "$schema": "node_modules/nx/schemas/project-schema.json", + "targets": { + "local-registry": { + "executor": "@nx/js:verdaccio", + "options": { + "port": 4873, + "config": ".verdaccio/config.yml", + "storage": "tmp/local-registry/storage" + } + } + } +} diff --git a/sonar-project.properties b/sonar-project.properties index 29088089..98016ecb 100644 --- a/sonar-project.properties +++ b/sonar-project.properties @@ -11,13 +11,11 @@ sonar.modules=ngx-deploy-npm-e2e,ngx-deploy-npm # Files to exclude sonar.exclusions=**/node_modules/** # How to find the test -sonar.test.inclusions=**/*.spec.ts -# Ignore all __mocks__ folders -sonar.coverage.exclusions=**/__mocks__/** +sonar.test.inclusions=**/*.spec.ts,**/__mocks__/** # ------- ngx-deploy-npm e2e ------- ngx-deploy-npm-e2e.sonar.projectBaseDir=e2e/ngx-deploy-npm-e2e -ngx-deploy-npm-e2e.sonar.tests=tests +ngx-deploy-npm-e2e.sonar.tests=./ # The coverage report # ngx-deploy-npm-e2e.sonar.typescript.lcov.reportPaths=../../../../coverage/apps/demo/lcov.info # ------- ngx-deploy-npm e2e off ------- @@ -38,4 +36,4 @@ ngx-deploy-npm.sonar.javascript.lcov.reportPaths=/github/workspace/coverage/pack # ------- ngx-deploy-npm off ------- # For more information visit -# https://docs.sonarqube.org/display/SONAR/Analysis+Parameters \ No newline at end of file +# https://docs.sonarqube.org/display/SONAR/Analysis+Parameters diff --git a/tools/create-nx-workspace.sh b/tools/create-nx-workspace.sh index cf7a0faf..e079815c 100755 --- a/tools/create-nx-workspace.sh +++ b/tools/create-nx-workspace.sh @@ -20,14 +20,16 @@ echo "NX_WORKSPACE_ROOT_PATH=$(pwd)" >.env echo "----- Generate lib -----" npm add -D @nx/node@$version -npx nx generate @nx/node:lib --name nx-lib --publishable --importPath nx-lib +npx nx generate @nx/node:init +npx nx generate @nx/node:library nx-lib --directory libs --publishable --importPath nx-lib echo "----- Link ngx-deploy-npm -----" -npx --yes yalc add ngx-deploy-npm -npm i +# npx --yes yalc add ngx-deploy-npm +npm install -D ngx-deploy-npm +# npm i echo "----- Add ngx-deploy-npm to the workspace -----" -npx nx generate ngx-deploy-npm:install +npx nx generate ngx-deploy-npm:install --project nx-lib --distFolderPath dist/libs/nx-lib echo "----- Test the build -----" npx nx deploy nx-lib --dry-run