├── .eslintrc.json ├── .github └── workflows │ └── test.yml ├── .gitignore ├── .npmrc ├── CODE_OF_CONDUCT.md ├── CONTRIBUTING.md ├── LICENSE ├── README.md ├── bin └── support ├── doc └── command-line-usage.md ├── examples ├── basic.json ├── complex.json └── minimum.json ├── index.js ├── lib └── cli │ ├── commands │ ├── badges.js │ ├── create.js │ ├── show.js │ └── validate.js │ ├── create │ ├── create-support-template.json │ └── index.js │ └── index.js ├── package-support.json ├── package.json ├── schema.json ├── support-element-schema.json └── test ├── cli ├── create-on-existed-support │ ├── command │ ├── expected │ ├── expected-errors │ ├── package-support.json │ └── package.json ├── show-local-circular-dependency │ ├── command │ ├── expected │ ├── exptected │ ├── node_modules │ │ ├── dep1 │ │ │ ├── package-support.json │ │ │ └── package.json │ │ ├── dep2 │ │ │ ├── package-support.json │ │ │ └── package.json │ │ └── dep3 │ │ │ ├── package-support.json │ │ │ └── package.json │ ├── package-support.json │ └── package.json ├── show-local-escape-ok │ ├── command │ ├── expected │ └── package.json ├── show-local-escape │ ├── command │ ├── expected │ └── package.json ├── show-local-path1 │ ├── command │ ├── expected │ ├── my-support-info.json │ └── package.json ├── show-local-path2 │ ├── command │ ├── expected │ ├── package.json │ └── subdir1 │ │ └── my-support-info.json ├── show-local-tree-flat │ ├── command │ ├── expected │ ├── exptected │ ├── node_modules │ │ ├── dep1 │ │ │ ├── package-support.json │ │ │ └── package.json │ │ ├── dep2 │ │ │ ├── package-support.json │ │ │ └── package.json │ │ └── dep3 │ │ │ ├── package-support.json │ │ │ └── package.json │ ├── package-support.json │ └── package.json ├── show-local-tree │ ├── command │ ├── expected │ ├── exptected │ ├── node_modules │ │ ├── dep1 │ │ │ ├── package-support.json │ │ │ └── package.json │ │ └── dep2 │ │ │ ├── node_modules │ │ │ └── dep3 │ │ │ │ ├── package-support.json │ │ │ │ └── package.json │ │ │ ├── package-support.json │ │ │ └── package.json │ ├── package-support.json │ └── package.json ├── show-local │ ├── command │ ├── expected │ ├── package-support.json │ └── package.json ├── show-separate-repo-directory1 │ ├── command │ ├── expected │ └── package.json ├── show-separate-repo-directory2 │ ├── command │ ├── expected │ └── package.json ├── show-separate-repo-directory3 │ ├── command │ ├── expected │ └── package.json ├── show-separate-repo-fetch-missing │ ├── command │ ├── expected-errors │ └── package.json ├── show-separate-repo-fetch │ ├── command │ ├── expected │ └── package.json ├── show-separate-repo-path-escape │ ├── command │ ├── expected │ └── package.json ├── show-separate-repo-path1 │ ├── command │ ├── expected │ └── package.json ├── show-separate-repo-path2 │ ├── command │ ├── expected │ └── package.json ├── show-separate-repo │ ├── command │ ├── expected │ ├── package-support.json │ └── package.json ├── validate-invalid-json │ ├── command │ ├── expected-errors │ ├── package-support.json │ └── package.json ├── validate-local-bad-element1 │ ├── command │ ├── expected-errors │ └── package.json ├── validate-local-bad-element2 │ ├── command │ ├── expected-errors │ └── package.json ├── validate-local-bad-element3 │ ├── command │ ├── expected-errors │ └── package.json ├── validate-local-escape-ok │ ├── command │ ├── expected │ └── package.json ├── validate-local-no-data │ ├── command │ ├── expected-errors │ └── package.json ├── validate-local-repository-bad1 │ ├── command │ ├── expected-errors │ └── package.json ├── validate-local-repository-bad2 │ ├── command │ ├── expected-errors │ └── package.json ├── validate-local-repository-bad3 │ ├── command │ ├── expected-errors │ └── package.json ├── validate-local-repository-bad4 │ ├── command │ ├── expected-errors │ └── package.json ├── validate-local-repository-bad5 │ ├── command │ ├── expected-errors │ └── package.json ├── validate-local-repository1 │ ├── command │ ├── expected-errors │ └── package.json ├── validate-local-support-json-bad │ ├── command │ ├── expected-errors │ ├── package-support.json │ └── package.json ├── validate-local-support-json-bad2 │ ├── command │ ├── expected-errors │ ├── package-support.json │ └── package.json ├── validate-local-support-json-bad3 │ ├── command │ ├── expected-errors │ ├── package-support.json │ └── package.json ├── validate-local │ ├── command │ ├── expected │ ├── package-support.json │ └── package.json ├── validate-multiple-backing │ ├── command │ ├── expected │ ├── package-support.json │ └── package.json ├── validate-multiple-backing2 │ ├── command │ ├── expected │ ├── package-support.json │ └── package.json ├── validate-non-resolved │ ├── command │ ├── expected-errors │ └── package.json └── validate-separate-repo-fetch │ ├── command │ ├── expected │ └── package.json ├── create.js ├── fixtures ├── create │ ├── create-with-default-values │ │ ├── default-package.json │ │ ├── expected-package.json │ │ └── expexted-package-support.json │ ├── create-with-funding-yml-no-file │ │ └── default-package.json │ ├── create-with-funding-yml-positive │ │ ├── .github │ │ │ └── FUNDING.yml │ │ ├── default-package.json │ │ ├── expected-package.json │ │ └── expexted-package-support.json │ ├── create-with-package-json-funding-positive │ │ ├── default-package.json │ │ ├── expected-package.json │ │ └── expexted-package-support.json │ ├── create-with-package-json-funding-string-positive │ │ ├── default-package.json │ │ ├── expected-package.json │ │ └── expexted-package-support.json │ └── create-with-package-json-funding │ │ └── default-package.json └── my-support-info.json └── index.js /.eslintrc.json: -------------------------------------------------------------------------------- 1 | {"extends": "semistandard"} 2 | -------------------------------------------------------------------------------- /.github/workflows/test.yml: -------------------------------------------------------------------------------- 1 | name: Test 2 | on: 3 | push: 4 | branches: [ main ] 5 | pull_request: 6 | branches: [ main ] 7 | 8 | jobs: 9 | test: 10 | runs-on: ubuntu-latest 11 | strategy: 12 | matrix: 13 | node-version: [10.x, 12.x, 14.x, 16.x, 17.x, 18.x, 20.x, 22.x] 14 | os: [ubuntu-latest, windows-latest] 15 | 16 | steps: 17 | - uses: actions/checkout@v2 18 | - name: Use Node.js ${{ matrix.node-version }} 19 | uses: actions/setup-node@v1 20 | with: 21 | node-version: ${{ matrix.node-version }} 22 | - name: npm install and test 23 | run: npm it 24 | env: 25 | NO_COLOR: 1 26 | -------------------------------------------------------------------------------- /.gitignore: -------------------------------------------------------------------------------- 1 | # default 2 | pacakge-lock.json 3 | 4 | # Logs 5 | logs 6 | *.log 7 | npm-debug.log* 8 | yarn-debug.log* 9 | yarn-error.log* 10 | lerna-debug.log* 11 | 12 | # Diagnostic reports (https://nodejs.org/api/report.html) 13 | report.[0-9]*.[0-9]*.[0-9]*.[0-9]*.json 14 | 15 | # Runtime data 16 | pids 17 | *.pid 18 | *.seed 19 | *.pid.lock 20 | 21 | # Directory for instrumented libs generated by jscoverage/JSCover 22 | lib-cov 23 | 24 | # Coverage directory used by tools like istanbul 25 | coverage 26 | *.lcov 27 | 28 | # nyc test coverage 29 | .nyc_output 30 | 31 | # Grunt intermediate storage (https://gruntjs.com/creating-plugins#storing-task-files) 32 | .grunt 33 | 34 | # Bower dependency directory (https://bower.io/) 35 | bower_components 36 | 37 | # node-waf configuration 38 | .lock-wscript 39 | 40 | # Compiled binary addons (https://nodejs.org/api/addons.html) 41 | build/Release 42 | 43 | # Dependency directories 44 | node_modules/ 45 | jspm_packages/ 46 | 47 | # TypeScript v1 declaration files 48 | typings/ 49 | 50 | # TypeScript cache 51 | *.tsbuildinfo 52 | 53 | # Optional npm cache directory 54 | .npm 55 | 56 | # Optional eslint cache 57 | .eslintcache 58 | 59 | # Optional REPL history 60 | .node_repl_history 61 | 62 | # Output of 'npm pack' 63 | *.tgz 64 | 65 | # Yarn Integrity file 66 | .yarn-integrity 67 | 68 | # dotenv environment variables file 69 | .env 70 | .env.test 71 | 72 | # parcel-bundler cache (https://parceljs.org/) 73 | .cache 74 | 75 | # next.js build output 76 | .next 77 | 78 | # nuxt.js build output 79 | .nuxt 80 | 81 | # vuepress build output 82 | .vuepress/dist 83 | 84 | # Serverless directories 85 | .serverless/ 86 | 87 | # FuseBox cache 88 | .fusebox/ 89 | 90 | # DynamoDB Local files 91 | .dynamodb/ -------------------------------------------------------------------------------- /.npmrc: -------------------------------------------------------------------------------- 1 | package-lock=false 2 | -------------------------------------------------------------------------------- /CODE_OF_CONDUCT.md: -------------------------------------------------------------------------------- 1 | # Code of Conduct 2 | 3 | The Node.js Code of Conduct, which applies to this project, can be found at 4 | https://github.com/nodejs/admin/blob/master/CODE_OF_CONDUCT.md. 5 | -------------------------------------------------------------------------------- /CONTRIBUTING.md: -------------------------------------------------------------------------------- 1 | # Contributing 2 | 3 | ## Code of Conduct 4 | 5 | The Node.js project has a 6 | [Code of Conduct](https://github.com/nodejs/admin/blob/master/CODE_OF_CONDUCT.md) 7 | to which all contributors must adhere. 8 | 9 | See [details on our policy on Code of Conduct](https://github.com/nodejs/node/blob/master/doc/contributing/code-of-conduct.md). 10 | 11 | 12 | ## Developer's Certificate of Origin 1.1 13 | 14 | By making a contribution to this project, I certify that: 15 | 16 | * (a) The contribution was created in whole or in part by me and I 17 | have the right to submit it under the open source license 18 | indicated in the file; or 19 | 20 | * (b) The contribution is based upon previous work that, to the best 21 | of my knowledge, is covered under an appropriate open source 22 | license and I have the right under that license to submit that 23 | work with modifications, whether created in whole or in part 24 | by me, under the same open source license (unless I am 25 | permitted to submit under a different license), as indicated 26 | in the file; or 27 | 28 | * (c) The contribution was provided directly to me by some other 29 | person who certified (a), (b) or (c) and I have not modified 30 | it. 31 | 32 | * (d) I understand and agree that this project and the contribution 33 | are public and that a record of the contribution (including all 34 | personal information I submit with it, including my sign-off) is 35 | maintained indefinitely and may be redistributed consistent with 36 | this project or the open source license(s) involved. 37 | -------------------------------------------------------------------------------- /LICENSE: -------------------------------------------------------------------------------- 1 | MIT License 2 | 3 | Copyright (c) 2020 Contributors https://github.com/pkgjs/support/graphs/contributors 4 | 5 | Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated documentation files (the "Software"), to deal in the Software without restriction, including without limitation the rights to use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of the Software, and to permit persons to whom the Software is furnished to do so, subject to the following conditions: 6 | 7 | The above copyright notice and this permission notice shall be included in all copies or substantial portions of the Software. 8 | 9 | THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. 10 | 11 | -------------------------------------------------------------------------------- /README.md: -------------------------------------------------------------------------------- 1 | # Package Support 2 | 3 | [![NPM Version](https://img.shields.io/npm/v/@pkgjs/support.svg)](https://npmjs.org/package/@pkgjs/support) 4 | [![NPM Downloads](https://img.shields.io/npm/dm/@pkgjs/support.svg)](https://npmjs.org/package/@pkgjs/support) 5 | [![js-semistandard-style](https://img.shields.io/badge/code%20style-semistandard-brightgreen.svg)](https://github.com/standard/semistandard) 6 | [![CI Test](https://github.com/pkgjs/support/workflows/Test/badge.svg)](https://github.com/pkgjs/support/actions) 7 | 8 | ![support backing](https://img.shields.io/badge/support%20backing-HOBBY-blue.svg) 9 | ![support target](https://img.shields.io/badge/support%20target-LTS-red.svg) 10 | ![support response-def](https://img.shields.io/badge/support%20response-best--effort-yellow.svg) 11 | 12 | When an author releases an Open Source package there are many different levels 13 | of support they may intend to provide. The [Node.js Package Maintenance Working Group](https://github.com/nodejs/package-maintenance) 14 | is working to propose [a spec](https://github.com/nodejs/package-maintenance/blob/HEAD/docs/PACKAGE-SUPPORT.md) to help package authors declare their intended support goals. This package provides 15 | some tooling around working with the format proposed. 16 | 17 | This repository is managed by the [Package Maintenance Working Group](https://github.com/nodejs/package-maintenance), see [Governance](https://github.com/nodejs/package-maintenance/blob/HEAD/Governance.md). 18 | 19 | ## Command line usage 20 | 21 | A command line tool is provided which supports the following commands: 22 | 23 | * show - show the support info for the package tree. 24 | * validate - validate support info for a package, to be used by a 25 | maintainer before publishing. 26 | * create - setup a support declaration for a package. 27 | 28 | These commands support the following options: 29 | 30 | * --canonical - prefer canonical data over package support data 31 | that may be available locally. Default is `false`. 32 | * --fetch - if local support data is not available or --canonical 33 | is specified, fetch the support data from the remote canonical 34 | location when needed. Default is `false` 35 | * --base-path - directory root within which the tool can read/validate 36 | package support files. The default is the directory from which the 37 | package.json for the top level package was read. 38 | 39 | More details and explanation of the use cases for these 40 | commands is provided in [command line usage](./doc/command-line-usage.md). 41 | 42 | The simplest way to run the tool is to simply run: 43 | 44 | ``` 45 | npx @pkgjs/support show 46 | ``` 47 | 48 | ``` 49 | npx @pkgjs/support validate 50 | ``` 51 | 52 | ``` 53 | npx @pkgjs/support create 54 | ``` 55 | -------------------------------------------------------------------------------- /bin/support: -------------------------------------------------------------------------------- 1 | #! /usr/bin/env node 2 | require('../lib/cli')()(process.argv.slice(2)); 3 | -------------------------------------------------------------------------------- /doc/command-line-usage.md: -------------------------------------------------------------------------------- 1 | # Using the package support tool from the command line 2 | 3 | There are 2 main use cases for the package support tool 4 | 5 | * Package Maintainers - document and communicate expectations to consumers 6 | * Package Consumers - understand more about their key dependencies and where they 7 | should invest. 8 | 9 | The sections which follow document the usage/options of interest for each use 10 | case. 11 | 12 | Once you have node.js installed (version 10.x or later) you can 13 | run the support command directly using npx or optionally npm install the 14 | package and add the `bin` directory to your path. In either case 15 | you can run the support tool using `npx @pkgjs/support`. 16 | 17 | ## Package Consumers 18 | 19 | The support tool helps package consumers review and understand the 20 | package support information provided by maintainers. See 21 | [Package-support.md](https://github.com/nodejs/package-maintenance/blob/HEAD/docs/PACKAGE-SUPPORT.md) 22 | which documents the suggested best practice and the specific format of the 23 | package support information. 24 | 25 | Package consumers use the `show` command to display the support information 26 | provided by package maintainers. 27 | 28 | It is understood that this is only the most basic support that can be provided 29 | to the consumer. The current focus for the support tool is to provide features 30 | to encourage/support maintainers to add the package support info to their packages. 31 | In the future more advanced options can be added to the show command to provide 32 | more deduplicated or focussed views of the information available. 33 | 34 | The general flow is: 35 | 36 | * install the package to display package support information for 37 | * cd into the directory which contains the root package 38 | * execute `npx @pkgjs/support show` 39 | 40 | For example once node.js and the package support tool are installed to show 41 | the package support for a module (the support module itself in this example): 42 | 43 | ```shell 44 | npm install @pkgjs/support 45 | cd node_modules/@pkgjs/support 46 | npx @pkgjs/support show 47 | ``` 48 | 49 | with a stripped down version of the the output to make it more easily readable being: 50 | 51 | ```shell 52 | @pkgjs/support(0.0.2) - { "versions": [ { "version": "*", "target": { "node": "supported" }, "response": { "type": "time-permitting" }, "backing": { "hobby": "https://github.com/pkgjs/support" } } ] } 53 | @npmcli/arborist(0.0.0) - unknown 54 | @npmcli/installed-package-contents(1.0.5) - unknown 55 | npm-bundled(1.1.1) - unknown 56 | npm-normalize-package-bin(1.0.1) - unknown 57 | @npmcli/map-workspaces(0.0.0-pre.1) - unknown 58 | glob(7.1.6) - unknown 59 | fs.realpath(1.0.0) - unknown 60 | inflight(1.0.6) - unknown 61 | wrappy(1.0.2) - unknown 62 | 63 | ... 64 | 65 | y18n(4.0.0) - unknown 66 | yargs-parser(18.1.3) - unknown 67 | camelcase(5.3.1) - unknown 68 | ``` 69 | 70 | The command shows the support information for the tree of packages starting from the package being assessed. 71 | In this case it ONLY shows support info for the `support` package as the support information has not 72 | been added to any of the dependent packages yet. 73 | 74 | The support info shown is: 75 | 76 | ```shell 77 | @pkgjs/support(0.0.2) - { "versions": [ { "version": "*", "target": { "node": "supported" }, "response": { "type": "time-permitting" }, "backing": { "hobby": "https://github.com/pkgjs/support" } } ] } 78 | ``` 79 | 80 | For the rest of the modules it simply shows `unknown` as the packages do not yet provide it. 81 | 82 | The package support tool prefers support information which is available locally within the package after installation. 83 | This is to allow offline use. The documented best practices for adding support info are written to maximize 84 | the likelyhood that at reasonably up to date copy of the support information is provided as part of the npm 85 | install. 86 | 87 | If the consumer wishes to ignore the local information and always use the canonical version of the support information 88 | they can add the `--canonical` option to the command. Instead of using the local support info, if available, it will 89 | display the URL from which the canonical information can be retrieved. This is the same behavior when 90 | as when the package.json specifies that there is support info but it is not available in the npm package itself. 91 | 92 | For example: 93 | 94 | ``` 95 | npx @pkgjs/support show --canonical 96 | ``` 97 | 98 | 99 | ``` 100 | @pkgjs/support(0.0.2) - https://github.com/pkgjs/support/blob/HEAD/package-support.json 101 | @npmcli/arborist(0.0.0) - unknown 102 | @npmcli/installed-package-contents(1.0.5) - unknown 103 | npm-bundled(1.1.1) - unknown 104 | npm-normalize-package-bin(1.0.1) - unknown 105 | @npmcli/map-workspaces(0.0.0-pre.1) - unknown 106 | glob(7.1.6) - unknown 107 | fs.realpath(1.0.0) - unknown 108 | inflight(1.0.6) - unknown 109 | wrappy(1.0.2) - unknown 110 | 111 | ... 112 | 113 | y18n(4.0.0) - unknown 114 | yargs-parser(18.1.3) - unknown 115 | camelcase(5.3.1) - unknown 116 | ``` 117 | 118 | where the support info is listed as 119 | `https://github.com/pkgjs/support/blob/HEAD/package-support.json` 120 | 121 | The --canonical option does not automatically pull the remote information so that the 122 | consumer can choose to find the locations without automatically triggering a number of 123 | remote calls. 124 | 125 | If the consumer wants to have the canonical information pulled automatically they can 126 | add the `--fetch` option which will pull the remote support information when necessary. 127 | 128 | 129 | The following command/options will always show the most up to date package support information 130 | at the cost of fetching from remote sites. 131 | ``` 132 | npx @pkgjs/support show --canonical --fetch 133 | ``` 134 | 135 | `--fetch` can also be used without `--canonical` in which case the remote support 136 | information will only be pulled when it is not provided as part of the npm package. 137 | 138 | Local support information may be available locally but outside of the package itself. 139 | This may be the case if you are using mono-repo and sharing the support file. 140 | In this case, by default, the support tool will not read/display files outside of the 141 | package itself to avoid potential security issues. In order to allow the tool to display 142 | support info in these cases you can use the `--base-path` option to specify the top 143 | most root from which package support files can be read: 144 | 145 | ```shell 146 | npx @pkgjs/support --base-path=${cwd}/../.. show 147 | ``` 148 | 149 | In the case where the required base path is not specified, and the file is outside 150 | of the package, the tool will simply print the url from which the support information 151 | can be obtained versus displaying it. For example: 152 | 153 | ``` 154 | @pkgjs/support-show-local-escape-ok(0.0.1) - https://github.com/pkgjs/support/blob/HEAD/my-support-info.json 155 | ``` 156 | 157 | where the `support` entry was: 158 | 159 | ```json 160 | "support": "../../fixtures/my-support-info.json", 161 | ``` 162 | 163 | ## Package Maintainers 164 | 165 | Package maintainers want to add and manage the support information for their modules. 166 | 167 | [Integration into package.json](https://github.com/nodejs/package-maintenance/blob/HEAD/docs/PACKAGE-SUPPORT.md#integration-into-packagejson) 168 | explains the options for providing support info and what goes into the package.json for 169 | each case. 170 | 171 | In order to add support information a maintainer can use `create` command. 172 | 173 | `npx @pkgjs/support create` is run from the directory that contains the `package.json` for the package. 174 | It will ask few questions (e.g. what Node.js version your package support or how quickly you are able to respond to issues) 175 | in order to build proper `package-support.json` file. 176 | This command can also build [`backing`](https://github.com/nodejs/package-maintenance/blob/HEAD/docs/PACKAGE-SUPPORT.md#support-backing) field based on your `.github/FUNDING.yml` file or `"funding"` field from `package.json`. 177 | 178 | `create` command will create `package-support.json` file in current working directory for you 179 | and will update `package.json` in order to set `"support: true"` field. 180 | 181 | `create` command has `-y|--yes` flag which does pretty much the same as `npm init -y` but with package support info. 182 | It will create `package-support.json` file with default commonly-used values. 183 | This can be used in case you want to get some basic scaffolding and edit file manually. 184 | 185 | ```shell 186 | npx @pkgjs/support create -y 187 | ``` 188 | 189 | In case package support information was added manually - `@pkgjs/support` also provides 190 | ability to validate this infomation automatically according to official schema. 191 | 192 | The `validate` command checks that both the information added to the package.json 193 | and the file containing the support info (package-support.json by default) is valid. 194 | 195 | `npx @pkgjs/support validate` is run from the directory that contains the `package.json` for the package. 196 | Depending the how the `support` section in the package.json is configured validate will: 197 | 198 | * validate the format of the `support` section in the package.json conforms to the 199 | documentation in [Integration into package.json](https://github.com/nodejs/package-maintenance/blob/HEAD/docs/PACKAGE-SUPPORT.md#integration-into-packagejson) 200 | * calculate the file which contains the support info 201 | * if the file is available locally, use that data unless the `--canonical` 202 | option was specified. 203 | * if the file is not available locally or `--canonical` was specified 204 | * if --fetch was provided as an option, fetch the file and use that data 205 | * otherwise simply print that the file was not resolved and the url from 206 | where it can be retrieved. 207 | 208 | If both the entry in the package.json and the contents of the file with the package support 209 | information is validate you'll see the following output: 210 | 211 | ```shell 212 | Your support information is valid! 213 | ``` 214 | 215 | If the support information is not available locally or you have specified 216 | `--canonical` without `--fetch` you'll see something like: 217 | 218 | ```shell 219 | support info not resolved: https://github.com/pkgjs/support/blob/HEAD/package-support.json 220 | ``` 221 | 222 | in this case the file is local to the package, but --canonical was specified. The same 223 | would be shown if the info in the package.json file pointed to a file a different github 224 | repository. 225 | 226 | You might also see this if the file with the support information is outside of the 227 | the package itself, but still available locally. This may be the case if you 228 | are using mono-repo and sharing the support file. An example would be: 229 | 230 | ```json 231 | "support": "../../fixtures/my-support-info.json", 232 | ``` 233 | 234 | This is the case because, by default, the support tool will not read/display files outside of the 235 | package itself in order to avoid potential security issues. In order to allow the tool to validate 236 | support info in these cases you can use the `--base-path` option to specify the top 237 | most root from which package support files can be read: 238 | 239 | ```shell 240 | npx @pkgjs/support --base-path=${cwd}/../.. validate 241 | ``` 242 | -------------------------------------------------------------------------------- /examples/basic.json: -------------------------------------------------------------------------------- 1 | { 2 | "versions": [{ 3 | "version": "*", 4 | "target": { 5 | "node": "lts" 6 | }, 7 | "response": { 8 | "type": "time-permitting" 9 | }, 10 | "backing": { 11 | "hobby": "https://github.com/pkgjs/support" 12 | } 13 | }] 14 | } 15 | -------------------------------------------------------------------------------- /examples/complex.json: -------------------------------------------------------------------------------- 1 | { 2 | "versions": [{ 3 | "version": "<1", 4 | "target": { 5 | "node": "none" 6 | }, 7 | "response": { 8 | "type": "none" 9 | } 10 | }, { 11 | "version": "^1.0.0", 12 | "target": { 13 | "node": ">=8 <10" 14 | }, 15 | "response": [{ 16 | "type": "time-permitting", 17 | "paid": false, 18 | "contact": { 19 | "name": "Volunteers", 20 | "url": "https://github.com/pkgjs/support" 21 | } 22 | }, { 23 | "type": "regular-2", 24 | "paid": true, 25 | "contact": [{ 26 | "name": "Premium Support", 27 | "email": "wes@wesleytodd.com" 28 | }, { 29 | "name": "Premium Support", 30 | "url": "https://github.com/pkgjs/support" 31 | }] 32 | }] 33 | }, { 34 | "version": ">2.0.0", 35 | "target": { 36 | "node": "lts" 37 | }, 38 | "response": [{ 39 | "type": "time-permitting", 40 | "paid": false, 41 | "contact": { 42 | "name": "Volunteers", 43 | "url": "https://github.com/pkgjs/support" 44 | } 45 | }, { 46 | "type": "regular-1", 47 | "paid": true, 48 | "contact": [{ 49 | "name": "Premium Support", 50 | "email": "wes@wesleytodd.com" 51 | }, { 52 | "name": "Premium Support", 53 | "url": "https://github.com/pkgjs/support" 54 | }] 55 | }], 56 | "backing": { 57 | "hobby": "https://github.com/pkgjs/support" 58 | } 59 | }] 60 | } 61 | -------------------------------------------------------------------------------- /examples/minimum.json: -------------------------------------------------------------------------------- 1 | { 2 | "versions": [{ 3 | "version": "*" 4 | }] 5 | } 6 | -------------------------------------------------------------------------------- /index.js: -------------------------------------------------------------------------------- 1 | 'use strict'; 2 | const path = require('path'); 3 | const fs = require('fs'); 4 | const normalizeUrl = require('normalize-url'); 5 | const Ajv = require('ajv'); 6 | const got = require('got'); 7 | const betterAjvErrors = require('better-ajv-errors'); 8 | const create = require('./lib/cli/create'); 9 | 10 | let ajv; 11 | let compiledSchema; 12 | let ajvElement; 13 | let compiledSchemaElement; 14 | 15 | const schema = module.exports.schema = require('./schema.json'); 16 | const supportElementSchema = module.exports.schema = require('./support-element-schema.json'); 17 | 18 | module.exports.defaultPackageSupport = 'package-support.json'; 19 | module.exports.create = create; 20 | 21 | function getBetterAjvErrorsOptions (cli) { 22 | const options = { format: 'js' }; 23 | if (cli === true) { 24 | options.format = 'cli'; 25 | } 26 | return options; 27 | } 28 | 29 | module.exports.validateSupportElement = (obj, cli = false) => { 30 | if (!ajvElement) { 31 | ajvElement = new Ajv({ jsonPointers: true }); 32 | compiledSchemaElement = ajvElement.compile(supportElementSchema); 33 | } 34 | 35 | const validates = compiledSchemaElement(obj); 36 | if (!validates) { 37 | const err = new Error('Validation Failed'); 38 | err.validationErrors = compiledSchemaElement.errors; 39 | err.prettyValidationErrors = betterAjvErrors(supportElementSchema, obj, compiledSchemaElement.errors, getBetterAjvErrorsOptions(cli)); 40 | err.validationSchema = compiledSchemaElement.schema; 41 | throw err; 42 | } 43 | return true; 44 | }; 45 | 46 | module.exports.validate = (obj, cli = false) => { 47 | if (!ajv) { 48 | ajv = new Ajv({ jsonPointers: true }); 49 | compiledSchema = ajv.compile(schema); 50 | } 51 | 52 | const validates = compiledSchema(obj); 53 | if (!validates) { 54 | const err = new Error('Validation Failed'); 55 | err.validationErrors = compiledSchema.errors; 56 | err.prettyValidationErrors = betterAjvErrors(schema, obj, compiledSchema.errors, getBetterAjvErrorsOptions(cli)); 57 | err.validationSchema = compiledSchema.schema; 58 | throw err; 59 | } 60 | return true; 61 | }; 62 | 63 | // extract the URL for the support info from the pkg info 64 | module.exports.getRemoteSupportInfoUrl = (repository, supportPath) => { 65 | const gitHubInitialPath = '/blob/HEAD/'; 66 | 67 | if (repository && (repository.type === 'git')) { 68 | const directory = repository.directory || ''; 69 | let remoteURL = repository.url; 70 | const trailerLocation = remoteURL.indexOf('.git'); 71 | if (trailerLocation >= 0) { 72 | remoteURL = remoteURL.substring(0, trailerLocation) + 73 | gitHubInitialPath + '/' + directory + 74 | '/' + supportPath; 75 | } 76 | return normalizeUrl(remoteURL); 77 | } else { 78 | return 'unknown'; 79 | } 80 | }; 81 | 82 | // the path should not try to escape the root as it 83 | // is specified to be a relative path 84 | module.exports.sanitizePath = (basePath, inputPath, basePathOverride) => { 85 | const effectiveBasePath = path.normalize(basePathOverride || basePath); 86 | const candidatePath = path.join(basePath, inputPath); 87 | let ret = path.basename(inputPath); 88 | if (candidatePath.indexOf(effectiveBasePath) === 0) { 89 | // inputPath did not try to escape 90 | ret = inputPath; 91 | } 92 | return ret; 93 | }; 94 | 95 | async function resolveSupportInfo (supportInfo, fetchCanonical) { 96 | supportInfo.resolved = false; 97 | if (fetchCanonical) { 98 | const url = normalizeUrl(supportInfo.url 99 | .replace('blob', '') 100 | .replace('github.com', 'raw.githubusercontent.com')); 101 | try { 102 | const result = await got(url); 103 | supportInfo.contents = result.body; 104 | supportInfo.resolved = true; 105 | } catch (e) { 106 | supportInfo.error = e; 107 | } 108 | } 109 | } 110 | 111 | module.exports.getSupportData = async (pkg, pkgPath, preferCanonical, basePathOverride, fetchCanonical) => { 112 | const supportInfo = { contents: 'unknown', url: '', resolved: true }; 113 | if (pkg.support) { 114 | if ((pkg.support === true) || (typeof pkg.support === 'string')) { 115 | const supportInfoName = (pkg.support === true) 116 | ? module.exports.defaultPackageSupport : module.exports.sanitizePath(pkgPath, pkg.support, basePathOverride); 117 | const localPath = path.join(pkgPath, supportInfoName); 118 | if (!preferCanonical && fs.existsSync(localPath)) { 119 | supportInfo.contents = fs.readFileSync(localPath); 120 | supportInfo.resolved = true; 121 | } else { 122 | supportInfo.url = module.exports.getRemoteSupportInfoUrl(pkg.repository, supportInfoName); 123 | await resolveSupportInfo(supportInfo, fetchCanonical); 124 | } 125 | } else if (typeof pkg.support === 'object') { 126 | const supportInfoName = pkg.support.path ? pkg.support.path : module.exports.defaultPackageSupport; 127 | supportInfo.url = module.exports.getRemoteSupportInfoUrl(pkg.support.repository, supportInfoName); 128 | await resolveSupportInfo(supportInfo, fetchCanonical); 129 | } 130 | } 131 | return supportInfo; 132 | }; 133 | 134 | /** 135 | * Returns list of target Node.js versions for package-support.json file 136 | */ 137 | module.exports.getNodeJsTargetVersionsList = () => { 138 | return [ 139 | 'abandoned', 140 | 'none', 141 | 'all', 142 | 'lts', 143 | 'active', 144 | 'lts_active', 145 | 'lts_latest', 146 | 'supported', 147 | 'current' 148 | ]; 149 | }; 150 | 151 | /** 152 | * Returns list of response types for package-support.json file 153 | */ 154 | module.exports.getSupportResponseTypesList = () => { 155 | const schemaOptions = [ 156 | 'none', 157 | 'time-permitting', 158 | '24-7' 159 | ]; 160 | 161 | for (let daysForResponse = 1; daysForResponse <= 7; daysForResponse++) { 162 | schemaOptions.push(`regular-${daysForResponse}`); 163 | } 164 | 165 | return schemaOptions; 166 | }; 167 | -------------------------------------------------------------------------------- /lib/cli/commands/badges.js: -------------------------------------------------------------------------------- 1 | 'use strict'; 2 | module.exports = function (opts) { 3 | return { 4 | command: 'badges', 5 | desc: 'Output badges markdown based on support', 6 | builder: function (yargs) { 7 | return yargs; 8 | }, 9 | handler: function (argv) { 10 | argv.log.info('badges'); 11 | } 12 | }; 13 | }; 14 | -------------------------------------------------------------------------------- /lib/cli/commands/create.js: -------------------------------------------------------------------------------- 1 | 'use strict'; 2 | const support = require('../../../index.js'); 3 | 4 | module.exports = function (opts) { 5 | return { 6 | command: 'create', 7 | desc: 'Setup a support declaration for a package', 8 | builder: function (yargs) { 9 | return yargs 10 | .option('yes', { 11 | desc: 'Apply default values', 12 | type: 'boolean', 13 | alias: 'y' 14 | }); 15 | }, 16 | handler: async function (argv) { 17 | try { 18 | await support.create(argv.y); 19 | console.log('Support info created'); 20 | } catch (error) { 21 | console.error(error.message); 22 | } 23 | } 24 | }; 25 | }; 26 | -------------------------------------------------------------------------------- /lib/cli/commands/show.js: -------------------------------------------------------------------------------- 1 | 'use strict'; 2 | const support = require('../../../index.js'); 3 | const Arborist = require('@npmcli/arborist'); 4 | const printed = {}; 5 | 6 | // print out the information for a module and its 7 | // children 8 | async function printModule (module, depth, argv) { 9 | const pkg = module.package; 10 | const moduleInfo = `${pkg.name}(${pkg.version})`; 11 | 12 | const supportInfo = await support.getSupportData(pkg, 13 | module.path, 14 | argv.canonical, 15 | argv['base-path'], 16 | argv.fetch); 17 | if (supportInfo.resolved) { 18 | const flattenedSupportInfo = supportInfo.contents.toString().replace(/\n/g, '').replace(/\s+/g, ' '); 19 | console.log(`${' '.repeat(2 * (depth + 1))}${moduleInfo} - ${flattenedSupportInfo}`); 20 | } else if (supportInfo.error) { 21 | console.error(`${' '.repeat(2 * (depth + 1))}${moduleInfo} - failed to fetch - ${supportInfo.url}`); 22 | } else { 23 | console.log(`${' '.repeat(2 * (depth + 1))}${moduleInfo} - ${supportInfo.url}`); 24 | } 25 | 26 | // avoid printing children of already printed module in current branch 27 | if (pkg.name in printed && depth > printed[pkg.name]) { 28 | return; 29 | } 30 | printed[pkg.name] = depth; 31 | 32 | // sort child modules 33 | module.edgesOut = new Map([...module.edgesOut.entries()].sort()); 34 | 35 | // print info for all of the child modules 36 | for (const child of module.edgesOut.values()) { 37 | await printModule(child.to, depth + 1, argv); 38 | } 39 | } 40 | 41 | module.exports = function (opts) { 42 | return { 43 | command: 'show', 44 | desc: 'Show support information', 45 | builder: function (yargs) { 46 | return yargs; 47 | }, 48 | handler: function (argv) { 49 | const arb = new Arborist(); 50 | arb.buildIdealTree({ legacyBundling: true }).then(root => { 51 | printModule(root, 0, argv).then(() => {}, (e) => { 52 | argv.log.error('show failed: ', e); 53 | }); 54 | }); 55 | } 56 | }; 57 | }; 58 | -------------------------------------------------------------------------------- /lib/cli/commands/validate.js: -------------------------------------------------------------------------------- 1 | 'use strict'; 2 | 3 | const fs = require('fs-extra'); 4 | const path = require('path'); 5 | const support = require('../../../index.js'); 6 | 7 | const errorInSupportElement = 'Error in support element in package.json'; 8 | 9 | module.exports = function (opts) { 10 | return { 11 | command: 'validate', 12 | desc: 'Validate support information schema', 13 | builder: function (yargs) { 14 | return yargs; 15 | }, 16 | handler: async function (argv) { 17 | let userPackageJson; 18 | try { 19 | userPackageJson = await fs.readJSON(path.join(process.cwd(), 'package.json')); 20 | } catch (error) { 21 | argv.log.error(error); 22 | return; 23 | } 24 | 25 | let supportData = userPackageJson.support; 26 | if ((supportData === false) || supportData) { 27 | // first validate that the supportData is correct 28 | if ((supportData !== true) && !(typeof supportData === 'string') && !(supportData instanceof Object)) { 29 | console.error(errorInSupportElement); 30 | console.error('Support element should either be true or an Object matching the required schema'); 31 | return; 32 | } 33 | 34 | try { 35 | support.validateSupportElement({ support: supportData }, true); 36 | } catch (e) { 37 | console.error(errorInSupportElement); 38 | console.error(e.prettyValidationErrors); 39 | return; 40 | } 41 | 42 | // support element was ok so validate the data itself 43 | supportData = await support.getSupportData(userPackageJson, 44 | path.join(process.cwd()), 45 | argv.canonical, 46 | argv['base-path'], 47 | argv.fetch); 48 | if (supportData.resolved) { 49 | try { 50 | const supportDataJSON = JSON.parse(supportData.contents); 51 | try { 52 | const result = support.validate(supportDataJSON, true); 53 | if (result) { 54 | console.log('Your support information is valid!'); 55 | return; 56 | } 57 | } catch (e) { 58 | console.error('Error in support JSON'); 59 | console.error(e.prettyValidationErrors); 60 | } 61 | } catch (e) { 62 | console.error('Your support information is not properly formed'); 63 | console.error(e.message); 64 | } 65 | } else { 66 | console.error('support info not resolved: ' + supportData.url); 67 | } 68 | } else { 69 | console.error('no support info'); 70 | } 71 | } 72 | }; 73 | }; 74 | -------------------------------------------------------------------------------- /lib/cli/create/create-support-template.json: -------------------------------------------------------------------------------- 1 | { 2 | "versions": [ 3 | { 4 | "version": "*", 5 | "target": { 6 | "node": "" 7 | }, 8 | "response": { 9 | "type": "" 10 | }, 11 | "backing": {} 12 | } 13 | ] 14 | } 15 | -------------------------------------------------------------------------------- /lib/cli/create/index.js: -------------------------------------------------------------------------------- 1 | /** 2 | module "create" - containing 'support create' command functionality 3 | **/ 4 | 'use strict'; 5 | 6 | const jsonFile = require('json-file-plus'); 7 | const path = require('path'); 8 | const support = require('../../../index.js'); 9 | const inquirer = require('inquirer'); 10 | const supportFileTemplate = require('./create-support-template.json'); 11 | const yaml = require('js-yaml'); 12 | const fs = require('fs-extra'); 13 | 14 | // list of values for backing field 15 | const backingStatusesEnum = Object.freeze({ 16 | NONE: 'none', 17 | HOBBY: 'hobby', 18 | GET_FROM_FUNDING_YML: 'get_from_funding', 19 | GET_FROM_FUNDING_PACKAGE_JSON: 'get_from_funding_package_json' 20 | }); 21 | 22 | /** 23 | * Create command handler. Interacts with user for building "package-support.json" 24 | * 25 | * Accepts boolean param "useDefaultValues" - will skip interaction with user 26 | * and use default values. 27 | */ 28 | module.exports = async function create (useDefaultValues) { 29 | // check package.json for support info presence 30 | const supportInfoFound = await isSupportInfoExist(); 31 | if (supportInfoFound) { 32 | throw new Error('Support info already present in package.json'); 33 | } 34 | 35 | // default 36 | let responses = { 37 | targetVersion: 'lts', 38 | responseTime: 'time-permitting', 39 | backingType: backingStatusesEnum.HOBBY 40 | }; 41 | 42 | if (!useDefaultValues) { 43 | // if no support info exist - collect data from user 44 | responses = await inquirer.prompt(getInteractiveQuestions()); 45 | } 46 | 47 | const resultSupportObject = await prepareSupportObject(responses); 48 | 49 | await writeGeneratedSupportInfo(resultSupportObject); 50 | }; 51 | 52 | /** 53 | * Returns config array for "inquirer" package 54 | */ 55 | const getInteractiveQuestions = module.exports.getInteractiveQuestions = () => { 56 | const responseTypes = support.getSupportResponseTypesList(); 57 | const defaultResponseTypeIndex = responseTypes.indexOf('time-permitting'); 58 | 59 | return [ 60 | { 61 | type: 'list', 62 | name: 'targetVersion', 63 | message: 'What versions of Node.js does your package support?', 64 | choices: support.getNodeJsTargetVersionsList() 65 | }, 66 | { 67 | type: 'list', 68 | name: 'responseTime', 69 | message: 'How quickly you are able to respond to issues?', 70 | choices: responseTypes, 71 | default: defaultResponseTypeIndex 72 | }, 73 | { 74 | type: 'list', 75 | name: 'backingType', 76 | message: 'What type of backing your package accepts?', 77 | choices: [ 78 | backingStatusesEnum.NONE, 79 | backingStatusesEnum.HOBBY, 80 | { 81 | name: 'Get values from .github/FUNDING.yml', 82 | value: backingStatusesEnum.GET_FROM_FUNDING_YML 83 | }, 84 | { 85 | name: 'Get values from package.json funding field', 86 | value: backingStatusesEnum.GET_FROM_FUNDING_PACKAGE_JSON 87 | } 88 | ], 89 | default: 1 90 | } 91 | ]; 92 | }; 93 | 94 | /** 95 | * Returns "support" field value from package.json 96 | */ 97 | const isSupportInfoExist = module.exports.isSupportInfoExist = async () => { 98 | const packageJsonFile = await getPackageJsonFile(); 99 | const supportValue = await packageJsonFile.get('support'); 100 | 101 | return !!supportValue; 102 | }; 103 | 104 | /** 105 | * Returns prepared support object based on provided answers from user 106 | */ 107 | const prepareSupportObject = module.exports.prepareSupportObject = async (supportValues) => { 108 | const version = supportFileTemplate.versions[0]; 109 | 110 | // set target Node.js version 111 | version.target.node = supportValues.targetVersion; 112 | // set support response time 113 | version.response.type = supportValues.responseTime; 114 | 115 | if (supportValues.backingType === backingStatusesEnum.GET_FROM_FUNDING_YML) { 116 | // build backing object based on FUNDING.yml 117 | version.backing.donations = await buildBackingFromFundingYml(); 118 | } else if (supportValues.backingType === backingStatusesEnum.GET_FROM_FUNDING_PACKAGE_JSON) { 119 | // build backing object based on funding field in package.json 120 | version.backing.donations = await buildBackingFromPackageJson(); 121 | } else { 122 | // use value from user 123 | version.backing[supportValues.backingType] = ''; 124 | } 125 | 126 | return supportFileTemplate; 127 | }; 128 | 129 | /** 130 | * Returns array of backing URLs based on .github/FUNDING.yml 131 | */ 132 | const buildBackingFromFundingYml = module.exports.buildBackingFromFundingYml = async () => { 133 | try { 134 | const fundingPlatformsURLs = { 135 | github: 'https://github.com/', 136 | patreon: 'https://www.patreon.com/', 137 | open_collective: 'https://opencollective.com/', 138 | ko_fi: 'https://ko-fi.com/', 139 | tidelift: 'https://tidelift.com/funding/github/', 140 | community_bridge: 'https://funding.communitybridge.org/projects/', 141 | liberapay: 'https://liberapay.com/', 142 | issuehunt: 'https://issuehunt.io/r/', 143 | otechie: 'https://otechie.com/', 144 | custom: '' 145 | }; 146 | const backingResult = []; 147 | const fundingPath = path.join(process.cwd(), '.github', 'FUNDING.yml'); 148 | const fundingYml = yaml.load(await fs.readFile(fundingPath, 'utf8')); 149 | 150 | const platformsAdded = Object.keys(fundingYml); 151 | 152 | for (const platform of platformsAdded) { 153 | if (fundingYml[platform]) { 154 | const username = fundingYml[platform]; 155 | 156 | if (Array.isArray(username)) { 157 | username.forEach(el => { 158 | backingResult.push(`${fundingPlatformsURLs[platform]}${el}`); 159 | }); 160 | } else { 161 | backingResult.push(`${fundingPlatformsURLs[platform]}${username}`); 162 | } 163 | } 164 | } 165 | 166 | return backingResult; 167 | } catch (e) { 168 | throw new Error(`Generating backing from FUNDING.yml failed - ${e.message}`); 169 | } 170 | }; 171 | 172 | /** 173 | * Returns array of backing URLs based on "funding" field from package.json 174 | */ 175 | const buildBackingFromPackageJson = module.exports.buildBackingFromPackageJson = async () => { 176 | try { 177 | const packageJsonFile = await getPackageJsonFile(); 178 | const funding = await packageJsonFile.get('funding'); 179 | const supportBackingResult = []; 180 | 181 | if (!funding) { 182 | throw new Error('Funding field not found in package.json'); 183 | } 184 | 185 | const processFundingValue = fundingValue => { 186 | let fundingUrl = ''; 187 | 188 | if (typeof fundingValue === 'string') { 189 | fundingUrl = fundingValue; 190 | } else if (typeof fundingValue === 'object' && fundingValue.url) { 191 | fundingUrl = fundingValue.url; 192 | } 193 | 194 | if (fundingUrl) { 195 | supportBackingResult.push(fundingUrl); 196 | } 197 | }; 198 | 199 | if (Array.isArray(funding)) { 200 | funding.forEach(el => { 201 | processFundingValue(el); 202 | }); 203 | } else { 204 | processFundingValue(funding); 205 | } 206 | 207 | return supportBackingResult; 208 | } catch (e) { 209 | throw new Error(`Generating backing from package.json failed - ${e.message}`); 210 | } 211 | }; 212 | 213 | /** 214 | * Writes provided support object into 'package-support.json' file 215 | * and update "support" field to true in 'package.json' 216 | */ 217 | const writeGeneratedSupportInfo = module.exports.writeGeneratedSupportInfo = async (supportObj) => { 218 | try { 219 | const packageJsonFile = await getPackageJsonFile(); 220 | 221 | const writeToPackageJson = () => { 222 | packageJsonFile.set({ 223 | support: true 224 | }); 225 | 226 | return packageJsonFile.save(); 227 | }; 228 | 229 | const writeSupportFile = () => { 230 | return fs.writeFile( 231 | path.join(process.cwd(), 'package-support.json'), 232 | JSON.stringify(supportObj, null, 2), 233 | 'utf-8' 234 | ); 235 | }; 236 | 237 | return Promise.all([ 238 | writeToPackageJson(), 239 | writeSupportFile() 240 | ]); 241 | } catch (e) { 242 | throw new Error(`Writing support info failed - ${e.message}`); 243 | } 244 | }; 245 | 246 | /** 247 | * Returns jsonFile instance for package.json 248 | */ 249 | async function getPackageJsonFile () { 250 | const packageJsonPath = path.join(process.cwd(), 'package.json'); 251 | return await jsonFile(packageJsonPath); 252 | } 253 | -------------------------------------------------------------------------------- /lib/cli/index.js: -------------------------------------------------------------------------------- 1 | 'use strict'; 2 | const yargs = require('yargs/yargs'); 3 | const path = require('path'); 4 | const { Loggerr } = require('loggerr'); 5 | 6 | module.exports = (options = {}) => { 7 | // Defaults cli configuration 8 | const opts = Object.assign({ 9 | commandsDir: path.join(__dirname, 'commands'), 10 | usage: '$0 [options]', 11 | silentLevel: -1, 12 | verboseLevel: 'info', 13 | logLevel: 'error', 14 | logger: (level) => { 15 | return new Loggerr({ 16 | formatter: 'cli', 17 | level: level 18 | }); 19 | }, 20 | fail: (msg) => { 21 | console.log(); 22 | cli.showHelp(); 23 | process.exit(1); 24 | } 25 | }, options); 26 | 27 | // The log instance 28 | const log = opts.logger(opts.logLevel); 29 | 30 | // Setup yargs cli instance 31 | const cli = yargs() 32 | 33 | // Log related flags 34 | .option('log-level', { 35 | alias: 'l', 36 | describe: 'Set the log level', 37 | type: 'string', 38 | group: 'Logging:', 39 | defaultDescription: opts.logLevel 40 | }) 41 | .option('silent', { 42 | alias: 'S', 43 | describe: 'Suppress all output', 44 | type: 'boolean', 45 | group: 'Logging:' 46 | }) 47 | .option('verbose', { 48 | alias: 'v', 49 | describe: `Verbose output (alias of --log-level=${opts.verboseLevel})`, 50 | type: 'boolean', 51 | group: 'Logging:' 52 | }) 53 | .conflicts({ 54 | verbose: 'silent', 55 | silent: 'verbose', 56 | 'log-level': ['silent', 'verbose'] 57 | }) 58 | .option('canonical', { 59 | describe: 'Use canonical support info even when local info is available', 60 | type: 'boolean', 61 | group: 'preferences' 62 | }) 63 | .option('fetch', { 64 | describe: 'Fetch canonical support info from remote repositories when necessary', 65 | type: 'boolean', 66 | group: 'preferences' 67 | }) 68 | .option('base-path', { 69 | describe: 'Set top most directory from which local support info files can be read. Defaults to same directory in which package.json is located.', 70 | type: 'string', 71 | group: 'preferences' 72 | }) 73 | 74 | .middleware([ 75 | // Log setup 76 | (argv) => { 77 | if (argv.silent) { 78 | argv.logLevel = opts.silentLevel; 79 | } else if (argv.verbose) { 80 | argv.logLevel = opts.verboseLevel; 81 | } 82 | log.setLevel(argv.logLevel); 83 | argv.log = log; 84 | } 85 | ]) 86 | 87 | // ensure we get an error if there is no command 88 | .demandCommand(1, 'You must specify the command to run') 89 | 90 | // ensure we get an error if we get an unrecognized command 91 | .strictCommands(true) 92 | 93 | // ensure we only allow known options 94 | .strict(true) 95 | 96 | .commandDir(opts.commandsDir, { 97 | visit: (mod) => typeof mod === 'function' ? mod(opts) : mod 98 | }) 99 | .usage(opts.usage); 100 | 101 | cli.wrap(Math.min(cli.terminalWidth(), 120)); 102 | 103 | // on fail callback 104 | if (typeof opts.fail === 'function') { 105 | cli.fail(opts.fail); 106 | } 107 | 108 | return (argv) => cli.parse(argv); 109 | }; 110 | -------------------------------------------------------------------------------- /package-support.json: -------------------------------------------------------------------------------- 1 | { 2 | "versions": [ 3 | { 4 | "version": "*", 5 | "target": { 6 | "node": "supported" 7 | }, 8 | "response": { 9 | "type": "time-permitting" 10 | }, 11 | "backing": { 12 | "hobby": "https://github.com/pkgjs/support" 13 | } 14 | } 15 | ] 16 | } 17 | -------------------------------------------------------------------------------- /package.json: -------------------------------------------------------------------------------- 1 | { 2 | "name": "@pkgjs/support", 3 | "version": "0.0.6", 4 | "description": "Package support information (see: https://github.com/nodejs/package-maintenance/pull/220)", 5 | "author": "Wes Todd ", 6 | "support": true, 7 | "keywords": [ 8 | "support", 9 | "package maintenance", 10 | "sustainability" 11 | ], 12 | "license": "MIT", 13 | "main": "index.js", 14 | "repository": { 15 | "type": "git", 16 | "url": "https://github.com/pkgjs/support.git" 17 | }, 18 | "bin": { 19 | "support": "./bin/support" 20 | }, 21 | "scripts": { 22 | "pretest": "eslint --ignore-path .gitignore .", 23 | "test": "mocha --delay", 24 | "prepublishOnly": "npm test", 25 | "postpublish": "git push origin && git push origin --tags" 26 | }, 27 | "dependencies": { 28 | "@npmcli/arborist": "^0.0.0", 29 | "ajv": "^6.11.0", 30 | "better-ajv-errors": "^0.6.7", 31 | "fs-extra": "^8.1.0", 32 | "got": "^11.1.3", 33 | "inquirer": "^7.3.3", 34 | "js-yaml": "^4.0.0", 35 | "json-file-plus": "^3.3.1", 36 | "loggerr": "^3.0.0-2", 37 | "normalize-url": "^5.0.0", 38 | "yargs": "^15.0.2" 39 | }, 40 | "devDependencies": { 41 | "eslint": "^7.5.0", 42 | "eslint-config-semistandard": "^15.0.1", 43 | "eslint-config-standard": "^14.1.1", 44 | "eslint-plugin-import": "^2.22.0", 45 | "eslint-plugin-node": "^11.1.0", 46 | "eslint-plugin-promise": "^4.2.1", 47 | "eslint-plugin-standard": "^4.0.1", 48 | "mocha": "^6.2.0" 49 | }, 50 | "engines": { 51 | "node": ">=10.19" 52 | } 53 | } 54 | -------------------------------------------------------------------------------- /schema.json: -------------------------------------------------------------------------------- 1 | { 2 | "$id": "https://raw.githubusercontent.com/pkgjs/support/main/schema.json", 3 | "$schema": "http://json-schema.org/draft-07/schema#", 4 | "title": "Package Support Information", 5 | 6 | "type": "object", 7 | "required": ["versions"], 8 | "properties": { 9 | "versions": { 10 | "type": "array", 11 | "minItems": 1, 12 | "items": { 13 | "$ref": "#SupportVersion" 14 | } 15 | } 16 | }, 17 | 18 | "definitions": { 19 | "SupportVersion": { 20 | "$id": "#SupportVersion", 21 | "type": "object", 22 | "required": ["version"], 23 | "properties": { 24 | "version": { "$ref": "#SemVerRange" }, 25 | "expires": { "type": "string", "format": "date-time" }, 26 | "target": { "$ref": "#SupportTarget" }, 27 | "response": { 28 | "oneOf": [{ 29 | "$ref": "#SupportResponse" 30 | }, { 31 | "type": "array", 32 | "minItems": 1, 33 | "items": { "$ref": "#SupportResponse" } 34 | }] 35 | }, 36 | "backing": { 37 | "oneOf": [{ 38 | "$ref": "#SupportBacking" 39 | }, { 40 | "type": "array", 41 | "minItems": 1, 42 | "items": { "$ref": "#SupportBacking" } 43 | }] 44 | } 45 | }, 46 | "additionalProperties": false 47 | }, 48 | 49 | "SemVerRange": { 50 | "$id": "#SemVerRange", 51 | "type": "string" 52 | }, 53 | 54 | "SupportTarget": { 55 | "$id": "#SupportTarget", 56 | "type": "object", 57 | "properties": { 58 | "node": { 59 | "oneOf": [ 60 | { "$ref": "#SupportTargetNodeVersion" }, 61 | { 62 | "type": "array", 63 | "minItems": 1, 64 | "items": { "$ref": "#SupportTargetNodeVersion" } 65 | } 66 | ] 67 | }, 68 | "additionalProperties": { 69 | "oneOf": [ 70 | { "type": "string" }, 71 | { 72 | "type": "array", 73 | "minItems": 1, 74 | "items": { "type": "string" } 75 | } 76 | ] 77 | } 78 | } 79 | }, 80 | 81 | "SupportTargetNodeVersion": { 82 | "$id": "#SupportTargetNodeVersion", 83 | "type": "string", 84 | "anyOf": [{ 85 | "type": "string", 86 | "enum": [ 87 | "abandoned", 88 | "none", 89 | "all", 90 | "lts", 91 | "active", 92 | "lts_active", 93 | "lts_latest", 94 | "supported", 95 | "current" 96 | ] 97 | }, { 98 | "$ref": "#SemVerRange" 99 | }] 100 | }, 101 | 102 | "SupportResponse": { 103 | "$id": "#SupportResponse", 104 | "type": "object", 105 | "properties": { 106 | "type": { 107 | "oneOf": [{ 108 | "type": "string", 109 | "enum": [ "none", "time-permitting", "24-7" ] 110 | }, { 111 | "type": "string", 112 | "pattern": "regular-[1-7]" 113 | }] 114 | }, 115 | "paid": { 116 | "type": "boolean" 117 | }, 118 | "contact": { 119 | "oneOf": [{ 120 | "$ref": "#SupportResponseContact" 121 | }, { 122 | "type": "array", 123 | "minItems": 1, 124 | "items": { "$ref": "#SupportResponseContact"} 125 | }] 126 | } 127 | } 128 | }, 129 | 130 | "SupportResponseContact": { 131 | "$id": "#SupportResponseContact", 132 | "type": "object", 133 | "required": ["name"], 134 | "properties": { 135 | "name": { "type": "string" }, 136 | "email": { "type": "string", "format": "email" }, 137 | "url": { "type": "string", "format": "uri" } 138 | } 139 | }, 140 | 141 | "SupportBacking": { 142 | "$id": "#SupportBacking", 143 | "type": "object", 144 | "properties": { 145 | "none": { "$ref": "#SupportBackingValue" }, 146 | "hobby": { "$ref": "#SupportBackingValue" }, 147 | "sponsored": { "$ref": "#SupportBackingValue" }, 148 | "bounty": { "$ref": "#SupportBackingValue" }, 149 | "project": { "$ref": "#SupportBackingValue" }, 150 | "foundation": { "$ref": "#SupportBackingValue" }, 151 | "company": { "$ref": "#SupportBackingValue" }, 152 | "commercial": { "$ref": "#SupportBackingValue" }, 153 | "paid-support": { "$ref": "#SupportBackingValue" }, 154 | "freemium": { "$ref": "#SupportBackingValue" }, 155 | "donations": { "$ref": "#SupportBackingValue" } 156 | } 157 | }, 158 | 159 | "SupportBackingValue": { 160 | "$id": "#SupportBackingValue", 161 | "oneOf": [{ 162 | "type": "string" 163 | }, { 164 | "type": "array", 165 | "minItems": 1, 166 | "items": { "type": "string" } 167 | }] 168 | } 169 | } 170 | } 171 | -------------------------------------------------------------------------------- /support-element-schema.json: -------------------------------------------------------------------------------- 1 | { 2 | "$id": "https://raw.githubusercontent.com/pkgjs/support/main/support-element-schema.json", 3 | "$schema": "http://json-schema.org/draft-07/schema#", 4 | "title": "Package Support Package.json element", 5 | 6 | "type": "object", 7 | "properties": { 8 | "support": { 9 | "oneOf": [{ 10 | "enum": [ true ] 11 | }, { 12 | "type": "string" 13 | }, { 14 | "type": "object", 15 | "required": ["repository"], 16 | "properties": { 17 | "repository": { "$ref": "#Repository" }, 18 | "path": { "type": "string" } 19 | }, 20 | "additionalProperties": false 21 | }] 22 | } 23 | }, 24 | 25 | "definitions": { 26 | "repository": { 27 | "$id": "#Repository", 28 | "type": "object", 29 | "required": ["type", "url"], 30 | "properties": { 31 | "type": { "enum": [ "git" ] }, 32 | "url": { "type": "string", "format": "uri" }, 33 | "directory": { "type": "string" } 34 | }, 35 | "additionalProperties": false 36 | } 37 | } 38 | } 39 | -------------------------------------------------------------------------------- /test/cli/create-on-existed-support/command: -------------------------------------------------------------------------------- 1 | create 2 | -------------------------------------------------------------------------------- /test/cli/create-on-existed-support/expected: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/pkgjs/support/81a010c3bcf0f88b7d915a9b562b1ff09d5d181d/test/cli/create-on-existed-support/expected -------------------------------------------------------------------------------- /test/cli/create-on-existed-support/expected-errors: -------------------------------------------------------------------------------- 1 | Support info already present in package.json 2 | -------------------------------------------------------------------------------- /test/cli/create-on-existed-support/package-support.json: -------------------------------------------------------------------------------- 1 | { 2 | "versions": [ 3 | { 4 | "version": "*", 5 | "target": { 6 | "node": "supported" 7 | }, 8 | "response": { 9 | "type": "time-permitting" 10 | }, 11 | "backing": { 12 | "hobby": "https://github.com/pkgjs/support" 13 | } 14 | } 15 | ] 16 | } 17 | -------------------------------------------------------------------------------- /test/cli/create-on-existed-support/package.json: -------------------------------------------------------------------------------- 1 | { 2 | "name": "@pkgjs/create-on-existed-support", 3 | "version": "0.0.1", 4 | "support": true, 5 | "repository": { 6 | "type": "git", 7 | "url": "https://github.com/pkgjs/support.git" 8 | } 9 | } 10 | -------------------------------------------------------------------------------- /test/cli/show-local-circular-dependency/command: -------------------------------------------------------------------------------- 1 | show 2 | -------------------------------------------------------------------------------- /test/cli/show-local-circular-dependency/expected: -------------------------------------------------------------------------------- 1 | @pkgjs/support-show-local(0.0.1) - { "versions": [ { "version": "*", "target": { "node": "supported" }, "response": { "type": "time-permitting" }, "backing": { "hobby": "https://github.com/pkgjs/support" } } ] } 2 | dep1(0.0.1) - { "versions": [ { "version": "*", "target": { "node": "supported" }, "response": { "type": "time-permitting" }, "backing": { "hobby": "https://github.com/pkgjs/support" } } ] } 3 | dep2(0.0.1) - { "versions": [ { "version": "*", "target": { "node": "supported" }, "response": { "type": "time-permitting" }, "backing": { "hobby": "https://github.com/pkgjs/support" } } ] } 4 | dep3(0.0.1) - { "versions": [ { "version": "*", "target": { "node": "supported" }, "response": { "type": "time-permitting" }, "backing": { "hobby": "https://github.com/pkgjs/support" } } ] } 5 | dep1(0.0.1) - { "versions": [ { "version": "*", "target": { "node": "supported" }, "response": { "type": "time-permitting" }, "backing": { "hobby": "https://github.com/pkgjs/support" } } ] } 6 | dep2(0.0.1) - { "versions": [ { "version": "*", "target": { "node": "supported" }, "response": { "type": "time-permitting" }, "backing": { "hobby": "https://github.com/pkgjs/support" } } ] } 7 | -------------------------------------------------------------------------------- /test/cli/show-local-circular-dependency/exptected: -------------------------------------------------------------------------------- 1 | @pkgjs/support-show-local(0.0.1) - { "versions": [ { "version": "*", "target": { "node": "supported" }, "response": { "type": "time-permitting" }, "backing": { "hobby": "https://github.com/pkgjs/support" } } ] } 2 | dep1(0.0.1) - { "versions": [ { "version": "*", "target": { "node": "supported" }, "response": { "type": "time-permitting" }, "backing": { "hobby": "https://github.com/pkgjs/support" } } ] } 3 | dep2(0.0.1) - { "versions": [ { "version": "*", "target": { "node": "supported" }, "response": { "type": "time-permitting" }, "backing": { "hobby": "https://github.com/pkgjs/support" } } ] } 4 | dep3(0.0.1) - { "versions": [ { "version": "*", "target": { "node": "supported" }, "response": { "type": "time-permitting" }, "backing": { "hobby": "https://github.com/pkgjs/support" } } ] } 5 | -------------------------------------------------------------------------------- /test/cli/show-local-circular-dependency/node_modules/dep1/package-support.json: -------------------------------------------------------------------------------- 1 | { 2 | "versions": [ 3 | { 4 | "version": "*", 5 | "target": { 6 | "node": "supported" 7 | }, 8 | "response": { 9 | "type": "time-permitting" 10 | }, 11 | "backing": { 12 | "hobby": "https://github.com/pkgjs/support" 13 | } 14 | } 15 | ] 16 | } 17 | -------------------------------------------------------------------------------- /test/cli/show-local-circular-dependency/node_modules/dep1/package.json: -------------------------------------------------------------------------------- 1 | { 2 | "name": "dep1", 3 | "version": "0.0.1", 4 | "support": true, 5 | "repository": { 6 | "type": "git", 7 | "url": "https://github.com/pkgjs/dep1.git" 8 | } 9 | } 10 | -------------------------------------------------------------------------------- /test/cli/show-local-circular-dependency/node_modules/dep2/package-support.json: -------------------------------------------------------------------------------- 1 | { 2 | "versions": [ 3 | { 4 | "version": "*", 5 | "target": { 6 | "node": "supported" 7 | }, 8 | "response": { 9 | "type": "time-permitting" 10 | }, 11 | "backing": { 12 | "hobby": "https://github.com/pkgjs/support" 13 | } 14 | } 15 | ] 16 | } 17 | -------------------------------------------------------------------------------- /test/cli/show-local-circular-dependency/node_modules/dep2/package.json: -------------------------------------------------------------------------------- 1 | { 2 | "name": "dep2", 3 | "version": "0.0.1", 4 | "support": true, 5 | "repository": { 6 | "type": "git", 7 | "url": "https://github.com/pkgjs/dep2.git" 8 | }, 9 | "dependencies": { 10 | "dep3": "^0.0.1" 11 | } 12 | } 13 | -------------------------------------------------------------------------------- /test/cli/show-local-circular-dependency/node_modules/dep3/package-support.json: -------------------------------------------------------------------------------- 1 | { 2 | "versions": [ 3 | { 4 | "version": "*", 5 | "target": { 6 | "node": "supported" 7 | }, 8 | "response": { 9 | "type": "time-permitting" 10 | }, 11 | "backing": { 12 | "hobby": "https://github.com/pkgjs/support" 13 | } 14 | } 15 | ] 16 | } 17 | -------------------------------------------------------------------------------- /test/cli/show-local-circular-dependency/node_modules/dep3/package.json: -------------------------------------------------------------------------------- 1 | { 2 | "name": "dep3", 3 | "version": "0.0.1", 4 | "support": true, 5 | "repository": { 6 | "type": "git", 7 | "url": "https://github.com/pkgjs/dep3.git" 8 | }, 9 | "dependencies": { 10 | "dep2": "^0.0.1", 11 | "dep1": "^0.0.1" 12 | } 13 | } 14 | -------------------------------------------------------------------------------- /test/cli/show-local-circular-dependency/package-support.json: -------------------------------------------------------------------------------- 1 | { 2 | "versions": [ 3 | { 4 | "version": "*", 5 | "target": { 6 | "node": "supported" 7 | }, 8 | "response": { 9 | "type": "time-permitting" 10 | }, 11 | "backing": { 12 | "hobby": "https://github.com/pkgjs/support" 13 | } 14 | } 15 | ] 16 | } 17 | -------------------------------------------------------------------------------- /test/cli/show-local-circular-dependency/package.json: -------------------------------------------------------------------------------- 1 | { 2 | "name": "@pkgjs/support-show-local", 3 | "version": "0.0.1", 4 | "support": true, 5 | "repository": { 6 | "type": "git", 7 | "url": "https://github.com/pkgjs/support.git" 8 | }, 9 | "dependencies": { 10 | "dep1": "^0.0.1", 11 | "dep2": "^0.0.1" 12 | } 13 | } 14 | -------------------------------------------------------------------------------- /test/cli/show-local-escape-ok/command: -------------------------------------------------------------------------------- 1 | show --base-path=${cwd}/../.. 2 | -------------------------------------------------------------------------------- /test/cli/show-local-escape-ok/expected: -------------------------------------------------------------------------------- 1 | @pkgjs/support-show-local-escape-ok(0.0.1) - { "versions": [ { "version": "*", "target": { "node": "supported" }, "response": { "type": "time-permitting" }, "backing": { "hobby": "https://github.com/pkgjs/support" } } ] } 2 | -------------------------------------------------------------------------------- /test/cli/show-local-escape-ok/package.json: -------------------------------------------------------------------------------- 1 | { 2 | "name": "@pkgjs/support-show-local-escape-ok", 3 | "version": "0.0.1", 4 | "support": "../../fixtures/my-support-info.json", 5 | "repository": { 6 | "type": "git", 7 | "url": "https://github.com/pkgjs/support.git" 8 | } 9 | } 10 | -------------------------------------------------------------------------------- /test/cli/show-local-escape/command: -------------------------------------------------------------------------------- 1 | show 2 | -------------------------------------------------------------------------------- /test/cli/show-local-escape/expected: -------------------------------------------------------------------------------- 1 | @pkgjs/support-show-local-escape(0.0.1) - https://github.com/pkgjs/support/blob/HEAD/my-support-info.json 2 | -------------------------------------------------------------------------------- /test/cli/show-local-escape/package.json: -------------------------------------------------------------------------------- 1 | { 2 | "name": "@pkgjs/support-show-local-escape", 3 | "version": "0.0.1", 4 | "support": "../fixtures/my-support-info.json", 5 | "repository": { 6 | "type": "git", 7 | "url": "https://github.com/pkgjs/support.git" 8 | } 9 | } 10 | -------------------------------------------------------------------------------- /test/cli/show-local-path1/command: -------------------------------------------------------------------------------- 1 | show 2 | -------------------------------------------------------------------------------- /test/cli/show-local-path1/expected: -------------------------------------------------------------------------------- 1 | @pkgjs/support-show-local-path1(0.0.1) - { "versions": [ { "version": "*", "target": { "node": "supported" }, "response": { "type": "time-permitting" }, "backing": { "hobby": "https://github.com/pkgjs/support" } } ] } 2 | -------------------------------------------------------------------------------- /test/cli/show-local-path1/my-support-info.json: -------------------------------------------------------------------------------- 1 | { 2 | "versions": [ 3 | { 4 | "version": "*", 5 | "target": { 6 | "node": "supported" 7 | }, 8 | "response": { 9 | "type": "time-permitting" 10 | }, 11 | "backing": { 12 | "hobby": "https://github.com/pkgjs/support" 13 | } 14 | } 15 | ] 16 | } 17 | -------------------------------------------------------------------------------- /test/cli/show-local-path1/package.json: -------------------------------------------------------------------------------- 1 | { 2 | "name": "@pkgjs/support-show-local-path1", 3 | "version": "0.0.1", 4 | "support": "./my-support-info.json", 5 | "repository": { 6 | "type": "git", 7 | "url": "https://github.com/pkgjs/support-show-local-path1.git" 8 | } 9 | } 10 | -------------------------------------------------------------------------------- /test/cli/show-local-path2/command: -------------------------------------------------------------------------------- 1 | show 2 | -------------------------------------------------------------------------------- /test/cli/show-local-path2/expected: -------------------------------------------------------------------------------- 1 | @pkgjs/show-local-path2(0.0.1) - https://github.com/pkgjs/show-local-path2/blob/HEAD/subdir/my-support-info.json 2 | -------------------------------------------------------------------------------- /test/cli/show-local-path2/package.json: -------------------------------------------------------------------------------- 1 | { 2 | "name": "@pkgjs/show-local-path2", 3 | "version": "0.0.1", 4 | "support": "./subdir/my-support-info.json", 5 | "repository": { 6 | "type": "git", 7 | "url": "https://github.com/pkgjs/show-local-path2.git" 8 | } 9 | } 10 | -------------------------------------------------------------------------------- /test/cli/show-local-path2/subdir1/my-support-info.json: -------------------------------------------------------------------------------- 1 | { 2 | "versions": [ 3 | { 4 | "version": "*", 5 | "target": { 6 | "node": "supported" 7 | }, 8 | "response": { 9 | "type": "time-permitting" 10 | }, 11 | "backing": { 12 | "hobby": "https://github.com/pkgjs/support" 13 | } 14 | } 15 | ] 16 | } 17 | -------------------------------------------------------------------------------- /test/cli/show-local-tree-flat/command: -------------------------------------------------------------------------------- 1 | show 2 | -------------------------------------------------------------------------------- /test/cli/show-local-tree-flat/expected: -------------------------------------------------------------------------------- 1 | @pkgjs/support-show-local(0.0.1) - { "versions": [ { "version": "*", "target": { "node": "supported" }, "response": { "type": "time-permitting" }, "backing": { "hobby": "https://github.com/pkgjs/support" } } ] } 2 | dep1(0.0.1) - { "versions": [ { "version": "*", "target": { "node": "supported" }, "response": { "type": "time-permitting" }, "backing": { "hobby": "https://github.com/pkgjs/support" } } ] } 3 | dep2(0.0.1) - { "versions": [ { "version": "*", "target": { "node": "supported" }, "response": { "type": "time-permitting" }, "backing": { "hobby": "https://github.com/pkgjs/support" } } ] } 4 | dep3(0.0.1) - { "versions": [ { "version": "*", "target": { "node": "supported" }, "response": { "type": "time-permitting" }, "backing": { "hobby": "https://github.com/pkgjs/support" } } ] } 5 | -------------------------------------------------------------------------------- /test/cli/show-local-tree-flat/exptected: -------------------------------------------------------------------------------- 1 | @pkgjs/support-show-local(0.0.1) - { "versions": [ { "version": "*", "target": { "node": "supported" }, "response": { "type": "time-permitting" }, "backing": { "hobby": "https://github.com/pkgjs/support" } } ] } 2 | dep1(0.0.1) - { "versions": [ { "version": "*", "target": { "node": "supported" }, "response": { "type": "time-permitting" }, "backing": { "hobby": "https://github.com/pkgjs/support" } } ] } 3 | dep2(0.0.1) - { "versions": [ { "version": "*", "target": { "node": "supported" }, "response": { "type": "time-permitting" }, "backing": { "hobby": "https://github.com/pkgjs/support" } } ] } 4 | dep3(0.0.1) - { "versions": [ { "version": "*", "target": { "node": "supported" }, "response": { "type": "time-permitting" }, "backing": { "hobby": "https://github.com/pkgjs/support" } } ] } 5 | -------------------------------------------------------------------------------- /test/cli/show-local-tree-flat/node_modules/dep1/package-support.json: -------------------------------------------------------------------------------- 1 | { 2 | "versions": [ 3 | { 4 | "version": "*", 5 | "target": { 6 | "node": "supported" 7 | }, 8 | "response": { 9 | "type": "time-permitting" 10 | }, 11 | "backing": { 12 | "hobby": "https://github.com/pkgjs/support" 13 | } 14 | } 15 | ] 16 | } 17 | -------------------------------------------------------------------------------- /test/cli/show-local-tree-flat/node_modules/dep1/package.json: -------------------------------------------------------------------------------- 1 | { 2 | "name": "dep1", 3 | "version": "0.0.1", 4 | "support": true, 5 | "repository": { 6 | "type": "git", 7 | "url": "https://github.com/pkgjs/dep1.git" 8 | } 9 | } 10 | -------------------------------------------------------------------------------- /test/cli/show-local-tree-flat/node_modules/dep2/package-support.json: -------------------------------------------------------------------------------- 1 | { 2 | "versions": [ 3 | { 4 | "version": "*", 5 | "target": { 6 | "node": "supported" 7 | }, 8 | "response": { 9 | "type": "time-permitting" 10 | }, 11 | "backing": { 12 | "hobby": "https://github.com/pkgjs/support" 13 | } 14 | } 15 | ] 16 | } 17 | -------------------------------------------------------------------------------- /test/cli/show-local-tree-flat/node_modules/dep2/package.json: -------------------------------------------------------------------------------- 1 | { 2 | "name": "dep2", 3 | "version": "0.0.1", 4 | "support": true, 5 | "repository": { 6 | "type": "git", 7 | "url": "https://github.com/pkgjs/dep2.git" 8 | }, 9 | "dependencies": { 10 | "dep3": "^0.0.1" 11 | } 12 | } 13 | -------------------------------------------------------------------------------- /test/cli/show-local-tree-flat/node_modules/dep3/package-support.json: -------------------------------------------------------------------------------- 1 | { 2 | "versions": [ 3 | { 4 | "version": "*", 5 | "target": { 6 | "node": "supported" 7 | }, 8 | "response": { 9 | "type": "time-permitting" 10 | }, 11 | "backing": { 12 | "hobby": "https://github.com/pkgjs/support" 13 | } 14 | } 15 | ] 16 | } 17 | -------------------------------------------------------------------------------- /test/cli/show-local-tree-flat/node_modules/dep3/package.json: -------------------------------------------------------------------------------- 1 | { 2 | "name": "dep3", 3 | "version": "0.0.1", 4 | "support": true, 5 | "repository": { 6 | "type": "git", 7 | "url": "https://github.com/pkgjs/dep3.git" 8 | } 9 | } 10 | -------------------------------------------------------------------------------- /test/cli/show-local-tree-flat/package-support.json: -------------------------------------------------------------------------------- 1 | { 2 | "versions": [ 3 | { 4 | "version": "*", 5 | "target": { 6 | "node": "supported" 7 | }, 8 | "response": { 9 | "type": "time-permitting" 10 | }, 11 | "backing": { 12 | "hobby": "https://github.com/pkgjs/support" 13 | } 14 | } 15 | ] 16 | } 17 | -------------------------------------------------------------------------------- /test/cli/show-local-tree-flat/package.json: -------------------------------------------------------------------------------- 1 | { 2 | "name": "@pkgjs/support-show-local", 3 | "version": "0.0.1", 4 | "support": true, 5 | "repository": { 6 | "type": "git", 7 | "url": "https://github.com/pkgjs/support.git" 8 | }, 9 | "dependencies": { 10 | "dep1": "^0.0.1", 11 | "dep2": "^0.0.1" 12 | } 13 | } 14 | -------------------------------------------------------------------------------- /test/cli/show-local-tree/command: -------------------------------------------------------------------------------- 1 | show 2 | -------------------------------------------------------------------------------- /test/cli/show-local-tree/expected: -------------------------------------------------------------------------------- 1 | @pkgjs/support-show-local(0.0.1) - { "versions": [ { "version": "*", "target": { "node": "supported" }, "response": { "type": "time-permitting" }, "backing": { "hobby": "https://github.com/pkgjs/support" } } ] } 2 | dep1(0.0.1) - { "versions": [ { "version": "*", "target": { "node": "supported" }, "response": { "type": "time-permitting" }, "backing": { "hobby": "https://github.com/pkgjs/support" } } ] } 3 | dep2(0.0.1) - { "versions": [ { "version": "*", "target": { "node": "supported" }, "response": { "type": "time-permitting" }, "backing": { "hobby": "https://github.com/pkgjs/support" } } ] } 4 | dep3(0.0.1) - { "versions": [ { "version": "*", "target": { "node": "supported" }, "response": { "type": "time-permitting" }, "backing": { "hobby": "https://github.com/pkgjs/support" } } ] } 5 | -------------------------------------------------------------------------------- /test/cli/show-local-tree/exptected: -------------------------------------------------------------------------------- 1 | @pkgjs/support-show-local(0.0.1) - { "versions": [ { "version": "*", "target": { "node": "supported" }, "response": { "type": "time-permitting" }, "backing": { "hobby": "https://github.com/pkgjs/support" } } ] } 2 | dep1(0.0.1) - { "versions": [ { "version": "*", "target": { "node": "supported" }, "response": { "type": "time-permitting" }, "backing": { "hobby": "https://github.com/pkgjs/support" } } ] } 3 | dep2(0.0.1) - { "versions": [ { "version": "*", "target": { "node": "supported" }, "response": { "type": "time-permitting" }, "backing": { "hobby": "https://github.com/pkgjs/support" } } ] } 4 | dep3(0.0.1) - { "versions": [ { "version": "*", "target": { "node": "supported" }, "response": { "type": "time-permitting" }, "backing": { "hobby": "https://github.com/pkgjs/support" } } ] } 5 | -------------------------------------------------------------------------------- /test/cli/show-local-tree/node_modules/dep1/package-support.json: -------------------------------------------------------------------------------- 1 | { 2 | "versions": [ 3 | { 4 | "version": "*", 5 | "target": { 6 | "node": "supported" 7 | }, 8 | "response": { 9 | "type": "time-permitting" 10 | }, 11 | "backing": { 12 | "hobby": "https://github.com/pkgjs/support" 13 | } 14 | } 15 | ] 16 | } 17 | -------------------------------------------------------------------------------- /test/cli/show-local-tree/node_modules/dep1/package.json: -------------------------------------------------------------------------------- 1 | { 2 | "name": "dep1", 3 | "version": "0.0.1", 4 | "support": true, 5 | "repository": { 6 | "type": "git", 7 | "url": "https://github.com/pkgjs/dep1.git" 8 | } 9 | } 10 | -------------------------------------------------------------------------------- /test/cli/show-local-tree/node_modules/dep2/node_modules/dep3/package-support.json: -------------------------------------------------------------------------------- 1 | { 2 | "versions": [ 3 | { 4 | "version": "*", 5 | "target": { 6 | "node": "supported" 7 | }, 8 | "response": { 9 | "type": "time-permitting" 10 | }, 11 | "backing": { 12 | "hobby": "https://github.com/pkgjs/support" 13 | } 14 | } 15 | ] 16 | } 17 | -------------------------------------------------------------------------------- /test/cli/show-local-tree/node_modules/dep2/node_modules/dep3/package.json: -------------------------------------------------------------------------------- 1 | { 2 | "name": "dep3", 3 | "version": "0.0.1", 4 | "support": true, 5 | "repository": { 6 | "type": "git", 7 | "url": "https://github.com/pkgjs/dep3.git" 8 | } 9 | } 10 | -------------------------------------------------------------------------------- /test/cli/show-local-tree/node_modules/dep2/package-support.json: -------------------------------------------------------------------------------- 1 | { 2 | "versions": [ 3 | { 4 | "version": "*", 5 | "target": { 6 | "node": "supported" 7 | }, 8 | "response": { 9 | "type": "time-permitting" 10 | }, 11 | "backing": { 12 | "hobby": "https://github.com/pkgjs/support" 13 | } 14 | } 15 | ] 16 | } 17 | -------------------------------------------------------------------------------- /test/cli/show-local-tree/node_modules/dep2/package.json: -------------------------------------------------------------------------------- 1 | { 2 | "name": "dep2", 3 | "version": "0.0.1", 4 | "support": true, 5 | "repository": { 6 | "type": "git", 7 | "url": "https://github.com/pkgjs/dep2.git" 8 | }, 9 | "dependencies": { 10 | "dep3": "^0.0.1" 11 | } 12 | } 13 | -------------------------------------------------------------------------------- /test/cli/show-local-tree/package-support.json: -------------------------------------------------------------------------------- 1 | { 2 | "versions": [ 3 | { 4 | "version": "*", 5 | "target": { 6 | "node": "supported" 7 | }, 8 | "response": { 9 | "type": "time-permitting" 10 | }, 11 | "backing": { 12 | "hobby": "https://github.com/pkgjs/support" 13 | } 14 | } 15 | ] 16 | } 17 | -------------------------------------------------------------------------------- /test/cli/show-local-tree/package.json: -------------------------------------------------------------------------------- 1 | { 2 | "name": "@pkgjs/support-show-local", 3 | "version": "0.0.1", 4 | "support": true, 5 | "repository": { 6 | "type": "git", 7 | "url": "https://github.com/pkgjs/support.git" 8 | }, 9 | "dependencies": { 10 | "dep1": "^0.0.1", 11 | "dep2": "^0.0.1" 12 | } 13 | } 14 | -------------------------------------------------------------------------------- /test/cli/show-local/command: -------------------------------------------------------------------------------- 1 | show 2 | -------------------------------------------------------------------------------- /test/cli/show-local/expected: -------------------------------------------------------------------------------- 1 | @pkgjs/support-show-local(0.0.1) - { "versions": [ { "version": "*", "target": { "node": "supported" }, "response": { "type": "time-permitting" }, "backing": { "hobby": "https://github.com/pkgjs/support" } } ] } 2 | -------------------------------------------------------------------------------- /test/cli/show-local/package-support.json: -------------------------------------------------------------------------------- 1 | { 2 | "versions": [ 3 | { 4 | "version": "*", 5 | "target": { 6 | "node": "supported" 7 | }, 8 | "response": { 9 | "type": "time-permitting" 10 | }, 11 | "backing": { 12 | "hobby": "https://github.com/pkgjs/support" 13 | } 14 | } 15 | ] 16 | } 17 | -------------------------------------------------------------------------------- /test/cli/show-local/package.json: -------------------------------------------------------------------------------- 1 | { 2 | "name": "@pkgjs/support-show-local", 3 | "version": "0.0.1", 4 | "support": true, 5 | "repository": { 6 | "type": "git", 7 | "url": "https://github.com/pkgjs/support.git" 8 | } 9 | } 10 | -------------------------------------------------------------------------------- /test/cli/show-separate-repo-directory1/command: -------------------------------------------------------------------------------- 1 | show 2 | -------------------------------------------------------------------------------- /test/cli/show-separate-repo-directory1/expected: -------------------------------------------------------------------------------- 1 | @pkgjs/support-separate-repo-directory1(0.0.1) - https://github.com/pkgjs/support-separate-repo-other/blob/HEAD/subdir2/my-support-package.json 2 | -------------------------------------------------------------------------------- /test/cli/show-separate-repo-directory1/package.json: -------------------------------------------------------------------------------- 1 | { 2 | "name": "@pkgjs/support-separate-repo-directory1", 3 | "version": "0.0.1", 4 | "support": true, 5 | "repository": { 6 | "type": "git", 7 | "url": "https://github.com/pkgjs/support-separate-repo-directory1.git" 8 | }, 9 | "support": { 10 | "repository" : { 11 | "type": "git", 12 | "url" : "https://github.com/pkgjs/support-separate-repo-other.git", 13 | "directory" : "subdir2" 14 | }, 15 | "path" : "./my-support-package.json" 16 | } 17 | } 18 | -------------------------------------------------------------------------------- /test/cli/show-separate-repo-directory2/command: -------------------------------------------------------------------------------- 1 | show 2 | -------------------------------------------------------------------------------- /test/cli/show-separate-repo-directory2/expected: -------------------------------------------------------------------------------- 1 | @pkgjs/support-separate-repo-directory2(0.0.1) - https://github.com/pkgjs/support-separate-repo-other/blob/HEAD/subdir2/package-support.json 2 | -------------------------------------------------------------------------------- /test/cli/show-separate-repo-directory2/package.json: -------------------------------------------------------------------------------- 1 | { 2 | "name": "@pkgjs/support-separate-repo-directory2", 3 | "version": "0.0.1", 4 | "support": true, 5 | "repository": { 6 | "type": "git", 7 | "url": "https://github.com/pkgjs/support-separate-repo-directory2.git" 8 | }, 9 | "support": { 10 | "repository" : { 11 | "type": "git", 12 | "url" : "https://github.com/pkgjs/support-separate-repo-other.git", 13 | "directory" : "subdir2" 14 | } 15 | } 16 | } 17 | -------------------------------------------------------------------------------- /test/cli/show-separate-repo-directory3/command: -------------------------------------------------------------------------------- 1 | show 2 | -------------------------------------------------------------------------------- /test/cli/show-separate-repo-directory3/expected: -------------------------------------------------------------------------------- 1 | @pkgjs/support-separate-repo-directory3(0.0.1) - https://github.com/pkgjs/support-separate-repo-other/blob/HEAD/subdir2/subdir1/my-support-package.json 2 | -------------------------------------------------------------------------------- /test/cli/show-separate-repo-directory3/package.json: -------------------------------------------------------------------------------- 1 | { 2 | "name": "@pkgjs/support-separate-repo-directory3", 3 | "version": "0.0.1", 4 | "support": true, 5 | "repository": { 6 | "type": "git", 7 | "url": "https://github.com/pkgjs/support-separate-repo-directory3.git" 8 | }, 9 | "support": { 10 | "repository" : { 11 | "type": "git", 12 | "url" : "https://github.com/pkgjs/support-separate-repo-other.git", 13 | "directory" : "subdir2" 14 | }, 15 | "path" : "./subdir1/my-support-package.json" 16 | } 17 | } 18 | -------------------------------------------------------------------------------- /test/cli/show-separate-repo-fetch-missing/command: -------------------------------------------------------------------------------- 1 | show --fetch 2 | -------------------------------------------------------------------------------- /test/cli/show-separate-repo-fetch-missing/expected-errors: -------------------------------------------------------------------------------- 1 | @pkgjs/support-separate-repo(0.0.1) - failed to fetch - https://github.com/pkgjs/support/blob/HEAD/examples/does-not-exist.json 2 | -------------------------------------------------------------------------------- /test/cli/show-separate-repo-fetch-missing/package.json: -------------------------------------------------------------------------------- 1 | { 2 | "name": "@pkgjs/support-separate-repo", 3 | "version": "0.0.1", 4 | "support": { 5 | "path": "./examples/does-not-exist.json", 6 | "repository": { 7 | "type": "git", 8 | "url": "https://github.com/pkgjs/support.git" 9 | } 10 | }, 11 | "repository": { 12 | "type": "git", 13 | "url": "https://github.com/pkgjs/support-separate-repo.git" 14 | } 15 | } 16 | -------------------------------------------------------------------------------- /test/cli/show-separate-repo-fetch/command: -------------------------------------------------------------------------------- 1 | show --fetch 2 | -------------------------------------------------------------------------------- /test/cli/show-separate-repo-fetch/expected: -------------------------------------------------------------------------------- 1 | @pkgjs/support-separate-repo(0.0.1) - { "versions": [{ "version": "*", "target": { "node": "lts" }, "response": { "type": "time-permitting" }, "backing": { "hobby": "https://github.com/pkgjs/support" } }]} 2 | -------------------------------------------------------------------------------- /test/cli/show-separate-repo-fetch/package.json: -------------------------------------------------------------------------------- 1 | { 2 | "name": "@pkgjs/support-separate-repo", 3 | "version": "0.0.1", 4 | "support": { 5 | "path": "./examples/basic.json", 6 | "repository": { 7 | "type": "git", 8 | "url": "https://github.com/pkgjs/support.git" 9 | } 10 | }, 11 | "repository": { 12 | "type": "git", 13 | "url": "https://github.com/pkgjs/support-separate-repo.git" 14 | } 15 | } 16 | -------------------------------------------------------------------------------- /test/cli/show-separate-repo-path-escape/command: -------------------------------------------------------------------------------- 1 | show 2 | -------------------------------------------------------------------------------- /test/cli/show-separate-repo-path-escape/expected: -------------------------------------------------------------------------------- 1 | @pkgjs/support-separate-repo-path-escape(0.0.1) - https://github.com/pkgjs/support-separate-repo-other/blob/my-support-package.json 2 | -------------------------------------------------------------------------------- /test/cli/show-separate-repo-path-escape/package.json: -------------------------------------------------------------------------------- 1 | { 2 | "name": "@pkgjs/support-separate-repo-path-escape", 3 | "version": "0.0.1", 4 | "support": true, 5 | "repository": { 6 | "type": "git", 7 | "url": "https://github.com/pkgjs/support-separate-repo-path-escape.git" 8 | }, 9 | "support": { 10 | "repository" : { 11 | "type": "git", 12 | "url" : "https://github.com/pkgjs/support-separate-repo-other.git" 13 | }, 14 | "path" : "./subdir1/../../../../my-support-package.json" 15 | } 16 | } 17 | -------------------------------------------------------------------------------- /test/cli/show-separate-repo-path1/command: -------------------------------------------------------------------------------- 1 | show 2 | -------------------------------------------------------------------------------- /test/cli/show-separate-repo-path1/expected: -------------------------------------------------------------------------------- 1 | @pkgjs/support-separate-repo-path1(0.0.1) - https://github.com/pkgjs/support-separate-repo-other/blob/HEAD/my-support-package.json 2 | -------------------------------------------------------------------------------- /test/cli/show-separate-repo-path1/package.json: -------------------------------------------------------------------------------- 1 | { 2 | "name": "@pkgjs/support-separate-repo-path1", 3 | "version": "0.0.1", 4 | "support": true, 5 | "repository": { 6 | "type": "git", 7 | "url": "https://github.com/pkgjs/support-separate-repo-path1.git" 8 | }, 9 | "support": { 10 | "repository" : { 11 | "type": "git", 12 | "url" : "https://github.com/pkgjs/support-separate-repo-other.git" 13 | }, 14 | "path" : "./my-support-package.json" 15 | } 16 | } 17 | -------------------------------------------------------------------------------- /test/cli/show-separate-repo-path2/command: -------------------------------------------------------------------------------- 1 | show 2 | -------------------------------------------------------------------------------- /test/cli/show-separate-repo-path2/expected: -------------------------------------------------------------------------------- 1 | @pkgjs/support-separate-repo-path2(0.0.1) - https://github.com/pkgjs/support-separate-repo-other/blob/HEAD/subdir1/my-support-package.json 2 | -------------------------------------------------------------------------------- /test/cli/show-separate-repo-path2/package.json: -------------------------------------------------------------------------------- 1 | { 2 | "name": "@pkgjs/support-separate-repo-path2", 3 | "version": "0.0.1", 4 | "support": true, 5 | "repository": { 6 | "type": "git", 7 | "url": "https://github.com/pkgjs/support-separate-repo-path2.git" 8 | }, 9 | "support": { 10 | "repository" : { 11 | "type": "git", 12 | "url" : "https://github.com/pkgjs/support-separate-repo-other.git" 13 | }, 14 | "path" : "./subdir1/my-support-package.json" 15 | } 16 | } 17 | -------------------------------------------------------------------------------- /test/cli/show-separate-repo/command: -------------------------------------------------------------------------------- 1 | show 2 | -------------------------------------------------------------------------------- /test/cli/show-separate-repo/expected: -------------------------------------------------------------------------------- 1 | @pkgjs/support-separate-repo(0.0.1) - https://github.com/pkgjs/support-separate-repo-other/blob/HEAD/package-support.json 2 | -------------------------------------------------------------------------------- /test/cli/show-separate-repo/package-support.json: -------------------------------------------------------------------------------- 1 | { 2 | "versions": [ 3 | { 4 | "version": "*", 5 | "target": { 6 | "node": "supported" 7 | }, 8 | "response": { 9 | "type": "time-permitting" 10 | }, 11 | "backing": { 12 | "hobby": "https://github.com/pkgjs/support" 13 | } 14 | } 15 | ] 16 | } 17 | -------------------------------------------------------------------------------- /test/cli/show-separate-repo/package.json: -------------------------------------------------------------------------------- 1 | { 2 | "name": "@pkgjs/support-separate-repo", 3 | "version": "0.0.1", 4 | "support": { 5 | "repository": { 6 | "type": "git", 7 | "url": "https://github.com/pkgjs/support-separate-repo-other.git" 8 | } 9 | }, 10 | "repository": { 11 | "type": "git", 12 | "url": "https://github.com/pkgjs/support-separate-repo.git" 13 | } 14 | } 15 | -------------------------------------------------------------------------------- /test/cli/validate-invalid-json/command: -------------------------------------------------------------------------------- 1 | validate 2 | -------------------------------------------------------------------------------- /test/cli/validate-invalid-json/expected-errors: -------------------------------------------------------------------------------- 1 | Your support information is not properly formed 2 | Unexpected end of JSON input 3 | -------------------------------------------------------------------------------- /test/cli/validate-invalid-json/package-support.json: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/pkgjs/support/81a010c3bcf0f88b7d915a9b562b1ff09d5d181d/test/cli/validate-invalid-json/package-support.json -------------------------------------------------------------------------------- /test/cli/validate-invalid-json/package.json: -------------------------------------------------------------------------------- 1 | { 2 | "name": "@pkgjs/validate-multiple-backing", 3 | "version": "0.0.1", 4 | "support": true 5 | } 6 | -------------------------------------------------------------------------------- /test/cli/validate-local-bad-element1/command: -------------------------------------------------------------------------------- 1 | validate 2 | -------------------------------------------------------------------------------- /test/cli/validate-local-bad-element1/expected-errors: -------------------------------------------------------------------------------- 1 | Error in support element in package.json 2 | Support element should either be true or an Object matching the required schema 3 | -------------------------------------------------------------------------------- /test/cli/validate-local-bad-element1/package.json: -------------------------------------------------------------------------------- 1 | { 2 | "name": "@pkgjs/support-show-local", 3 | "version": "0.0.1", 4 | "support": false, 5 | "repository": { 6 | "type": "git", 7 | "url": "https://github.com/pkgjs/support.git" 8 | } 9 | } 10 | -------------------------------------------------------------------------------- /test/cli/validate-local-bad-element2/command: -------------------------------------------------------------------------------- 1 | validate 2 | -------------------------------------------------------------------------------- /test/cli/validate-local-bad-element2/expected-errors: -------------------------------------------------------------------------------- 1 | Error in support element in package.json 2 | Support element should either be true or an Object matching the required schema 3 | -------------------------------------------------------------------------------- /test/cli/validate-local-bad-element2/package.json: -------------------------------------------------------------------------------- 1 | { 2 | "name": "@pkgjs/support-show-local", 3 | "version": "0.0.1", 4 | "support": 1235, 5 | "repository": { 6 | "type": "git", 7 | "url": "https://github.com/pkgjs/support.git" 8 | } 9 | } 10 | -------------------------------------------------------------------------------- /test/cli/validate-local-bad-element3/command: -------------------------------------------------------------------------------- 1 | validate 2 | -------------------------------------------------------------------------------- /test/cli/validate-local-bad-element3/expected-errors: -------------------------------------------------------------------------------- 1 | Error in support element in package.json 2 | REQUIRED should have required property 'repository' 3 | 4 | > 1 | {"support":{}} 5 | | ^ ☹️ repository is missing here! 6 | -------------------------------------------------------------------------------- /test/cli/validate-local-bad-element3/package.json: -------------------------------------------------------------------------------- 1 | { 2 | "name": "@pkgjs/support-show-local", 3 | "version": "0.0.1", 4 | "support": { }, 5 | "repository": { 6 | "type": "git", 7 | "url": "https://github.com/pkgjs/support.git" 8 | } 9 | } 10 | -------------------------------------------------------------------------------- /test/cli/validate-local-escape-ok/command: -------------------------------------------------------------------------------- 1 | validate --base-path=${cwd}/../.. 2 | -------------------------------------------------------------------------------- /test/cli/validate-local-escape-ok/expected: -------------------------------------------------------------------------------- 1 | Your support information is valid! 2 | -------------------------------------------------------------------------------- /test/cli/validate-local-escape-ok/package.json: -------------------------------------------------------------------------------- 1 | { 2 | "name": "@pkgjs/support-show-local-escape-ok", 3 | "version": "0.0.1", 4 | "support": "../../fixtures/my-support-info.json", 5 | "repository": { 6 | "type": "git", 7 | "url": "https://github.com/pkgjs/support.git" 8 | } 9 | } 10 | -------------------------------------------------------------------------------- /test/cli/validate-local-no-data/command: -------------------------------------------------------------------------------- 1 | validate 2 | -------------------------------------------------------------------------------- /test/cli/validate-local-no-data/expected-errors: -------------------------------------------------------------------------------- 1 | no support info 2 | -------------------------------------------------------------------------------- /test/cli/validate-local-no-data/package.json: -------------------------------------------------------------------------------- 1 | { 2 | "name": "@pkgjs/support-show-local", 3 | "version": "0.0.1", 4 | "repository": { 5 | "type": "git", 6 | "url": "https://github.com/pkgjs/support.git" 7 | } 8 | } 9 | -------------------------------------------------------------------------------- /test/cli/validate-local-repository-bad1/command: -------------------------------------------------------------------------------- 1 | validate 2 | -------------------------------------------------------------------------------- /test/cli/validate-local-repository-bad1/expected-errors: -------------------------------------------------------------------------------- 1 | Error in support element in package.json 2 | ENUM should be equal to one of the allowed values 3 | 4 | > 1 | {"support":{"repository":{"type":"xxx","url":"https://github.com/pkgjs/support-separate-repo-other.git","directory":"subdir2"},"path":"./my-support-package.json"}} 5 | | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ 👈🏽 enum should be equal to one of the allowed values 6 | 7 | TYPE should be string 8 | 9 | > 1 | {"support":{"repository":{"type":"xxx","url":"https://github.com/pkgjs/support-separate-repo-other.git","directory":"subdir2"},"path":"./my-support-package.json"}} 10 | | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ 👈🏽 type should be string 11 | 12 | ONEOF should match exactly one schema in oneOf 13 | 14 | > 1 | {"support":{"repository":{"type":"xxx","url":"https://github.com/pkgjs/support-separate-repo-other.git","directory":"subdir2"},"path":"./my-support-package.json"}} 15 | | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ 👈🏽 oneOf should match exactly one schema in oneOf 16 | 17 | ENUM should be equal to one of the allowed values 18 | (git) 19 | 20 | > 1 | {"support":{"repository":{"type":"xxx","url":"https://github.com/pkgjs/support-separate-repo-other.git","directory":"subdir2"},"path":"./my-support-package.json"}} 21 | | ^^^^^ 👈🏽 Did you mean git here? 22 | -------------------------------------------------------------------------------- /test/cli/validate-local-repository-bad1/package.json: -------------------------------------------------------------------------------- 1 | { 2 | "name": "@pkgjs/support-separate-repo-directory1", 3 | "version": "0.0.1", 4 | "support": true, 5 | "repository": { 6 | "type": "git", 7 | "url": "https://github.com/pkgjs/support-separate-repo-directory1.git" 8 | }, 9 | "support": { 10 | "repository" : { 11 | "type": "xxx", 12 | "url" : "https://github.com/pkgjs/support-separate-repo-other.git", 13 | "directory" : "subdir2" 14 | }, 15 | "path" : "./my-support-package.json" 16 | } 17 | } 18 | -------------------------------------------------------------------------------- /test/cli/validate-local-repository-bad2/command: -------------------------------------------------------------------------------- 1 | validate 2 | -------------------------------------------------------------------------------- /test/cli/validate-local-repository-bad2/expected-errors: -------------------------------------------------------------------------------- 1 | Error in support element in package.json 2 | ENUM should be equal to one of the allowed values 3 | 4 | > 1 | {"support":{"repository":{"type":"git","directory":"subdir2"},"path":"./my-support-package.json"}} 5 | | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ 👈🏽 enum should be equal to one of the allowed values 6 | 7 | TYPE should be string 8 | 9 | > 1 | {"support":{"repository":{"type":"git","directory":"subdir2"},"path":"./my-support-package.json"}} 10 | | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ 👈🏽 type should be string 11 | 12 | ONEOF should match exactly one schema in oneOf 13 | 14 | > 1 | {"support":{"repository":{"type":"git","directory":"subdir2"},"path":"./my-support-package.json"}} 15 | | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ 👈🏽 oneOf should match exactly one schema in oneOf 16 | 17 | REQUIRED should have required property 'url' 18 | 19 | > 1 | {"support":{"repository":{"type":"git","directory":"subdir2"},"path":"./my-support-package.json"}} 20 | | ^ ☹️ url is missing here! 21 | -------------------------------------------------------------------------------- /test/cli/validate-local-repository-bad2/package.json: -------------------------------------------------------------------------------- 1 | { 2 | "name": "@pkgjs/support-separate-repo-directory1", 3 | "version": "0.0.1", 4 | "support": true, 5 | "repository": { 6 | "type": "git", 7 | "url": "https://github.com/pkgjs/support-separate-repo-directory1.git" 8 | }, 9 | "support": { 10 | "repository" : { 11 | "type": "git", 12 | "directory" : "subdir2" 13 | }, 14 | "path" : "./my-support-package.json" 15 | } 16 | } 17 | -------------------------------------------------------------------------------- /test/cli/validate-local-repository-bad3/command: -------------------------------------------------------------------------------- 1 | validate 2 | -------------------------------------------------------------------------------- /test/cli/validate-local-repository-bad3/expected-errors: -------------------------------------------------------------------------------- 1 | Error in support element in package.json 2 | ENUM should be equal to one of the allowed values 3 | 4 | > 1 | {"support":{"repository":{"url":"https://github.com/pkgjs/support-separate-repo-other.git","directory":"subdir2"},"path":"./my-support-package.json"}} 5 | | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ 👈🏽 enum should be equal to one of the allowed values 6 | 7 | TYPE should be string 8 | 9 | > 1 | {"support":{"repository":{"url":"https://github.com/pkgjs/support-separate-repo-other.git","directory":"subdir2"},"path":"./my-support-package.json"}} 10 | | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ 👈🏽 type should be string 11 | 12 | ONEOF should match exactly one schema in oneOf 13 | 14 | > 1 | {"support":{"repository":{"url":"https://github.com/pkgjs/support-separate-repo-other.git","directory":"subdir2"},"path":"./my-support-package.json"}} 15 | | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ 👈🏽 oneOf should match exactly one schema in oneOf 16 | 17 | REQUIRED should have required property 'type' 18 | 19 | > 1 | {"support":{"repository":{"url":"https://github.com/pkgjs/support-separate-repo-other.git","directory":"subdir2"},"path":"./my-support-package.json"}} 20 | | ^ ☹️ type is missing here! 21 | -------------------------------------------------------------------------------- /test/cli/validate-local-repository-bad3/package.json: -------------------------------------------------------------------------------- 1 | { 2 | "name": "@pkgjs/support-separate-repo-directory1", 3 | "version": "0.0.1", 4 | "support": true, 5 | "repository": { 6 | "type": "git", 7 | "url": "https://github.com/pkgjs/support-separate-repo-directory1.git" 8 | }, 9 | "support": { 10 | "repository" : { 11 | "url" : "https://github.com/pkgjs/support-separate-repo-other.git", 12 | "directory" : "subdir2" 13 | }, 14 | "path" : "./my-support-package.json" 15 | } 16 | } 17 | -------------------------------------------------------------------------------- /test/cli/validate-local-repository-bad4/command: -------------------------------------------------------------------------------- 1 | validate 2 | -------------------------------------------------------------------------------- /test/cli/validate-local-repository-bad4/expected-errors: -------------------------------------------------------------------------------- 1 | Error in support element in package.json 2 | ENUM should be equal to one of the allowed values 3 | 4 | > 1 | {"support":{"repository":{"type":"git","url":"https://github.com/pkgjs/support-separate-repo-other.git","directory":"subdir2","extra":"123"},"path":"./my-support-package.json"}} 5 | | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ 👈🏽 enum should be equal to one of the allowed values 6 | 7 | TYPE should be string 8 | 9 | > 1 | {"support":{"repository":{"type":"git","url":"https://github.com/pkgjs/support-separate-repo-other.git","directory":"subdir2","extra":"123"},"path":"./my-support-package.json"}} 10 | | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ 👈🏽 type should be string 11 | 12 | ONEOF should match exactly one schema in oneOf 13 | 14 | > 1 | {"support":{"repository":{"type":"git","url":"https://github.com/pkgjs/support-separate-repo-other.git","directory":"subdir2","extra":"123"},"path":"./my-support-package.json"}} 15 | | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ 👈🏽 oneOf should match exactly one schema in oneOf 16 | 17 | ADDTIONAL PROPERTY should NOT have additional properties 18 | 19 | > 1 | {"support":{"repository":{"type":"git","url":"https://github.com/pkgjs/support-separate-repo-other.git","directory":"subdir2","extra":"123"},"path":"./my-support-package.json"}} 20 | | ^^^^^^^ 😲 extra is not expected to be here! 21 | -------------------------------------------------------------------------------- /test/cli/validate-local-repository-bad4/package.json: -------------------------------------------------------------------------------- 1 | { 2 | "name": "@pkgjs/support-separate-repo-directory1", 3 | "version": "0.0.1", 4 | "support": true, 5 | "repository": { 6 | "type": "git", 7 | "url": "https://github.com/pkgjs/support-separate-repo-directory1.git" 8 | }, 9 | "support": { 10 | "repository" : { 11 | "type": "git", 12 | "url" : "https://github.com/pkgjs/support-separate-repo-other.git", 13 | "directory" : "subdir2", 14 | "extra": "123" 15 | }, 16 | "path" : "./my-support-package.json" 17 | } 18 | } 19 | -------------------------------------------------------------------------------- /test/cli/validate-local-repository-bad5/command: -------------------------------------------------------------------------------- 1 | validate 2 | -------------------------------------------------------------------------------- /test/cli/validate-local-repository-bad5/expected-errors: -------------------------------------------------------------------------------- 1 | Error in support element in package.json 2 | ENUM should be equal to one of the allowed values 3 | 4 | > 1 | {"support":{"repository":{"type":"git","url":"https://github.com/pkgjs/support-separate-repo-other.git","directory":"subdir2"},"path":"./my-support-package.json","extra":"123"}} 5 | | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ 👈🏽 enum should be equal to one of the allowed values 6 | 7 | TYPE should be string 8 | 9 | > 1 | {"support":{"repository":{"type":"git","url":"https://github.com/pkgjs/support-separate-repo-other.git","directory":"subdir2"},"path":"./my-support-package.json","extra":"123"}} 10 | | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ 👈🏽 type should be string 11 | 12 | ADDTIONAL PROPERTY should NOT have additional properties 13 | 14 | > 1 | {"support":{"repository":{"type":"git","url":"https://github.com/pkgjs/support-separate-repo-other.git","directory":"subdir2"},"path":"./my-support-package.json","extra":"123"}} 15 | | ^^^^^^^ 😲 extra is not expected to be here! 16 | 17 | ONEOF should match exactly one schema in oneOf 18 | 19 | > 1 | {"support":{"repository":{"type":"git","url":"https://github.com/pkgjs/support-separate-repo-other.git","directory":"subdir2"},"path":"./my-support-package.json","extra":"123"}} 20 | | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ 👈🏽 oneOf should match exactly one schema in oneOf 21 | -------------------------------------------------------------------------------- /test/cli/validate-local-repository-bad5/package.json: -------------------------------------------------------------------------------- 1 | { 2 | "name": "@pkgjs/support-separate-repo-directory1", 3 | "version": "0.0.1", 4 | "support": true, 5 | "repository": { 6 | "type": "git", 7 | "url": "https://github.com/pkgjs/support-separate-repo-directory1.git" 8 | }, 9 | "support": { 10 | "repository" : { 11 | "type": "git", 12 | "url" : "https://github.com/pkgjs/support-separate-repo-other.git", 13 | "directory" : "subdir2" 14 | }, 15 | "path" : "./my-support-package.json", 16 | "extra": "123" 17 | } 18 | } 19 | -------------------------------------------------------------------------------- /test/cli/validate-local-repository1/command: -------------------------------------------------------------------------------- 1 | validate 2 | -------------------------------------------------------------------------------- /test/cli/validate-local-repository1/expected-errors: -------------------------------------------------------------------------------- 1 | support info not resolved: https://github.com/pkgjs/support-separate-repo-other/blob/HEAD/subdir2/my-support-package.json 2 | -------------------------------------------------------------------------------- /test/cli/validate-local-repository1/package.json: -------------------------------------------------------------------------------- 1 | { 2 | "name": "@pkgjs/support-separate-repo-directory1", 3 | "version": "0.0.1", 4 | "support": true, 5 | "repository": { 6 | "type": "git", 7 | "url": "https://github.com/pkgjs/support-separate-repo-directory1.git" 8 | }, 9 | "support": { 10 | "repository" : { 11 | "type": "git", 12 | "url" : "https://github.com/pkgjs/support-separate-repo-other.git", 13 | "directory" : "subdir2" 14 | }, 15 | "path" : "./my-support-package.json" 16 | } 17 | } 18 | -------------------------------------------------------------------------------- /test/cli/validate-local-support-json-bad/command: -------------------------------------------------------------------------------- 1 | validate 2 | -------------------------------------------------------------------------------- /test/cli/validate-local-support-json-bad/expected-errors: -------------------------------------------------------------------------------- 1 | Error in support JSON 2 | TYPE should be array 3 | 4 | > 1 | {"versions":[{"version":"*","target":{"node":"supported"},"response":{"type":"Xtime-permitting"},"backing":{"hobby":"https://github.com/pkgjs/support"}}]} 5 | | ^^^^^^^^^^^^^^^^^^^^^^^^^^^ 👈🏽 type should be array 6 | 7 | ONEOF should match exactly one schema in oneOf 8 | 9 | > 1 | {"versions":[{"version":"*","target":{"node":"supported"},"response":{"type":"Xtime-permitting"},"backing":{"hobby":"https://github.com/pkgjs/support"}}]} 10 | | ^^^^^^^^^^^^^^^^^^^^^^^^^^^ 👈🏽 oneOf should match exactly one schema in oneOf 11 | 12 | ENUM should be equal to one of the allowed values 13 | 14 | > 1 | {"versions":[{"version":"*","target":{"node":"supported"},"response":{"type":"Xtime-permitting"},"backing":{"hobby":"https://github.com/pkgjs/support"}}]} 15 | | ^^^^^^^^^^^^^^^^^^ 👈🏽 enum should be equal to one of the allowed values 16 | 17 | PATTERN should match pattern "regular-[1-7]" 18 | 19 | > 1 | {"versions":[{"version":"*","target":{"node":"supported"},"response":{"type":"Xtime-permitting"},"backing":{"hobby":"https://github.com/pkgjs/support"}}]} 20 | | ^^^^^^^^^^^^^^^^^^ 👈🏽 pattern should match pattern "regular-[1-7]" 21 | 22 | ONEOF should match exactly one schema in oneOf 23 | 24 | > 1 | {"versions":[{"version":"*","target":{"node":"supported"},"response":{"type":"Xtime-permitting"},"backing":{"hobby":"https://github.com/pkgjs/support"}}]} 25 | | ^^^^^^^^^^^^^^^^^^ 👈🏽 oneOf should match exactly one schema in oneOf 26 | -------------------------------------------------------------------------------- /test/cli/validate-local-support-json-bad/package-support.json: -------------------------------------------------------------------------------- 1 | { 2 | "versions": [ 3 | { 4 | "version": "*", 5 | "target": { 6 | "node": "supported" 7 | }, 8 | "response": { 9 | "type": "Xtime-permitting" 10 | }, 11 | "backing": { 12 | "hobby": "https://github.com/pkgjs/support" 13 | } 14 | } 15 | ] 16 | } 17 | -------------------------------------------------------------------------------- /test/cli/validate-local-support-json-bad/package.json: -------------------------------------------------------------------------------- 1 | { 2 | "name": "@pkgjs/support-show-local", 3 | "version": "0.0.1", 4 | "support": true, 5 | "repository": { 6 | "type": "git", 7 | "url": "https://github.com/pkgjs/support.git" 8 | } 9 | } 10 | -------------------------------------------------------------------------------- /test/cli/validate-local-support-json-bad2/command: -------------------------------------------------------------------------------- 1 | validate 2 | -------------------------------------------------------------------------------- /test/cli/validate-local-support-json-bad2/expected-errors: -------------------------------------------------------------------------------- 1 | Error in support JSON 2 | ADDTIONAL PROPERTY should NOT have additional properties 3 | 4 | > 1 | {"versions":[{"version":"*","target":{"node":"supported"},"response":{"type":"time-permitting"},"Xbacking":{"hobby":"https://github.com/pkgjs/support"}}]} 5 | | ^^^^^^^^^^ 😲 Xbacking is not expected to be here! 6 | -------------------------------------------------------------------------------- /test/cli/validate-local-support-json-bad2/package-support.json: -------------------------------------------------------------------------------- 1 | { 2 | "versions": [ 3 | { 4 | "version": "*", 5 | "target": { 6 | "node": "supported" 7 | }, 8 | "response": { 9 | "type": "time-permitting" 10 | }, 11 | "Xbacking": { 12 | "hobby": "https://github.com/pkgjs/support" 13 | } 14 | } 15 | ] 16 | } 17 | -------------------------------------------------------------------------------- /test/cli/validate-local-support-json-bad2/package.json: -------------------------------------------------------------------------------- 1 | { 2 | "name": "@pkgjs/support-show-local", 3 | "version": "0.0.1", 4 | "support": true, 5 | "repository": { 6 | "type": "git", 7 | "url": "https://github.com/pkgjs/support.git" 8 | } 9 | } 10 | -------------------------------------------------------------------------------- /test/cli/validate-local-support-json-bad3/command: -------------------------------------------------------------------------------- 1 | validate 2 | -------------------------------------------------------------------------------- /test/cli/validate-local-support-json-bad3/expected-errors: -------------------------------------------------------------------------------- 1 | Error in support JSON 2 | TYPE should be array 3 | 4 | > 1 | {"versions":[{"version":"*","target":{"node":"supported"},"response":{"type":"Xtime-permitting"},"backing":{"hobby":"https://github.com/pkgjs/support"}}]} 5 | | ^^^^^^^^^^^^^^^^^^^^^^^^^^^ 👈🏽 type should be array 6 | 7 | ONEOF should match exactly one schema in oneOf 8 | 9 | > 1 | {"versions":[{"version":"*","target":{"node":"supported"},"response":{"type":"Xtime-permitting"},"backing":{"hobby":"https://github.com/pkgjs/support"}}]} 10 | | ^^^^^^^^^^^^^^^^^^^^^^^^^^^ 👈🏽 oneOf should match exactly one schema in oneOf 11 | 12 | ENUM should be equal to one of the allowed values 13 | 14 | > 1 | {"versions":[{"version":"*","target":{"node":"supported"},"response":{"type":"Xtime-permitting"},"backing":{"hobby":"https://github.com/pkgjs/support"}}]} 15 | | ^^^^^^^^^^^^^^^^^^ 👈🏽 enum should be equal to one of the allowed values 16 | 17 | PATTERN should match pattern "regular-[1-7]" 18 | 19 | > 1 | {"versions":[{"version":"*","target":{"node":"supported"},"response":{"type":"Xtime-permitting"},"backing":{"hobby":"https://github.com/pkgjs/support"}}]} 20 | | ^^^^^^^^^^^^^^^^^^ 👈🏽 pattern should match pattern "regular-[1-7]" 21 | 22 | ONEOF should match exactly one schema in oneOf 23 | 24 | > 1 | {"versions":[{"version":"*","target":{"node":"supported"},"response":{"type":"Xtime-permitting"},"backing":{"hobby":"https://github.com/pkgjs/support"}}]} 25 | | ^^^^^^^^^^^^^^^^^^ 👈🏽 oneOf should match exactly one schema in oneOf 26 | -------------------------------------------------------------------------------- /test/cli/validate-local-support-json-bad3/package-support.json: -------------------------------------------------------------------------------- 1 | { 2 | "versions": [ 3 | { 4 | "version": "*", 5 | "target": { 6 | "node": "supported" 7 | }, 8 | "response": { 9 | "type": "Xtime-permitting" 10 | }, 11 | "backing": { 12 | "hobby": "https://github.com/pkgjs/support" 13 | } 14 | } 15 | ] 16 | } 17 | -------------------------------------------------------------------------------- /test/cli/validate-local-support-json-bad3/package.json: -------------------------------------------------------------------------------- 1 | { 2 | "name": "@pkgjs/support-show-local", 3 | "version": "0.0.1", 4 | "support": true, 5 | "repository": { 6 | "type": "git", 7 | "url": "https://github.com/pkgjs/support.git" 8 | } 9 | } 10 | -------------------------------------------------------------------------------- /test/cli/validate-local/command: -------------------------------------------------------------------------------- 1 | validate 2 | -------------------------------------------------------------------------------- /test/cli/validate-local/expected: -------------------------------------------------------------------------------- 1 | Your support information is valid! 2 | -------------------------------------------------------------------------------- /test/cli/validate-local/package-support.json: -------------------------------------------------------------------------------- 1 | { 2 | "versions": [ 3 | { 4 | "version": "*", 5 | "target": { 6 | "node": "supported" 7 | }, 8 | "response": { 9 | "type": "time-permitting" 10 | }, 11 | "backing": { 12 | "hobby": "https://github.com/pkgjs/support" 13 | } 14 | } 15 | ] 16 | } 17 | -------------------------------------------------------------------------------- /test/cli/validate-local/package.json: -------------------------------------------------------------------------------- 1 | { 2 | "name": "@pkgjs/support-show-local", 3 | "version": "0.0.1", 4 | "support": true, 5 | "repository": { 6 | "type": "git", 7 | "url": "https://github.com/pkgjs/support.git" 8 | } 9 | } 10 | -------------------------------------------------------------------------------- /test/cli/validate-multiple-backing/command: -------------------------------------------------------------------------------- 1 | validate 2 | -------------------------------------------------------------------------------- /test/cli/validate-multiple-backing/expected: -------------------------------------------------------------------------------- 1 | Your support information is valid! 2 | -------------------------------------------------------------------------------- /test/cli/validate-multiple-backing/package-support.json: -------------------------------------------------------------------------------- 1 | { 2 | "versions": [ 3 | { 4 | "version": "*", 5 | "target": { 6 | "node": "lts" 7 | }, 8 | "response": { 9 | "type": "time-permitting", 10 | "paid": false, 11 | "contact": { 12 | "name": "node-addon-api team", 13 | "url": "https://github.com/nodejs/node-addon-api/issues" 14 | } 15 | }, 16 | "backing": [ 17 | { "project": "https://github.com/nodejs" }, 18 | { "foundation": "https://openjsf.org/" } 19 | ] 20 | } 21 | ] 22 | } 23 | -------------------------------------------------------------------------------- /test/cli/validate-multiple-backing/package.json: -------------------------------------------------------------------------------- 1 | { 2 | "name": "@pkgjs/validate-multiple-backing", 3 | "version": "0.0.1", 4 | "support": true 5 | } 6 | -------------------------------------------------------------------------------- /test/cli/validate-multiple-backing2/command: -------------------------------------------------------------------------------- 1 | validate 2 | -------------------------------------------------------------------------------- /test/cli/validate-multiple-backing2/expected: -------------------------------------------------------------------------------- 1 | Your support information is valid! 2 | -------------------------------------------------------------------------------- /test/cli/validate-multiple-backing2/package-support.json: -------------------------------------------------------------------------------- 1 | { 2 | "versions": [ 3 | { 4 | "version": "*", 5 | "target": { 6 | "node": "lts" 7 | }, 8 | "response": { 9 | "type": "time-permitting", 10 | "paid": false, 11 | "contact": { 12 | "name": "node-addon-api team", 13 | "url": "https://github.com/nodejs/node-addon-api/issues" 14 | } 15 | }, 16 | "backing": { "project": [ "https://github.com/nodejs", 17 | "https://openjsf.org/" ] } 18 | } 19 | ] 20 | } 21 | -------------------------------------------------------------------------------- /test/cli/validate-multiple-backing2/package.json: -------------------------------------------------------------------------------- 1 | { 2 | "name": "@pkgjs/validate-multiple-backing", 3 | "version": "0.0.1", 4 | "support": true 5 | } 6 | -------------------------------------------------------------------------------- /test/cli/validate-non-resolved/command: -------------------------------------------------------------------------------- 1 | validate --canonical 2 | -------------------------------------------------------------------------------- /test/cli/validate-non-resolved/expected-errors: -------------------------------------------------------------------------------- 1 | support info not resolved: https://github.com/pkgjs/support/blob/HEAD/package-support.json 2 | -------------------------------------------------------------------------------- /test/cli/validate-non-resolved/package.json: -------------------------------------------------------------------------------- 1 | { 2 | "name": "@pkgjs/support-show-local", 3 | "version": "0.0.1", 4 | "support": true, 5 | "repository": { 6 | "type": "git", 7 | "url": "https://github.com/pkgjs/support.git" 8 | } 9 | } 10 | -------------------------------------------------------------------------------- /test/cli/validate-separate-repo-fetch/command: -------------------------------------------------------------------------------- 1 | validate --fetch 2 | -------------------------------------------------------------------------------- /test/cli/validate-separate-repo-fetch/expected: -------------------------------------------------------------------------------- 1 | Your support information is valid! 2 | -------------------------------------------------------------------------------- /test/cli/validate-separate-repo-fetch/package.json: -------------------------------------------------------------------------------- 1 | { 2 | "name": "@pkgjs/support-separate-repo", 3 | "version": "0.0.1", 4 | "support": { 5 | "path": "./examples/basic.json", 6 | "repository": { 7 | "type": "git", 8 | "url": "https://github.com/pkgjs/support.git" 9 | } 10 | }, 11 | "repository": { 12 | "type": "git", 13 | "url": "https://github.com/pkgjs/support-separate-repo.git" 14 | } 15 | } 16 | -------------------------------------------------------------------------------- /test/create.js: -------------------------------------------------------------------------------- 1 | const { suite, test, before, after } = require('mocha'); 2 | const assert = require('assert'); 3 | const fs = require('fs-extra'); 4 | const path = require('path'); 5 | const childProcess = require('child_process'); 6 | const inquirer = require('inquirer'); 7 | const support = require('../index.js'); 8 | 9 | suite('support create command', () => { 10 | const supportCommand = path.join(__dirname, '..', 'bin', 'support'); 11 | 12 | // for mocking inquirer 13 | let inquirerOrigin; 14 | before(() => { 15 | inquirerOrigin = inquirer.prompt; 16 | }); 17 | 18 | test('call create with -y', (done) => { 19 | const { fixtureCwd, targetPackageJsonPath } = prepareFixtures('create-with-default-values'); 20 | const targetPackageSupportPath = path.join(fixtureCwd, 'package-support.json'); 21 | 22 | childProcess.exec(`${supportCommand} create -y`, { cwd: fixtureCwd }, (err, stdout, stderr) => { 23 | const resultSupportContent = fs.readFileSync(targetPackageSupportPath, 'utf-8').trim(); 24 | const resultPackageJsonContent = fs.readFileSync(targetPackageJsonPath, 'utf-8').trim(); 25 | const expectedSupportContent = fs.readFileSync(path.join(fixtureCwd, 'expexted-package-support.json'), 'utf-8').trim(); 26 | const expectedPackageJsonContent = fs.readFileSync(path.join(fixtureCwd, 'expected-package.json'), 'utf-8').trim(); 27 | 28 | assert.strictEqual(resultSupportContent, expectedSupportContent); 29 | assert.strictEqual(resultPackageJsonContent, expectedPackageJsonContent); 30 | 31 | cleanUpFixtures('create-with-default-values'); 32 | done(err); 33 | }); 34 | }); 35 | 36 | suite('backing from FUNDING.yml', () => { 37 | test('FUNDING.yml not found', async () => { 38 | const { fixtureCwd } = prepareFixtures('create-with-funding-yml-no-file'); 39 | inquirer.prompt = (questions) => Promise.resolve({ 40 | targetVersion: 'lts', 41 | responseTime: 'time-permitting', 42 | backingType: 'get_from_funding' 43 | }); 44 | 45 | process.chdir(fixtureCwd); 46 | 47 | try { 48 | await support.create(false); 49 | } catch (e) { 50 | assert.strictEqual(e.message.includes('Generating backing from FUNDING.yml failed'), true); 51 | cleanUpFixtures('create-with-funding-yml-no-file'); 52 | } 53 | }); 54 | 55 | test('FUNDING.yml present', async () => { 56 | const { fixtureCwd, targetPackageJsonPath } = prepareFixtures('create-with-funding-yml-positive'); 57 | const targetPackageSupportPath = path.join(fixtureCwd, 'package-support.json'); 58 | inquirer.prompt = (questions) => Promise.resolve({ 59 | targetVersion: 'lts', 60 | responseTime: 'time-permitting', 61 | backingType: 'get_from_funding' 62 | }); 63 | 64 | process.chdir(fixtureCwd); 65 | 66 | await support.create(false); 67 | 68 | const resultSupportContent = fs.readFileSync(targetPackageSupportPath, 'utf-8').trim(); 69 | const resultPackageJsonContent = fs.readFileSync(targetPackageJsonPath, 'utf-8').trim(); 70 | const expectedSupportContent = fs.readFileSync(path.join(fixtureCwd, 'expexted-package-support.json'), 'utf-8').trim(); 71 | const expectedPackageJsonContent = fs.readFileSync(path.join(fixtureCwd, 'expected-package.json'), 'utf-8').trim(); 72 | 73 | assert.strictEqual(resultSupportContent, expectedSupportContent); 74 | assert.strictEqual(resultPackageJsonContent, expectedPackageJsonContent); 75 | 76 | cleanUpFixtures('create-with-funding-yml-positive'); 77 | }); 78 | }); 79 | 80 | suite('backing from package.json funding field', () => { 81 | test('funding field not found', async () => { 82 | const { fixtureCwd } = prepareFixtures('create-with-package-json-funding'); 83 | inquirer.prompt = (questions) => Promise.resolve({ 84 | targetVersion: 'lts', 85 | responseTime: 'time-permitting', 86 | backingType: 'get_from_funding_package_json' 87 | }); 88 | 89 | process.chdir(fixtureCwd); 90 | 91 | try { 92 | await support.create(false); 93 | } catch (e) { 94 | assert.strictEqual(e.message.includes('Funding field not found in package.json'), true); 95 | cleanUpFixtures('create-with-package-json-funding'); 96 | } 97 | }); 98 | 99 | test('funding field as array', async () => { 100 | const { fixtureCwd, targetPackageJsonPath } = prepareFixtures('create-with-package-json-funding-positive'); 101 | const targetPackageSupportPath = path.join(fixtureCwd, 'package-support.json'); 102 | inquirer.prompt = (questions) => Promise.resolve({ 103 | targetVersion: 'lts', 104 | responseTime: 'time-permitting', 105 | backingType: 'get_from_funding_package_json' 106 | }); 107 | 108 | process.chdir(fixtureCwd); 109 | 110 | await support.create(false); 111 | 112 | const resultSupportContent = fs.readFileSync(targetPackageSupportPath, 'utf-8').trim(); 113 | const resultPackageJsonContent = fs.readFileSync(targetPackageJsonPath, 'utf-8').trim(); 114 | const expectedSupportContent = fs.readFileSync(path.join(fixtureCwd, 'expexted-package-support.json'), 'utf-8').trim(); 115 | const expectedPackageJsonContent = fs.readFileSync(path.join(fixtureCwd, 'expected-package.json'), 'utf-8').trim(); 116 | 117 | assert.strictEqual(resultSupportContent, expectedSupportContent); 118 | assert.strictEqual(resultPackageJsonContent, expectedPackageJsonContent); 119 | 120 | cleanUpFixtures('create-with-package-json-funding-positive'); 121 | }); 122 | 123 | test('funding field as string', async () => { 124 | const { fixtureCwd, targetPackageJsonPath } = prepareFixtures('create-with-package-json-funding-string-positive'); 125 | const targetPackageSupportPath = path.join(fixtureCwd, 'package-support.json'); 126 | inquirer.prompt = (questions) => Promise.resolve({ 127 | targetVersion: 'lts', 128 | responseTime: 'time-permitting', 129 | backingType: 'get_from_funding_package_json' 130 | }); 131 | 132 | process.chdir(fixtureCwd); 133 | 134 | await support.create(false); 135 | 136 | const resultSupportContent = fs.readFileSync(targetPackageSupportPath, 'utf-8').trim(); 137 | const resultPackageJsonContent = fs.readFileSync(targetPackageJsonPath, 'utf-8').trim(); 138 | const expectedSupportContent = fs.readFileSync(path.join(fixtureCwd, 'expexted-package-support.json'), 'utf-8').trim(); 139 | const expectedPackageJsonContent = fs.readFileSync(path.join(fixtureCwd, 'expected-package.json'), 'utf-8').trim(); 140 | 141 | assert.strictEqual(resultSupportContent, expectedSupportContent); 142 | assert.strictEqual(resultPackageJsonContent, expectedPackageJsonContent); 143 | 144 | cleanUpFixtures('create-with-package-json-funding-string-positive'); 145 | }); 146 | }); 147 | 148 | // restore 149 | after(() => { 150 | inquirer.prompt = inquirerOrigin; 151 | process.chdir(__dirname); 152 | }); 153 | }); 154 | 155 | function prepareFixtures (fixtureFolderName) { 156 | const fixtureCwd = path.join(__dirname, 'fixtures', 'create', fixtureFolderName); 157 | const sourcePackageJsonPath = path.join(fixtureCwd, 'default-package.json'); 158 | const targetPackageJsonPath = path.join(fixtureCwd, 'package.json'); 159 | fs.copySync(sourcePackageJsonPath, targetPackageJsonPath); 160 | 161 | return { 162 | fixtureCwd, 163 | sourcePackageJsonPath, 164 | targetPackageJsonPath 165 | }; 166 | } 167 | 168 | function cleanUpFixtures (fixtureFolderName) { 169 | const fixtureCwd = path.join(__dirname, 'fixtures', 'create', fixtureFolderName); 170 | const targetPackageJsonPath = path.join(fixtureCwd, 'package.json'); 171 | const targetPackageSupportPath = path.join(fixtureCwd, 'package-support.json'); 172 | fs.removeSync(targetPackageJsonPath); 173 | fs.removeSync(targetPackageSupportPath); 174 | } 175 | -------------------------------------------------------------------------------- /test/fixtures/create/create-with-default-values/default-package.json: -------------------------------------------------------------------------------- 1 | { 2 | "name": "@pkgjs/create-with-default-values", 3 | "version": "0.0.1", 4 | "repository": { 5 | "type": "git", 6 | "url": "https://github.com/pkgjs/support.git" 7 | } 8 | } 9 | -------------------------------------------------------------------------------- /test/fixtures/create/create-with-default-values/expected-package.json: -------------------------------------------------------------------------------- 1 | { 2 | "name": "@pkgjs/create-with-default-values", 3 | "version": "0.0.1", 4 | "repository": { 5 | "type": "git", 6 | "url": "https://github.com/pkgjs/support.git" 7 | }, 8 | "support": true 9 | } 10 | -------------------------------------------------------------------------------- /test/fixtures/create/create-with-default-values/expexted-package-support.json: -------------------------------------------------------------------------------- 1 | { 2 | "versions": [ 3 | { 4 | "version": "*", 5 | "target": { 6 | "node": "lts" 7 | }, 8 | "response": { 9 | "type": "time-permitting" 10 | }, 11 | "backing": { 12 | "hobby": "" 13 | } 14 | } 15 | ] 16 | } 17 | -------------------------------------------------------------------------------- /test/fixtures/create/create-with-funding-yml-no-file/default-package.json: -------------------------------------------------------------------------------- 1 | { 2 | "name": "@pkgjs/create-command", 3 | "version": "0.0.1", 4 | "repository": { 5 | "type": "git", 6 | "url": "https://github.com/pkgjs/support.git" 7 | } 8 | } 9 | -------------------------------------------------------------------------------- /test/fixtures/create/create-with-funding-yml-positive/.github/FUNDING.yml: -------------------------------------------------------------------------------- 1 | patreon: test 2 | github: [test] 3 | open_collective: qwe # Replace with a single Open Collective username 4 | ko_fi: qwe # Replace with a single Ko-fi username 5 | tidelift: npm/test 6 | community_bridge: test # Replace with a single Community Bridge project-name e.g., cloud-foundry 7 | liberapay: test # Replace with a single Liberapay username 8 | issuehunt: test # Replace with a single IssueHunt username 9 | otechie: test # Replace with a single Otechie username 10 | custom: ['test1', 'test2'] # Replace with up to 4 custom sponsorship URLs e.g., ['link1', 'link2'] 11 | -------------------------------------------------------------------------------- /test/fixtures/create/create-with-funding-yml-positive/default-package.json: -------------------------------------------------------------------------------- 1 | { 2 | "name": "@pkgjs/create-command", 3 | "version": "0.0.1", 4 | "repository": { 5 | "type": "git", 6 | "url": "https://github.com/pkgjs/support.git" 7 | } 8 | } 9 | -------------------------------------------------------------------------------- /test/fixtures/create/create-with-funding-yml-positive/expected-package.json: -------------------------------------------------------------------------------- 1 | { 2 | "name": "@pkgjs/create-command", 3 | "version": "0.0.1", 4 | "repository": { 5 | "type": "git", 6 | "url": "https://github.com/pkgjs/support.git" 7 | }, 8 | "support": true 9 | } 10 | -------------------------------------------------------------------------------- /test/fixtures/create/create-with-funding-yml-positive/expexted-package-support.json: -------------------------------------------------------------------------------- 1 | { 2 | "versions": [ 3 | { 4 | "version": "*", 5 | "target": { 6 | "node": "lts" 7 | }, 8 | "response": { 9 | "type": "time-permitting" 10 | }, 11 | "backing": { 12 | "donations": [ 13 | "https://www.patreon.com/test", 14 | "https://github.com/test", 15 | "https://opencollective.com/qwe", 16 | "https://ko-fi.com/qwe", 17 | "https://tidelift.com/funding/github/npm/test", 18 | "https://funding.communitybridge.org/projects/test", 19 | "https://liberapay.com/test", 20 | "https://issuehunt.io/r/test", 21 | "https://otechie.com/test", 22 | "test1", 23 | "test2" 24 | ] 25 | } 26 | } 27 | ] 28 | } -------------------------------------------------------------------------------- /test/fixtures/create/create-with-package-json-funding-positive/default-package.json: -------------------------------------------------------------------------------- 1 | { 2 | "name": "@pkgjs/create-command", 3 | "version": "0.0.1", 4 | "repository": { 5 | "type": "git", 6 | "url": "https://github.com/pkgjs/support.git" 7 | }, 8 | "funding": [ 9 | { 10 | "type" : "individual", 11 | "url" : "http://example.com/donate" 12 | }, 13 | "http://example.com/donateAlso", 14 | { 15 | "type" : "patreon", 16 | "url" : "https://www.patreon.com/my-account" 17 | } 18 | ] 19 | } 20 | -------------------------------------------------------------------------------- /test/fixtures/create/create-with-package-json-funding-positive/expected-package.json: -------------------------------------------------------------------------------- 1 | { 2 | "name": "@pkgjs/create-command", 3 | "version": "0.0.1", 4 | "repository": { 5 | "type": "git", 6 | "url": "https://github.com/pkgjs/support.git" 7 | }, 8 | "funding": [ 9 | { 10 | "type": "individual", 11 | "url": "http://example.com/donate" 12 | }, 13 | "http://example.com/donateAlso", 14 | { 15 | "type": "patreon", 16 | "url": "https://www.patreon.com/my-account" 17 | } 18 | ], 19 | "support": true 20 | } 21 | -------------------------------------------------------------------------------- /test/fixtures/create/create-with-package-json-funding-positive/expexted-package-support.json: -------------------------------------------------------------------------------- 1 | { 2 | "versions": [ 3 | { 4 | "version": "*", 5 | "target": { 6 | "node": "lts" 7 | }, 8 | "response": { 9 | "type": "time-permitting" 10 | }, 11 | "backing": { 12 | "donations": [ 13 | "http://example.com/donate", 14 | "http://example.com/donateAlso", 15 | "https://www.patreon.com/my-account" 16 | ] 17 | } 18 | } 19 | ] 20 | } -------------------------------------------------------------------------------- /test/fixtures/create/create-with-package-json-funding-string-positive/default-package.json: -------------------------------------------------------------------------------- 1 | { 2 | "name": "@pkgjs/create-command", 3 | "version": "0.0.1", 4 | "repository": { 5 | "type": "git", 6 | "url": "https://github.com/pkgjs/support.git" 7 | }, 8 | "funding": "http://example.com/donateAlso" 9 | } 10 | -------------------------------------------------------------------------------- /test/fixtures/create/create-with-package-json-funding-string-positive/expected-package.json: -------------------------------------------------------------------------------- 1 | { 2 | "name": "@pkgjs/create-command", 3 | "version": "0.0.1", 4 | "repository": { 5 | "type": "git", 6 | "url": "https://github.com/pkgjs/support.git" 7 | }, 8 | "funding": "http://example.com/donateAlso", 9 | "support": true 10 | } 11 | -------------------------------------------------------------------------------- /test/fixtures/create/create-with-package-json-funding-string-positive/expexted-package-support.json: -------------------------------------------------------------------------------- 1 | { 2 | "versions": [ 3 | { 4 | "version": "*", 5 | "target": { 6 | "node": "lts" 7 | }, 8 | "response": { 9 | "type": "time-permitting" 10 | }, 11 | "backing": { 12 | "donations": [ 13 | "http://example.com/donateAlso" 14 | ] 15 | } 16 | } 17 | ] 18 | } -------------------------------------------------------------------------------- /test/fixtures/create/create-with-package-json-funding/default-package.json: -------------------------------------------------------------------------------- 1 | { 2 | "name": "@pkgjs/create-command", 3 | "version": "0.0.1", 4 | "repository": { 5 | "type": "git", 6 | "url": "https://github.com/pkgjs/support.git" 7 | } 8 | } 9 | -------------------------------------------------------------------------------- /test/fixtures/my-support-info.json: -------------------------------------------------------------------------------- 1 | { 2 | "versions": [ 3 | { 4 | "version": "*", 5 | "target": { 6 | "node": "supported" 7 | }, 8 | "response": { 9 | "type": "time-permitting" 10 | }, 11 | "backing": { 12 | "hobby": "https://github.com/pkgjs/support" 13 | } 14 | } 15 | ] 16 | } 17 | -------------------------------------------------------------------------------- /test/index.js: -------------------------------------------------------------------------------- 1 | 'use strict'; 2 | const { before, suite, test, run } = require('mocha'); 3 | const path = require('path'); 4 | const util = require('util'); 5 | const fs = require('fs-extra'); 6 | const Ajv = require('ajv'); 7 | const support = require('..'); 8 | const childProcess = require('child_process'); 9 | const assert = require('assert') 10 | 11 | // Delay so we can load in the example files 12 | ;(async () => { 13 | const examplesDir = path.join(__dirname, '..', 'examples'); 14 | const examples = await fs.readdir(examplesDir); 15 | 16 | suite('package support schema', async () => { 17 | let ajv; 18 | 19 | before(() => { 20 | ajv = new Ajv(); 21 | }); 22 | 23 | test('has a valid json schema', () => { 24 | ajv.compile(support.schema); 25 | const validates = ajv.validateSchema(support.schema); 26 | if (!validates) { 27 | console.error(util.inspect(ajv.errors, false, null, true)); 28 | throw new Error('Schema validation failed'); 29 | } 30 | }); 31 | 32 | examples.forEach((file) => { 33 | test(`validate examples: ${file}`, async () => { 34 | const json = await fs.readJSON(path.join(examplesDir, file)); 35 | try { 36 | support.validate(json); 37 | } catch (e) { 38 | console.error(util.inspect(e, false, null, true)); 39 | throw e; 40 | } 41 | }); 42 | }); 43 | }); 44 | 45 | const cliTestsDir = path.join(__dirname, 'cli'); 46 | const cliTests = await fs.readdir(cliTestsDir); 47 | suite('cli tests', async () => { 48 | const supportCommand = path.normalize('../../../bin/support'); 49 | cliTests.forEach((testDir) => { 50 | test(`cli test: ${testDir}`, (done) => { 51 | const cwd = path.join(__dirname, 'cli', testDir); 52 | const rawCommand = fs.readFileSync(path.join(cwd, 'command')).toString(); 53 | const command = rawCommand.replace(/\$\{cwd\}/g, cwd); 54 | const expected = safeReadFile(path.join(cwd, 'expected')); 55 | const expectedErr = safeReadFile(path.join(cwd, 'expected-errors')); 56 | 57 | childProcess.exec(`${supportCommand} ${command}`, { cwd: cwd }, (err, stdout, stderr) => { 58 | assert.strictEqual(stdout, expected); 59 | assert.strictEqual(stderr, expectedErr); 60 | done(err); 61 | }); 62 | }); 63 | }); 64 | }); 65 | 66 | run(); 67 | })(); 68 | 69 | function safeReadFile (filePath) { 70 | try { 71 | return String(fs.readFileSync(filePath)); 72 | } catch (error) { 73 | if (error.code === 'ENOENT') { 74 | return ''; 75 | } 76 | throw error; 77 | } 78 | } 79 | --------------------------------------------------------------------------------