feat(markdown)!: replace markdown-it-attrs with @mdit/plugin-attrs

The `fence` rule is disabled by default, replacing the patch we carried
to stop curly attributes from consuming code block meta (line
highlighting etc.). Drops both attrs patches and
`@types/markdown-it-attrs`.

BREAKING CHANGE: `markdown.attrs` options are now typed by
`@mdit/plugin-attrs`: `leftDelimiter`, `rightDelimiter`, and
`allowedAttributes` are renamed to `left`, `right`, and `allowed`. A
`rule` option is available for toggling individual attribute rules
(VitePress disables `fence` by default).
Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
pull/5335/head
Divyansh Singh 2 months ago
parent 7c09583eaa
commit 18380b0eb7

@ -21,7 +21,7 @@ describe('node/config', () => {
{
markdown: {
attrs: {
allowedAttributes: ['id']
allowed: ['id']
},
async preConfig() {
calls.push('extended-pre')
@ -35,7 +35,7 @@ describe('node/config', () => {
expect(merged.markdown?.lineNumbers).toBe(true)
expect(merged.markdown?.attrs).toEqual({
allowedAttributes: ['id']
allowed: ['id']
})
await merged.markdown?.preConfig?.(md)

@ -1,5 +1,5 @@
import { anchor as anchorPlugin } from '@mdit/plugin-anchor'
import attrsPlugin from 'markdown-it-attrs'
import { attrs as attrsPlugin } from '@mdit/plugin-attrs'
import { MarkdownItAsync } from 'markdown-it-async'
import {
createMarkdownRenderer,

@ -1,6 +1,6 @@
import path from 'node:path'
import { MarkdownItAsync } from 'markdown-it-async'
import attrsPlugin from 'markdown-it-attrs'
import { attrs as attrsPlugin } from '@mdit/plugin-attrs'
import { imagePlugin, type Options } from 'node/markdown/plugins/image'
const srcDir = path.resolve(import.meta.dirname, '../../../../e2e')

@ -261,7 +261,7 @@ console.log('Hello, VitePress!')
### Additional Attributes
You can add additional attributes to the custom containers. We use [markdown-it-attrs](https://github.com/arve0/markdown-it-attrs) for this feature, and it is supported on almost all markdown elements. For example, you can set the `open` attribute to make the details block open by default:
You can add additional attributes to the custom containers. We use [@mdit/plugin-attrs](https://mdit-plugins.github.io/attrs.html) for this feature, and it is supported on almost all markdown elements. For example, you can set the `open` attribute to make the details block open by default:
**Input**

@ -229,7 +229,7 @@ export default defineConfig({
### 追加属性 {#additional-attributes}
カスタムコンテナには追加の属性を付与できます。この機能には [markdown-it-attrs](https://github.com/arve0/markdown-it-attrs) を使用しており、ほぼすべての Markdown 要素でサポートされます。たとえば `open` 属性を付けると、details ブロックをデフォルトで開いた状態にできます。
カスタムコンテナには追加の属性を付与できます。この機能には [@mdit/plugin-attrs](https://mdit-plugins.github.io/attrs.html) を使用しており、ほぼすべての Markdown 要素でサポートされます。たとえば `open` 属性を付けると、details ブロックをデフォルトで開いた状態にできます。
**入力**

@ -235,7 +235,7 @@ export default defineConfig({
### Дополнительные атрибуты {#additional-attributes}
Вы можете добавить дополнительные атрибуты к пользовательским контейнерам. Мы используем [markdown-it-attrs](https://github.com/arve0/markdown-it-attrs) для этой функции, и она поддерживается почти для всех элементов Markdown. Например, можно установить атрибут `open`, чтобы сделать блок подробностей открытым по умолчанию:
Вы можете добавить дополнительные атрибуты к пользовательским контейнерам. Мы используем [@mdit/plugin-attrs](https://mdit-plugins.github.io/attrs.html) для этой функции, и она поддерживается почти для всех элементов Markdown. Например, можно установить атрибут `open`, чтобы сделать блок подробностей открытым по умолчанию:
**Разметка**

@ -130,6 +130,7 @@
"@mdit-vue/plugin-toc": "^3.0.2",
"@mdit-vue/shared": "^3.0.2",
"@mdit/plugin-anchor": "^1.1.1",
"@mdit/plugin-attrs": "^1.0.2",
"@mdit/plugin-emoji": "^1.1.0",
"@polka/compression": "^1.0.0-next.28",
"@rollup/plugin-alias": "^6.0.0",
@ -140,7 +141,6 @@
"@types/cross-spawn": "^6.0.6",
"@types/lodash.template": "^4.5.3",
"@types/mark.js": "^8.11.12",
"@types/markdown-it-attrs": "^4.1.3",
"@types/markdown-it-container": "^4.0.0",
"@types/minimist": "^1.2.5",
"@types/node": "^25.9.4",
@ -159,7 +159,6 @@
"lru-cache": "^11.5.1",
"markdown-it": "^14.2.0",
"markdown-it-async": "^2.2.0",
"markdown-it-attrs": "4.3.1",
"markdown-it-cjk-friendly": "^2.0.2",
"markdown-it-container": "^4.0.0",
"markdown-it-mathjax3": "^4.3.2",

@ -1,23 +0,0 @@
diff --git a/index.d.ts b/index.d.ts
index 41d4a858c6ece5a61a2088733cf8b333b45603d8..2cb19bcd8fc76ae82ebe87af742916e17f49334b 100644
--- a/index.d.ts
+++ b/index.d.ts
@@ -1,3 +1,15 @@
-import MarkdownIt = require("markdown-it");
-declare function attrs(md: MarkdownIt): void;
-export = attrs;
+import type MarkdownIt from 'markdown-it'
+
+export interface MarkdownItAttrsOptions {
+ /** left delimiter, default is `{`(left curly bracket) */
+ leftDelimiter?: string
+ /** right delimiter, default is `}`(right curly bracket) */
+ rightDelimiter?: string
+ /** rule of allowed attribute, empty means no limit */
+ allowedAttributes?: (string | RegExp)[]
+}
+
+export default function attrsPlugin(
+ md: MarkdownIt,
+ options?: MarkdownItAttrsOptions
+): void

@ -1,14 +0,0 @@
diff --git a/patterns.js b/patterns.js
index e56a3b785df29e726194f2b30e86bb19a78ef902..e1f6211b92cbb2bbbe2a3c317dd9e5f1f41ab8d1 100644
--- a/patterns.js
+++ b/patterns.js
@@ -28,7 +28,8 @@ module.exports = options => {
{
shift: 0,
block: true,
- info: utils.hasDelimiters('end', options)
+ info: utils.hasDelimiters('end', options),
+ markup: (str) => !/^[`~]{3,}$/.test(str)
}
],
transform: (tokens, i) => {

@ -8,15 +8,9 @@ overrides:
ora>string-width: ^5
patchedDependencies:
'@types/markdown-it-attrs':
hash: ef05082c7886d283042ddf9103f1408fc36fd8665ef278c82b3da0659441dfb6
path: patches/@types__markdown-it-attrs@4.1.3.patch
'@types/mdurl@2.0.0':
hash: 3460e7d18ce390685cf4b8d8237fb20df9ad952c1336f479995a508a6395bfa4
path: patches/@types__mdurl@2.0.0.patch
markdown-it-attrs@4.3.1:
hash: 12883b753541724964b5246a739df34c4b76db10415bbb63c35dce408cfe977e
path: patches/markdown-it-attrs@4.3.1.patch
importers:
@ -116,6 +110,9 @@ importers:
'@mdit/plugin-anchor':
specifier: ^1.1.1
version: 1.1.1(markdown-it@14.2.0)
'@mdit/plugin-attrs':
specifier: ^1.0.2
version: 1.0.2(markdown-it@14.2.0)
'@mdit/plugin-emoji':
specifier: ^1.1.0
version: 1.1.0(markdown-it@14.2.0)
@ -146,9 +143,6 @@ importers:
'@types/mark.js':
specifier: ^8.11.12
version: 8.11.12
'@types/markdown-it-attrs':
specifier: ^4.1.3
version: 4.1.3(patch_hash=ef05082c7886d283042ddf9103f1408fc36fd8665ef278c82b3da0659441dfb6)
'@types/markdown-it-container':
specifier: ^4.0.0
version: 4.0.0
@ -203,9 +197,6 @@ importers:
markdown-it-async:
specifier: ^2.2.0
version: 2.2.0
markdown-it-attrs:
specifier: 4.3.1
version: 4.3.1(patch_hash=12883b753541724964b5246a739df34c4b76db10415bbb63c35dce408cfe977e)(markdown-it@14.2.0)
markdown-it-cjk-friendly:
specifier: ^2.0.2
version: 2.0.2(@types/markdown-it@14.1.2)(markdown-it@14.2.0)
@ -637,11 +628,29 @@ packages:
resolution: {integrity: sha512-00aAZ0F0NLik6I6Yba2emGbHLxv+QYrPH00qQ5dFKXlAo1Ll2RHDXwY7nN2WAfrx2pP+WrvSRFTGFCNGdzBDHw==}
engines: {node: '>=20.0.0'}
'@mdit/helper@1.0.1':
resolution: {integrity: sha512-zAzShsRZmkqjuoOFg6/zTCYVpvghj9a30Cl/eOGkE0xzRJJJG8T18eqb2lgceQhjVLWHK02HNVkzyfNHc429lQ==}
engines: {node: '>=22'}
peerDependencies:
markdown-it: ^14.2.0
peerDependenciesMeta:
markdown-it:
optional: true
'@mdit/plugin-anchor@1.1.1':
resolution: {integrity: sha512-42m7dxzvfLbo3YnteMB70aXFQ1TtnalyNLyPUDj5rr1FqTNf8pnHjQbgmf6FCjshg6BrfLVx7zpHJ7UUehQ/fA==}
peerDependencies:
markdown-it: ^14.2.0
'@mdit/plugin-attrs@1.0.2':
resolution: {integrity: sha512-R9bvWt/MqyMAZ0povWkEh9n55+cQff+bXh9GZnd6Av+mPdE+L/k6jCOAyKzjUEWhQ8qqd5Keyqtn7h62gZq/VA==}
engines: {node: '>=22'}
peerDependencies:
markdown-it: ^14.2.0
peerDependenciesMeta:
markdown-it:
optional: true
'@mdit/plugin-emoji@1.1.0':
resolution: {integrity: sha512-rdGhZ0OVhK0EhiVpw8v22BdTq7XZ6Adrcbq3hR2Cx/YwGnL+kSXFtcGOeJXphiSics7oNgpIKdNyl974z7Cj1A==}
engines: {node: '>=22'}
@ -1064,9 +1073,6 @@ packages:
'@types/mark.js@8.11.12':
resolution: {integrity: sha512-244ZnaIBpz4c6xutliAnYVZp6xJlmC569jZqnR3ElO1Y01ooYASSVQEqpd2x0A2UfrgVMs5V9/9tUAdZaDMytQ==}
'@types/markdown-it-attrs@4.1.3':
resolution: {integrity: sha512-1JsseFdHD6rQHsPcy4W3xx/whxvZ09Z+CqPpnOtrGtpmkFW07N11q7oM383//LtoKv54yn+HGnk6r4ZHUTHJVg==}
'@types/markdown-it-container@4.0.0':
resolution: {integrity: sha512-GmD8OECLfzPHv8VyvFRzslqdwXoDBJ2H40fxXFjrarbqvJZSB/BJKZXN5e3k7Mx7GQanSNzTYhzeS3H9o0gAOw==}
@ -2043,12 +2049,6 @@ packages:
markdown-it-async@2.2.0:
resolution: {integrity: sha512-sITME+kf799vMeO/ww/CjH6q+c05f6TLpn6VOmmWCGNqPJzSh+uFgZoMB9s0plNtW6afy63qglNAC3MhrhP/gg==}
markdown-it-attrs@4.3.1:
resolution: {integrity: sha512-/ko6cba+H6gdZ0DOw7BbNMZtfuJTRp9g/IrGIuz8lYc/EfnmWRpaR3CFPnNbVz0LDvF8Gf1hFGPqrQqq7De0rg==}
engines: {node: '>=6'}
peerDependencies:
markdown-it: '>= 9.0.0'
markdown-it-cjk-friendly@2.0.2:
resolution: {integrity: sha512-KXCl6sd129UqkAiRDb+NcAHrxC9xRa2WsGIsMMvtp2y1YlbeIaNYzArX2zfDoGhOjsyNMfJrGO7xGBss27YQSA==}
engines: {node: '>=18'}
@ -3235,11 +3235,24 @@ snapshots:
'@mdit-vue/types@3.0.2': {}
'@mdit/helper@1.0.1(markdown-it@14.2.0)':
dependencies:
'@types/markdown-it': 14.1.2
optionalDependencies:
markdown-it: 14.2.0
'@mdit/plugin-anchor@1.1.1(markdown-it@14.2.0)':
dependencies:
'@types/markdown-it': 14.1.2
markdown-it: 14.2.0
'@mdit/plugin-attrs@1.0.2(markdown-it@14.2.0)':
dependencies:
'@mdit/helper': 1.0.1(markdown-it@14.2.0)
'@types/markdown-it': 14.1.2
optionalDependencies:
markdown-it: 14.2.0
'@mdit/plugin-emoji@1.1.0(markdown-it@14.2.0)':
dependencies:
'@types/markdown-it': 14.1.2
@ -3547,10 +3560,6 @@ snapshots:
dependencies:
'@types/jquery': 4.0.1
'@types/markdown-it-attrs@4.1.3(patch_hash=ef05082c7886d283042ddf9103f1408fc36fd8665ef278c82b3da0659441dfb6)':
dependencies:
'@types/markdown-it': 14.1.2
'@types/markdown-it-container@4.0.0':
dependencies:
'@types/markdown-it': 14.1.2
@ -4510,10 +4519,6 @@ snapshots:
'@types/markdown-it': 14.1.2
markdown-it: 14.2.0
markdown-it-attrs@4.3.1(patch_hash=12883b753541724964b5246a739df34c4b76db10415bbb63c35dce408cfe977e)(markdown-it@14.2.0):
dependencies:
markdown-it: 14.2.0
markdown-it-cjk-friendly@2.0.2(@types/markdown-it@14.1.2)(markdown-it@14.2.0):
dependencies:
get-east-asian-width: 1.6.0

@ -15,8 +15,6 @@ overrides:
ora>string-width: ^5
patchedDependencies:
'@types/markdown-it-attrs': patches/@types__markdown-it-attrs@4.1.3.patch
'@types/mdurl@2.0.0': patches/@types__mdurl@2.0.0.patch
markdown-it-attrs@4.3.1: patches/markdown-it-attrs@4.3.1.patch
shellEmulator: true

@ -15,6 +15,10 @@ import { titlePlugin } from '@mdit-vue/plugin-title'
import { tocPlugin, type TocPluginOptions } from '@mdit-vue/plugin-toc'
import { slugify as defaultSlugify } from '@mdit-vue/shared'
import { anchor as anchorPlugin, type AnchorOptions } from '@mdit/plugin-anchor'
import {
attrs as attrsPlugin,
type MarkdownItAttrsOptions
} from '@mdit/plugin-attrs'
import { fullEmoji as emojiPlugin } from '@mdit/plugin-emoji'
import type {
CodeToHastOptions,
@ -23,7 +27,6 @@ import type {
ThemeRegistrationAny
} from '@shikijs/types'
import { MarkdownItAsync, type MarkdownItAsyncOptions } from 'markdown-it-async'
import attrsPlugin, { type MarkdownItAttrsOptions } from 'markdown-it-attrs'
import mditCjkFriendly from 'markdown-it-cjk-friendly'
import path from 'node:path'
import type { BuiltinLanguage, BuiltinTheme, Highlighter } from 'shiki'
@ -178,8 +181,11 @@ export interface MarkdownOptions extends MarkdownItAsyncOptions {
/* ==================== Markdown Extensions ==================== */
/**
* Options for `markdown-it-attrs`. Set to `false` to disable.
* @see https://github.com/arve0/markdown-it-attrs
* Options for `@mdit/plugin-attrs`. Set to `false` to disable. The `fence`
* rule is off by default so that curly attributes never consume code block
* meta (e.g. line highlighting) - add classes to code blocks using shiki
* transformers instead.
* @see https://mdit-plugins.github.io/attrs.html
*/
attrs?: MarkdownItAttrsOptions | false
/**
@ -349,7 +355,12 @@ export async function createMarkdownRenderer(
// community plugins
if (options.attrs !== false) {
attrsPlugin(md, options.attrs)
attrsPlugin(md, {
// no `fence` - code block meta (e.g. line highlighting) must reach
// the highlighter intact
rule: ['inline', 'table', 'list', 'heading', 'hr', 'softbreak', 'block'],
...options.attrs
})
}
if (options.emoji !== false) {
emojiPlugin(md, options.emoji)

Loading…
Cancel
Save