From c5c3832ef9a10c5cd1af239f8694c94909366c57 Mon Sep 17 00:00:00 2001 From: Titus Wormer Date: Fri, 8 Oct 2021 13:09:59 +0200 Subject: [PATCH] Mark `no-auto-link-without-protocol` as deprecated MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit * Add internal support for deprecated packages in tooling * Remove `remark-lint-no-auto-link-without-protocol` from presets * Add info to `remark-lint-no-auto-link-without-protocol` on why it’s deprecated Related to remarkjs/remark#863. --- doc/rules.md | 1 - .../index.js | 18 +- .../package.json | 2 +- .../readme.md | 115 +--- .../index.js | 6 +- .../package.json | 1 - .../readme.md | 1 - .../remark-preset-lint-recommended/index.js | 3 - .../package.json | 1 - .../remark-preset-lint-recommended/readme.md | 1 - script/build-rules.js | 544 +++++++++--------- script/plugin/list-of-rules.js | 65 ++- script/util/rule.js | 14 +- 13 files changed, 337 insertions(+), 435 deletions(-) diff --git a/doc/rules.md b/doc/rules.md index 1da98dbf..cbaedd04 100644 --- a/doc/rules.md +++ b/doc/rules.md @@ -107,7 +107,6 @@ Rules][external]. * [`list-item-spacing`](https://github.com/remarkjs/remark-lint/tree/main/packages/remark-lint-list-item-spacing) — warn when list looseness is incorrect * [`maximum-heading-length`](https://github.com/remarkjs/remark-lint/tree/main/packages/remark-lint-maximum-heading-length) — warn when headings are too long * [`maximum-line-length`](https://github.com/remarkjs/remark-lint/tree/main/packages/remark-lint-maximum-line-length) — warn when lines are too long -* [`no-auto-link-without-protocol`](https://github.com/remarkjs/remark-lint/tree/main/packages/remark-lint-no-auto-link-without-protocol) — warn for angle bracketed links without protocol * [`no-blockquote-without-marker`](https://github.com/remarkjs/remark-lint/tree/main/packages/remark-lint-no-blockquote-without-marker) — warn when blank lines without markers (\`>\`) are found in a block quote * [`no-consecutive-blank-lines`](https://github.com/remarkjs/remark-lint/tree/main/packages/remark-lint-no-consecutive-blank-lines) — warn for too many consecutive blank lines * [`no-duplicate-defined-urls`](https://github.com/remarkjs/remark-lint/tree/main/packages/remark-lint-no-duplicate-defined-urls) — warn on definitions that define the same urls diff --git a/packages/remark-lint-no-auto-link-without-protocol/index.js b/packages/remark-lint-no-auto-link-without-protocol/index.js index 1dd43bd4..e0149d82 100644 --- a/packages/remark-lint-no-auto-link-without-protocol/index.js +++ b/packages/remark-lint-no-auto-link-without-protocol/index.js @@ -3,18 +3,12 @@ * @copyright 2015 Titus Wormer * @license MIT * @module no-auto-link-without-protocol - * @fileoverview - * Warn for autolinks without protocol. - * Autolinks are URLs enclosed in `<` (less than) and `>` (greater than) - * characters. - * - * ## Fix - * - * [`remark-stringify`](https://github.com/remarkjs/remark/tree/HEAD/packages/remark-stringify) - * adds a protocol where needed. - * - * See [Using remark to fix your Markdown](https://github.com/remarkjs/remark-lint#using-remark-to-fix-your-markdown) - * on how to automatically fix warnings for this rule. + * @deprecated + * This rule is no longer recommended for use. + * With CommonMark, all autolinks (except for emails) are required to have a + * protocol. + * Otherwise they don’t parse. + * The previous suggestion to add a protocol to email autolinks was wrong. * * @example * {"name": "ok.md"} diff --git a/packages/remark-lint-no-auto-link-without-protocol/package.json b/packages/remark-lint-no-auto-link-without-protocol/package.json index 28f585cd..1775e40f 100644 --- a/packages/remark-lint-no-auto-link-without-protocol/package.json +++ b/packages/remark-lint-no-auto-link-without-protocol/package.json @@ -1,7 +1,7 @@ { "name": "remark-lint-no-auto-link-without-protocol", "version": "3.1.0", - "description": "remark-lint rule to warn for angle bracketed links without protocol", + "description": "Deprecated", "license": "MIT", "keywords": [ "remark", diff --git a/packages/remark-lint-no-auto-link-without-protocol/readme.md b/packages/remark-lint-no-auto-link-without-protocol/readme.md index 3bde196b..913a94bb 100644 --- a/packages/remark-lint-no-auto-link-without-protocol/readme.md +++ b/packages/remark-lint-no-auto-link-without-protocol/readme.md @@ -10,112 +10,11 @@ [![Backers][backers-badge]][collective] [![Chat][chat-badge]][chat] -Warn for autolinks without protocol. -Autolinks are URLs enclosed in `<` (less than) and `>` (greater than) -characters. - -## Fix - -[`remark-stringify`](https://github.com/remarkjs/remark/tree/HEAD/packages/remark-stringify) -adds a protocol where needed. - -See [Using remark to fix your Markdown](https://github.com/remarkjs/remark-lint#using-remark-to-fix-your-markdown) -on how to automatically fix warnings for this rule. - -## Presets - -This rule is included in the following presets: - -| Preset | Setting | -| - | - | -| [`remark-preset-lint-markdown-style-guide`](https://github.com/remarkjs/remark-lint/tree/main/packages/remark-preset-lint-markdown-style-guide) | | -| [`remark-preset-lint-recommended`](https://github.com/remarkjs/remark-lint/tree/main/packages/remark-preset-lint-recommended) | | - -## Example - -##### `ok.md` - -###### In - -```markdown - - - -Most Markdown vendors don’t recognize the following as a link: - -``` - -###### Out - -No messages. - -##### `not-ok.md` - -###### In - -```markdown - -``` - -###### Out - -```text -1:1-1:14: All automatic links must start with a protocol -``` - -## Install - -This package is [ESM only][esm]: -Node 12+ is needed to use it and it must be `imported`ed instead of `required`d. - -[npm][]: - -```sh -npm install remark-lint-no-auto-link-without-protocol -``` - -This package exports no identifiers. -The default export is `remarkLintNoAutoLinkWithoutProtocol`. - -## Use - -You probably want to use it on the CLI through a config file: - -```diff - … - "remarkConfig": { - "plugins": [ - … - "lint", -+ "lint-no-auto-link-without-protocol", - … - ] - } - … -``` - -Or use it on the CLI directly - -```sh -remark -u lint -u lint-no-auto-link-without-protocol readme.md -``` - -Or use this on the API: - -```diff - import {remark} from 'remark' - import {reporter} from 'vfile-reporter' - import remarkLint from 'remark-lint' - import remarkLintNoAutoLinkWithoutProtocol from 'remark-lint-no-auto-link-without-protocol' - - remark() - .use(remarkLint) -+ .use(remarkLintNoAutoLinkWithoutProtocol) - .process('_Emphasis_ and **importance**') - .then((file) => { - console.error(reporter(file)) - }) -``` +This rule is no longer recommended for use. +With CommonMark, all autolinks (except for emails) are required to have a +protocol. +Otherwise they don’t parse. +The previous suggestion to add a protocol to email autolinks was wrong. ## Contribute @@ -157,10 +56,6 @@ abide by its terms. [chat]: https://github.com/remarkjs/remark/discussions -[esm]: https://gist.github.com/sindresorhus/a39789f98801d908bbc7ff3ecc99d99c - -[npm]: https://docs.npmjs.com/cli/install - [health]: https://github.com/remarkjs/.github [contributing]: https://github.com/remarkjs/.github/blob/HEAD/contributing.md diff --git a/packages/remark-preset-lint-markdown-style-guide/index.js b/packages/remark-preset-lint-markdown-style-guide/index.js index fb31c601..42543a8c 100644 --- a/packages/remark-preset-lint-markdown-style-guide/index.js +++ b/packages/remark-preset-lint-markdown-style-guide/index.js @@ -144,7 +144,6 @@ import remarkLintStrongMarker from 'remark-lint-strong-marker' import remarkLintEmphasisMarker from 'remark-lint-emphasis-marker' import remarkLintNoEmphasisAsHeading from 'remark-lint-no-emphasis-as-heading' import remarkLintNoLiteralUrls from 'remark-lint-no-literal-urls' -import remarkLintNoAutoLinkWithoutProtocol from 'remark-lint-no-auto-link-without-protocol' /** @type {Preset} */ const remarkPresetLintMarkdownStyleGuide = { @@ -281,10 +280,7 @@ const remarkPresetLintMarkdownStyleGuide = { remarkLintNoEmphasisAsHeading, // http://www.cirosantilli.com/markdown-style-guide/#automatic-links-without-angle-brackets - remarkLintNoLiteralUrls, - - // http://www.cirosantilli.com/markdown-style-guide/#content-of-automatic-links - remarkLintNoAutoLinkWithoutProtocol + remarkLintNoLiteralUrls // http://www.cirosantilli.com/markdown-style-guide/#email-automatic-links. // Not checked. diff --git a/packages/remark-preset-lint-markdown-style-guide/package.json b/packages/remark-preset-lint-markdown-style-guide/package.json index 9ca95859..e1a0e2ee 100644 --- a/packages/remark-preset-lint-markdown-style-guide/package.json +++ b/packages/remark-preset-lint-markdown-style-guide/package.json @@ -54,7 +54,6 @@ "remark-lint-list-item-spacing": "^4.0.0", "remark-lint-maximum-heading-length": "^3.0.0", "remark-lint-maximum-line-length": "^3.0.0", - "remark-lint-no-auto-link-without-protocol": "^3.0.0", "remark-lint-no-blockquote-without-marker": "^5.0.0", "remark-lint-no-consecutive-blank-lines": "^4.0.0", "remark-lint-no-duplicate-headings": "^3.0.0", diff --git a/packages/remark-preset-lint-markdown-style-guide/readme.md b/packages/remark-preset-lint-markdown-style-guide/readme.md index 04ffc439..652cba72 100644 --- a/packages/remark-preset-lint-markdown-style-guide/readme.md +++ b/packages/remark-preset-lint-markdown-style-guide/readme.md @@ -154,7 +154,6 @@ This preset configures [`remark-lint`](https://github.com/remarkjs/remark-lint) | [`remark-lint-emphasis-marker`](https://github.com/remarkjs/remark-lint/tree/main/packages/remark-lint-emphasis-marker) | `'*'` | | [`remark-lint-no-emphasis-as-heading`](https://github.com/remarkjs/remark-lint/tree/main/packages/remark-lint-no-emphasis-as-heading) | | | [`remark-lint-no-literal-urls`](https://github.com/remarkjs/remark-lint/tree/main/packages/remark-lint-no-literal-urls) | | -| [`remark-lint-no-auto-link-without-protocol`](https://github.com/remarkjs/remark-lint/tree/main/packages/remark-lint-no-auto-link-without-protocol) | | ## Install diff --git a/packages/remark-preset-lint-recommended/index.js b/packages/remark-preset-lint-recommended/index.js index e3b96123..36ca7710 100644 --- a/packages/remark-preset-lint-recommended/index.js +++ b/packages/remark-preset-lint-recommended/index.js @@ -12,7 +12,6 @@ import remarkLint from 'remark-lint' import remarkLintFinalNewline from 'remark-lint-final-newline' import remarkLintListItemBulletIndent from 'remark-lint-list-item-bullet-indent' import remarkLintListItemIndent from 'remark-lint-list-item-indent' -import remarkLintNoAutoLinkWithoutProtocol from 'remark-lint-no-auto-link-without-protocol' import remarkLintNoBlockquoteWithoutMarker from 'remark-lint-no-blockquote-without-marker' import remarkLintNoLiteralUrls from 'remark-lint-no-literal-urls' import remarkLintOrderedListMarkerStyle from 'remark-lint-ordered-list-marker-style' @@ -34,8 +33,6 @@ const remarkPresetLintRecommended = { // Rendering across vendors differs greatly if using other styles. remarkLintListItemBulletIndent, [remarkLintListItemIndent, 'tab-size'], - // Differs or unsupported across vendors. - remarkLintNoAutoLinkWithoutProtocol, remarkLintNoBlockquoteWithoutMarker, remarkLintNoLiteralUrls, [remarkLintOrderedListMarkerStyle, '.'], diff --git a/packages/remark-preset-lint-recommended/package.json b/packages/remark-preset-lint-recommended/package.json index 0eb46643..069c2fb6 100644 --- a/packages/remark-preset-lint-recommended/package.json +++ b/packages/remark-preset-lint-recommended/package.json @@ -38,7 +38,6 @@ "remark-lint-hard-break-spaces": "^3.0.0", "remark-lint-list-item-bullet-indent": "^4.0.0", "remark-lint-list-item-indent": "^3.0.0", - "remark-lint-no-auto-link-without-protocol": "^3.0.0", "remark-lint-no-blockquote-without-marker": "^5.0.0", "remark-lint-no-duplicate-definitions": "^3.0.0", "remark-lint-no-heading-content-indent": "^4.0.0", diff --git a/packages/remark-preset-lint-recommended/readme.md b/packages/remark-preset-lint-recommended/readme.md index 09c4b30f..4ed7b0f4 100644 --- a/packages/remark-preset-lint-recommended/readme.md +++ b/packages/remark-preset-lint-recommended/readme.md @@ -22,7 +22,6 @@ This preset configures [`remark-lint`](https://github.com/remarkjs/remark-lint) | [`remark-lint-final-newline`](https://github.com/remarkjs/remark-lint/tree/main/packages/remark-lint-final-newline) | | | [`remark-lint-list-item-bullet-indent`](https://github.com/remarkjs/remark-lint/tree/main/packages/remark-lint-list-item-bullet-indent) | | | [`remark-lint-list-item-indent`](https://github.com/remarkjs/remark-lint/tree/main/packages/remark-lint-list-item-indent) | `'tab-size'` | -| [`remark-lint-no-auto-link-without-protocol`](https://github.com/remarkjs/remark-lint/tree/main/packages/remark-lint-no-auto-link-without-protocol) | | | [`remark-lint-no-blockquote-without-marker`](https://github.com/remarkjs/remark-lint/tree/main/packages/remark-lint-no-blockquote-without-marker) | | | [`remark-lint-no-literal-urls`](https://github.com/remarkjs/remark-lint/tree/main/packages/remark-lint-no-literal-urls) | | | [`remark-lint-ordered-list-marker-style`](https://github.com/remarkjs/remark-lint/tree/main/packages/remark-lint-ordered-list-marker-style) | `'.'` | diff --git a/script/build-rules.js b/script/build-rules.js index ea9eb19c..ba11754f 100644 --- a/script/build-rules.js +++ b/script/build-rules.js @@ -179,321 +179,327 @@ presets(root).then((presetObjects) => { } ] }, - ...descriptionContent, - { - type: 'heading', - depth: 2, - children: [{type: 'text', value: 'Presets'}] - } + ...descriptionContent ] - if (includes.length === 0) { + if (!info.deprecated) { children.push({ - type: 'paragraph', - children: [ - { - type: 'text', - value: 'This rule is not included in any default preset' - } - ] + type: 'heading', + depth: 2, + children: [{type: 'text', value: 'Presets'}] }) - } else { - children.push( - { + + if (includes.length === 0) { + children.push({ type: 'paragraph', children: [ { type: 'text', - value: 'This rule is included in the following presets:' + value: 'This rule is not included in any default preset' } ] - }, - { - type: 'table', - align: [], - children: [ - { - type: 'tableRow', - children: [ - { - type: 'tableCell', - children: [{type: 'text', value: 'Preset'}] - }, - { - type: 'tableCell', - children: [{type: 'text', value: 'Setting'}] - } - ] - }, - ...includes.map((preset) => { - const option = preset.packages[basename] - - /** @type {TableContent} */ - const row = { + }) + } else { + children.push( + { + type: 'paragraph', + children: [ + { + type: 'text', + value: 'This rule is included in the following presets:' + } + ] + }, + { + type: 'table', + align: [], + children: [ + { type: 'tableRow', children: [ { type: 'tableCell', - children: [ - { - type: 'link', - url: remote + '/tree/main/packages/' + preset.name, - title: null, - children: [{type: 'inlineCode', value: preset.name}] - } - ] + children: [{type: 'text', value: 'Preset'}] }, { type: 'tableCell', - children: option - ? [{type: 'inlineCode', value: inspect(option)}] - : [] + children: [{type: 'text', value: 'Setting'}] } ] - } + }, + ...includes.map((preset) => { + const option = preset.packages[basename] - return row - }) - ] - } - ) - } + /** @type {TableContent} */ + const row = { + type: 'tableRow', + children: [ + { + type: 'tableCell', + children: [ + { + type: 'link', + url: remote + '/tree/main/packages/' + preset.name, + title: null, + children: [{type: 'inlineCode', value: preset.name}] + } + ] + }, + { + type: 'tableCell', + children: option + ? [{type: 'inlineCode', value: inspect(option)}] + : [] + } + ] + } - let first = true - /** @type {string} */ - let setting - - for (setting in tests) { - if (own.call(tests, setting)) { - const fixtures = tests[setting] - - if (first) { - children.push({ - type: 'heading', - depth: 2, - children: [{type: 'text', value: 'Example'}] - }) - first = false - } + return row + }) + ] + } + ) + } - /** @type {string} */ - let fileName + let first = true + /** @type {string} */ + let setting - for (fileName in fixtures) { - if (own.call(fixtures, fileName)) { - const fixture = fixtures[fileName] - const label = inspect(JSON.parse(setting)) - let clean = fixture.input + for (setting in tests) { + if (own.call(tests, setting)) { + const fixtures = tests[setting] + if (first) { children.push({ type: 'heading', - depth: 5, - children: [{type: 'inlineCode', value: fileName}] + depth: 2, + children: [{type: 'text', value: 'Example'}] }) + first = false + } - if (label !== 'true') { - children.push({ - type: 'paragraph', - children: [ - {type: 'text', value: 'When configured with '}, - {type: 'inlineCode', value: label}, - {type: 'text', value: '.'} - ] - }) - } + /** @type {string} */ + let fileName + + for (fileName in fixtures) { + if (own.call(fixtures, fileName)) { + const fixture = fixtures[fileName] + const label = inspect(JSON.parse(setting)) + let clean = fixture.input - if ( - fixture.input !== null && - fixture.input !== undefined && - fixture.input.trim() !== '' - ) { children.push({ type: 'heading', - depth: 6, - children: [{type: 'text', value: 'In'}] + depth: 5, + children: [{type: 'inlineCode', value: fileName}] }) - if (fixture.gfm) { - hasGfm = true + if (label !== 'true') { children.push({ type: 'paragraph', children: [ - {type: 'text', value: 'Note: this example uses '}, - { - type: 'linkReference', - label: 'GFM', - identifier: 'gfm', - referenceType: 'collapsed', - children: [{type: 'text', value: 'GFM'}] - }, + {type: 'text', value: 'When configured with '}, + {type: 'inlineCode', value: label}, {type: 'text', value: '.'} ] }) } - let index = -1 - while (++index < characters.length) { - const char = characters[index] - const next = clean.replace(char.in, char.out) + if ( + fixture.input !== null && + fixture.input !== undefined && + fixture.input.trim() !== '' + ) { + children.push({ + type: 'heading', + depth: 6, + children: [{type: 'text', value: 'In'}] + }) - if (clean !== next) { + if (fixture.gfm) { + hasGfm = true children.push({ type: 'paragraph', children: [ - {type: 'text', value: 'Note: '}, - {type: 'inlineCode', value: char.char}, - {type: 'text', value: ' represents ' + char.name + '.'} + {type: 'text', value: 'Note: this example uses '}, + { + type: 'linkReference', + label: 'GFM', + identifier: 'gfm', + referenceType: 'collapsed', + children: [{type: 'text', value: 'GFM'}] + }, + {type: 'text', value: '.'} ] }) + } - clean = next + let index = -1 + while (++index < characters.length) { + const char = characters[index] + const next = clean.replace(char.in, char.out) + + if (clean !== next) { + children.push({ + type: 'paragraph', + children: [ + {type: 'text', value: 'Note: '}, + {type: 'inlineCode', value: char.char}, + {type: 'text', value: ' represents ' + char.name + '.'} + ] + }) + + clean = next + } } + + children.push({ + type: 'code', + lang: 'markdown', + value: fixture.input + }) } children.push({ - type: 'code', - lang: 'markdown', - value: fixture.input + type: 'heading', + depth: 6, + children: [{type: 'text', value: 'Out'}] }) - } - children.push({ - type: 'heading', - depth: 6, - children: [{type: 'text', value: 'Out'}] - }) - - if (fixture.output.length === 0) { - children.push({ - type: 'paragraph', - children: [{type: 'text', value: 'No messages.'}] - }) - } else { - children.push({ - type: 'code', - lang: 'text', - value: fixture.output.join('\n') - }) + if (fixture.output.length === 0) { + children.push({ + type: 'paragraph', + children: [{type: 'text', value: 'No messages.'}] + }) + } else { + children.push({ + type: 'code', + lang: 'text', + value: fixture.output.join('\n') + }) + } } } } } + + children.push( + { + type: 'heading', + depth: 2, + children: [{type: 'text', value: 'Install'}] + }, + { + type: 'paragraph', + children: [ + {type: 'text', value: 'This package is '}, + { + type: 'linkReference', + identifier: 'esm', + referenceType: 'full', + children: [{type: 'text', value: 'ESM only'}] + }, + { + type: 'text', + value: ':\nNode 12+ is needed to use it and it must be ' + }, + {type: 'inlineCode', value: 'imported'}, + {type: 'text', value: 'ed instead of '}, + {type: 'inlineCode', value: 'required'}, + {type: 'text', value: 'd.'} + ] + }, + { + type: 'paragraph', + children: [ + { + type: 'linkReference', + identifier: 'npm', + referenceType: 'collapsed', + children: [{type: 'text', value: 'npm'}] + }, + {type: 'text', value: ':'} + ] + }, + {type: 'code', lang: 'sh', value: 'npm install ' + basename}, + { + type: 'paragraph', + children: [ + { + type: 'text', + value: + 'This package exports no identifiers.\nThe default export is ' + }, + { + type: 'inlineCode', + value: basename.replace(/-(\w)/g, (_, /** @type {string} */ $1) => + $1.toUpperCase() + ) + }, + {type: 'text', value: '.'} + ] + }, + {type: 'heading', depth: 2, children: [{type: 'text', value: 'Use'}]}, + { + type: 'paragraph', + children: [ + { + type: 'text', + value: + 'You probably want to use it on the CLI through a config file:' + } + ] + }, + { + type: 'code', + lang: 'diff', + value: [ + ' …', + ' "remarkConfig": {', + ' "plugins": [', + ' …', + ' "lint",', + '+ "' + short + '",', + ' …', + ' ]', + ' }', + ' …' + ].join('\n') + }, + { + type: 'paragraph', + children: [{type: 'text', value: 'Or use it on the CLI directly'}] + }, + { + type: 'code', + lang: 'sh', + value: 'remark -u lint -u ' + short + ' readme.md' + }, + { + type: 'paragraph', + children: [{type: 'text', value: 'Or use this on the API:'}] + }, + { + type: 'code', + lang: 'diff', + value: [ + " import {remark} from 'remark'", + " import {reporter} from 'vfile-reporter'", + " import remarkLint from 'remark-lint'", + ' import ' + camelcased + " from '" + basename + "'", + '', + ' remark()', + ' .use(remarkLint)', + '+ .use(' + camelcased + ')', + " .process('_Emphasis_ and **importance**')", + ' .then((file) => {', + ' console.error(reporter(file))', + ' })' + ].join('\n') + } + ) } children.push( - { - type: 'heading', - depth: 2, - children: [{type: 'text', value: 'Install'}] - }, - { - type: 'paragraph', - children: [ - {type: 'text', value: 'This package is '}, - { - type: 'linkReference', - identifier: 'esm', - referenceType: 'full', - children: [{type: 'text', value: 'ESM only'}] - }, - { - type: 'text', - value: ':\nNode 12+ is needed to use it and it must be ' - }, - {type: 'inlineCode', value: 'imported'}, - {type: 'text', value: 'ed instead of '}, - {type: 'inlineCode', value: 'required'}, - {type: 'text', value: 'd.'} - ] - }, - { - type: 'paragraph', - children: [ - { - type: 'linkReference', - identifier: 'npm', - referenceType: 'collapsed', - children: [{type: 'text', value: 'npm'}] - }, - {type: 'text', value: ':'} - ] - }, - {type: 'code', lang: 'sh', value: 'npm install ' + basename}, - { - type: 'paragraph', - children: [ - { - type: 'text', - value: - 'This package exports no identifiers.\nThe default export is ' - }, - { - type: 'inlineCode', - value: basename.replace(/-(\w)/g, (_, /** @type {string} */ $1) => - $1.toUpperCase() - ) - }, - {type: 'text', value: '.'} - ] - }, - {type: 'heading', depth: 2, children: [{type: 'text', value: 'Use'}]}, - { - type: 'paragraph', - children: [ - { - type: 'text', - value: - 'You probably want to use it on the CLI through a config file:' - } - ] - }, - { - type: 'code', - lang: 'diff', - value: [ - ' …', - ' "remarkConfig": {', - ' "plugins": [', - ' …', - ' "lint",', - '+ "' + short + '",', - ' …', - ' ]', - ' }', - ' …' - ].join('\n') - }, - { - type: 'paragraph', - children: [{type: 'text', value: 'Or use it on the CLI directly'}] - }, - { - type: 'code', - lang: 'sh', - value: 'remark -u lint -u ' + short + ' readme.md' - }, - { - type: 'paragraph', - children: [{type: 'text', value: 'Or use this on the API:'}] - }, - { - type: 'code', - lang: 'diff', - value: [ - " import {remark} from 'remark'", - " import {reporter} from 'vfile-reporter'", - " import remarkLint from 'remark-lint'", - ' import ' + camelcased + " from '" + basename + "'", - '', - ' remark()', - ' .use(remarkLint)', - '+ .use(' + camelcased + ')', - " .process('_Emphasis_ and **importance**')", - ' .then((file) => {', - ' console.error(reporter(file))', - ' })' - ].join('\n') - }, { type: 'heading', depth: 2, @@ -630,17 +636,25 @@ presets(root).then((presetObjects) => { type: 'definition', identifier: 'chat', url: 'https://github.com/remarkjs/remark/discussions' - }, - { - type: 'definition', - identifier: 'esm', - url: 'https://gist.github.com/sindresorhus/a39789f98801d908bbc7ff3ecc99d99c' - }, - { - type: 'definition', - identifier: 'npm', - url: 'https://docs.npmjs.com/cli/install' - }, + } + ) + + if (!info.deprecated) { + children.push( + { + type: 'definition', + identifier: 'esm', + url: 'https://gist.github.com/sindresorhus/a39789f98801d908bbc7ff3ecc99d99c' + }, + { + type: 'definition', + identifier: 'npm', + url: 'https://docs.npmjs.com/cli/install' + } + ) + } + + children.push( { type: 'definition', identifier: 'health', diff --git a/script/plugin/list-of-rules.js b/script/plugin/list-of-rules.js index 74c19f26..79ab251c 100644 --- a/script/plugin/list-of-rules.js +++ b/script/plugin/list-of-rules.js @@ -23,38 +23,43 @@ export default function listOfRules() { type: 'list', ordered: false, spread: false, - children: rules(root).map((basename) => { - const name = basename.slice('remark-lint-'.length) - /** @type {PackageJson} */ - const pack = JSON.parse( - String(fs.readFileSync(path.join(root, basename, 'package.json'))) - ) - const description = String(pack.description || '').replace( - /^remark-lint rule to ?/i, - '' - ) + children: rules(root) + .map((basename) => { + const name = basename.slice('remark-lint-'.length) + /** @type {PackageJson} */ + const pack = JSON.parse( + String(fs.readFileSync(path.join(root, basename, 'package.json'))) + ) + const description = String(pack.description || '').replace( + /^remark-lint rule to ?/i, + '' + ) + const deprecated = /^deprecated/i.test(description) - /** @type {ListItem} */ - const item = { - type: 'listItem', - spread: false, - children: [ - { - type: 'paragraph', - children: [ - { - type: 'link', - url: repoUrl(pack), - children: [{type: 'inlineCode', value: name}] - }, - {type: 'text', value: ' — ' + description} - ] - } - ] - } + /** @type {ListItem} */ + const item = { + type: 'listItem', + spread: false, + children: deprecated + ? [] + : [ + { + type: 'paragraph', + children: [ + { + type: 'link', + url: repoUrl(pack), + children: [{type: 'inlineCode', value: name}] + }, + {type: 'text', value: ' — ' + description} + ] + } + ] + } - return item - }) + return item + }) + .filter((d) => d.children.length > 0) } return [start, list, end] diff --git a/script/util/rule.js b/script/util/rule.js index 9c961bfc..f70e29f9 100755 --- a/script/util/rule.js +++ b/script/util/rule.js @@ -2,6 +2,7 @@ * @typedef Rule * @property {string} ruleId * @property {string} description + * @property {boolean} deprecated * @property {Record} tests * @property {string} filePath * @@ -26,6 +27,7 @@ import strip from 'strip-indent' * @param {string} filePath * @returns {Rule} */ +/* eslint-disable-next-line complexity */ export function rule(filePath) { const ruleId = path.basename(filePath).slice('remark-lint-'.length) /** @type {Record} */ @@ -34,6 +36,7 @@ export function rule(filePath) { const tags = parse(code, {spacing: 'preserve'})[0].tags const moduleTag = tags.find((d) => d.tag === 'module') const fileoverviewTag = tags.find((d) => d.tag === 'fileoverview') + const deprecatedTag = tags.find((d) => d.tag === 'deprecated') /* c8 ignore next 3 */ if (!moduleTag) { @@ -41,12 +44,14 @@ export function rule(filePath) { } /* c8 ignore next 3 */ - if (!fileoverviewTag) { - throw new Error('Expected `@fileoverview` in JSDoc') + if (!fileoverviewTag && !deprecatedTag) { + throw new Error('Expected `@fileoverview` (or `@deprecated`) in JSDoc') } const name = moduleTag.name - let description = fileoverviewTag.description + let description = + (fileoverviewTag && fileoverviewTag.description) || + (deprecatedTag && deprecatedTag.description) /* c8 ignore next 3 */ if (name !== ruleId) { @@ -55,7 +60,7 @@ export function rule(filePath) { /* c8 ignore next 3 */ if (!description) { - throw new Error(ruleId + ' is missing a `@fileoverview`') + throw new Error(ruleId + ' is missing a `@fileoverview` or `@deprecated`') } description = strip(description) @@ -64,6 +69,7 @@ export function rule(filePath) { const result = { ruleId, description: description.trim(), + deprecated: Boolean(deprecatedTag), tests, filePath }