@docusaurus/utils 3.9.2-canary-6495 → 3.9.2-canary-6526
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/lib/index.d.ts +2 -1
- package/lib/index.d.ts.map +1 -1
- package/lib/index.js +6 -5
- package/lib/index.js.map +1 -1
- package/lib/markdownHeadingIdUtils.d.ts +49 -0
- package/lib/markdownHeadingIdUtils.d.ts.map +1 -0
- package/lib/markdownHeadingIdUtils.js +148 -0
- package/lib/markdownHeadingIdUtils.js.map +1 -0
- package/lib/markdownUtils.d.ts +0 -31
- package/lib/markdownUtils.d.ts.map +1 -1
- package/lib/markdownUtils.js +0 -89
- package/lib/markdownUtils.js.map +1 -1
- package/package.json +5 -5
- package/src/index.ts +6 -3
- package/src/markdownHeadingIdUtils.ts +209 -0
- package/src/markdownUtils.ts +0 -119
package/lib/index.d.ts
CHANGED
|
@@ -12,7 +12,8 @@ export { mapAsyncSequential, findAsyncSequential } from './jsUtils';
|
|
|
12
12
|
export { normalizeUrl, getEditUrl, fileToPath, encodePath, isValidPathname, resolvePathname, parseURLPath, parseLocalURLPath, parseURLOrPath, toURLPath, serializeURLPath, hasSSHProtocol, buildHttpsUrl, buildSshUrl, } from './urlUtils';
|
|
13
13
|
export type { URLPath } from './urlUtils';
|
|
14
14
|
export { type Tag, type TagsFile, type TagsFileInput, type TagMetadata, type TagsListItem, type TagModule, type FrontMatterTag, type TagsPluginOptions, groupTaggedItems, getTagVisibility, } from './tags';
|
|
15
|
-
export {
|
|
15
|
+
export { unwrapMdxCodeBlocks, admonitionTitleToDirectiveLabel, createExcerpt, DEFAULT_PARSE_FRONT_MATTER, parseMarkdownContentTitle, parseMarkdownFile, } from './markdownUtils';
|
|
16
|
+
export { parseMarkdownHeadingId, escapeMarkdownHeadingIds, writeMarkdownHeadingId, type HeadingIdSyntax, type WriteHeadingIDOptions, } from './markdownHeadingIdUtils';
|
|
16
17
|
export { type ContentPaths, type SourceToPermalink, resolveMarkdownLinkPathname, } from './markdownLinks';
|
|
17
18
|
export { type SluggerOptions, type Slugger, createSlugger } from './slugger';
|
|
18
19
|
export { isNameTooLong, shortName, posixPath, toMessageRelativeFilePath, aliasedSitePath, aliasedSitePathToRelativePath, escapePath, addTrailingPathSeparator, } from './pathUtils';
|
package/lib/index.d.ts.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":"AAAA;;;;;GAKG;AAEH,OAAO,EACL,kBAAkB,EAClB,kBAAkB,EAClB,kBAAkB,EAClB,sBAAsB,EACtB,wBAAwB,EACxB,sBAAsB,EACtB,wBAAwB,EACxB,YAAY,EACZ,uBAAuB,EACvB,6BAA6B,EAC7B,UAAU,EACV,qBAAqB,EACrB,2BAA2B,EAC3B,YAAY,EACZ,iBAAiB,EACjB,wBAAwB,GACzB,MAAM,aAAa,CAAC;AACrB,OAAO,EAAC,QAAQ,EAAE,kBAAkB,EAAC,MAAM,aAAa,CAAC;AACzD,OAAO,EAGL,iBAAiB,EACjB,mBAAmB,EACnB,gBAAgB,GACjB,MAAM,gBAAgB,CAAC;AACxB,OAAO,EACL,iBAAiB,EACjB,6BAA6B,EAC7B,iBAAiB,EACjB,eAAe,GAChB,MAAM,aAAa,CAAC;AACrB,OAAO,EAAC,kBAAkB,EAAE,mBAAmB,EAAC,MAAM,WAAW,CAAC;AAClE,OAAO,EACL,YAAY,EACZ,UAAU,EACV,UAAU,EACV,UAAU,EACV,eAAe,EACf,eAAe,EACf,YAAY,EACZ,iBAAiB,EACjB,cAAc,EACd,SAAS,EACT,gBAAgB,EAChB,cAAc,EACd,aAAa,EACb,WAAW,GACZ,MAAM,YAAY,CAAC;AACpB,YAAY,EAAC,OAAO,EAAC,MAAM,YAAY,CAAC;AACxC,OAAO,EACL,KAAK,GAAG,EACR,KAAK,QAAQ,EACb,KAAK,aAAa,EAClB,KAAK,WAAW,EAChB,KAAK,YAAY,EACjB,KAAK,SAAS,EACd,KAAK,cAAc,EACnB,KAAK,iBAAiB,EACtB,gBAAgB,EAChB,gBAAgB,GACjB,MAAM,QAAQ,CAAC;AAChB,OAAO,EACL,
|
|
1
|
+
{"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":"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"}
|
package/lib/index.js
CHANGED
|
@@ -6,8 +6,8 @@
|
|
|
6
6
|
* LICENSE file in the root directory of this source tree.
|
|
7
7
|
*/
|
|
8
8
|
Object.defineProperty(exports, "__esModule", { value: true });
|
|
9
|
-
exports.
|
|
10
|
-
exports.reportInlineTags = exports.normalizeTags = exports.TEST_VCS = exports.getVcsPreset = exports.VcsPresetNames = exports.readLastUpdateData = exports.flattenRoutes = exports.escapeRegexp = exports.isUnlisted = exports.isDraft = exports.getFolderContainingFile = exports.findFolderContainingFile = exports.getContentPathList = exports.readDataFile = exports.getDataFilePath = exports.loadFreshModule = exports.getWebpackLoaderCompilerName = exports.getFileLoaderUtils = exports.createAbsoluteFilePathMatcher = exports.createMatcher = exports.globTranslatableSourceFiles = exports.safeGlobby = exports.GlobExcludeDefault = exports.Globby = exports.docuHash = exports.simpleHash = exports.md5Hash = exports.addTrailingPathSeparator = exports.escapePath = exports.aliasedSitePathToRelativePath = exports.aliasedSitePath = exports.toMessageRelativeFilePath = exports.posixPath = exports.shortName = exports.isNameTooLong = exports.createSlugger = exports.resolveMarkdownLinkPathname = exports.writeMarkdownHeadingId = exports.
|
|
9
|
+
exports.parseMarkdownHeadingId = exports.parseMarkdownFile = exports.parseMarkdownContentTitle = exports.DEFAULT_PARSE_FRONT_MATTER = exports.createExcerpt = exports.admonitionTitleToDirectiveLabel = exports.unwrapMdxCodeBlocks = exports.getTagVisibility = exports.groupTaggedItems = exports.buildSshUrl = exports.buildHttpsUrl = exports.hasSSHProtocol = exports.serializeURLPath = exports.toURLPath = exports.parseURLOrPath = exports.parseLocalURLPath = exports.parseURLPath = exports.resolvePathname = exports.isValidPathname = exports.encodePath = exports.fileToPath = exports.getEditUrl = exports.normalizeUrl = exports.findAsyncSequential = exports.mapAsyncSequential = exports.getLocaleConfig = exports.getPluginI18nPath = exports.updateTranslationFileMessages = exports.mergeTranslations = exports.GitNotFoundError = exports.FileNotTrackedError = exports.getFileCommitDate = exports.readOutputHTMLFile = exports.generate = exports.WEBPACK_URL_LOADER_LIMIT = exports.DEFAULT_PLUGIN_ID = exports.DEFAULT_PORT = exports.CODE_TRANSLATIONS_FILE_NAME = exports.DEFAULT_I18N_DIR_NAME = exports.THEME_PATH = exports.OUTPUT_STATIC_ASSETS_DIR_NAME = exports.DEFAULT_STATIC_DIR_NAME = exports.SRC_DIR_NAME = exports.GENERATED_FILES_DIR_NAME = exports.BABEL_CONFIG_FILE_NAME = exports.DEFAULT_CONFIG_FILE_NAME = exports.DEFAULT_BUILD_DIR_NAME = exports.DOCUSAURUS_VERSION = exports.NODE_MINOR_VERSION = exports.NODE_MAJOR_VERSION = void 0;
|
|
10
|
+
exports.reportInlineTags = exports.normalizeTags = exports.TEST_VCS = exports.getVcsPreset = exports.VcsPresetNames = exports.readLastUpdateData = exports.flattenRoutes = exports.escapeRegexp = exports.isUnlisted = exports.isDraft = exports.getFolderContainingFile = exports.findFolderContainingFile = exports.getContentPathList = exports.readDataFile = exports.getDataFilePath = exports.loadFreshModule = exports.getWebpackLoaderCompilerName = exports.getFileLoaderUtils = exports.createAbsoluteFilePathMatcher = exports.createMatcher = exports.globTranslatableSourceFiles = exports.safeGlobby = exports.GlobExcludeDefault = exports.Globby = exports.docuHash = exports.simpleHash = exports.md5Hash = exports.addTrailingPathSeparator = exports.escapePath = exports.aliasedSitePathToRelativePath = exports.aliasedSitePath = exports.toMessageRelativeFilePath = exports.posixPath = exports.shortName = exports.isNameTooLong = exports.createSlugger = exports.resolveMarkdownLinkPathname = exports.writeMarkdownHeadingId = exports.escapeMarkdownHeadingIds = void 0;
|
|
11
11
|
var constants_1 = require("./constants");
|
|
12
12
|
Object.defineProperty(exports, "NODE_MAJOR_VERSION", { enumerable: true, get: function () { return constants_1.NODE_MAJOR_VERSION; } });
|
|
13
13
|
Object.defineProperty(exports, "NODE_MINOR_VERSION", { enumerable: true, get: function () { return constants_1.NODE_MINOR_VERSION; } });
|
|
@@ -61,15 +61,16 @@ var tags_1 = require("./tags");
|
|
|
61
61
|
Object.defineProperty(exports, "groupTaggedItems", { enumerable: true, get: function () { return tags_1.groupTaggedItems; } });
|
|
62
62
|
Object.defineProperty(exports, "getTagVisibility", { enumerable: true, get: function () { return tags_1.getTagVisibility; } });
|
|
63
63
|
var markdownUtils_1 = require("./markdownUtils");
|
|
64
|
-
Object.defineProperty(exports, "parseMarkdownHeadingId", { enumerable: true, get: function () { return markdownUtils_1.parseMarkdownHeadingId; } });
|
|
65
|
-
Object.defineProperty(exports, "escapeMarkdownHeadingIds", { enumerable: true, get: function () { return markdownUtils_1.escapeMarkdownHeadingIds; } });
|
|
66
64
|
Object.defineProperty(exports, "unwrapMdxCodeBlocks", { enumerable: true, get: function () { return markdownUtils_1.unwrapMdxCodeBlocks; } });
|
|
67
65
|
Object.defineProperty(exports, "admonitionTitleToDirectiveLabel", { enumerable: true, get: function () { return markdownUtils_1.admonitionTitleToDirectiveLabel; } });
|
|
68
66
|
Object.defineProperty(exports, "createExcerpt", { enumerable: true, get: function () { return markdownUtils_1.createExcerpt; } });
|
|
69
67
|
Object.defineProperty(exports, "DEFAULT_PARSE_FRONT_MATTER", { enumerable: true, get: function () { return markdownUtils_1.DEFAULT_PARSE_FRONT_MATTER; } });
|
|
70
68
|
Object.defineProperty(exports, "parseMarkdownContentTitle", { enumerable: true, get: function () { return markdownUtils_1.parseMarkdownContentTitle; } });
|
|
71
69
|
Object.defineProperty(exports, "parseMarkdownFile", { enumerable: true, get: function () { return markdownUtils_1.parseMarkdownFile; } });
|
|
72
|
-
|
|
70
|
+
var markdownHeadingIdUtils_1 = require("./markdownHeadingIdUtils");
|
|
71
|
+
Object.defineProperty(exports, "parseMarkdownHeadingId", { enumerable: true, get: function () { return markdownHeadingIdUtils_1.parseMarkdownHeadingId; } });
|
|
72
|
+
Object.defineProperty(exports, "escapeMarkdownHeadingIds", { enumerable: true, get: function () { return markdownHeadingIdUtils_1.escapeMarkdownHeadingIds; } });
|
|
73
|
+
Object.defineProperty(exports, "writeMarkdownHeadingId", { enumerable: true, get: function () { return markdownHeadingIdUtils_1.writeMarkdownHeadingId; } });
|
|
73
74
|
var markdownLinks_1 = require("./markdownLinks");
|
|
74
75
|
Object.defineProperty(exports, "resolveMarkdownLinkPathname", { enumerable: true, get: function () { return markdownLinks_1.resolveMarkdownLinkPathname; } });
|
|
75
76
|
var slugger_1 = require("./slugger");
|
package/lib/index.js.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"index.js","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":";AAAA;;;;;GAKG;;;;AAEH,yCAiBqB;AAhBnB,+GAAA,kBAAkB,OAAA;AAClB,+GAAA,kBAAkB,OAAA;AAClB,+GAAA,kBAAkB,OAAA;AAClB,mHAAA,sBAAsB,OAAA;AACtB,qHAAA,wBAAwB,OAAA;AACxB,mHAAA,sBAAsB,OAAA;AACtB,qHAAA,wBAAwB,OAAA;AACxB,yGAAA,YAAY,OAAA;AACZ,oHAAA,uBAAuB,OAAA;AACvB,0HAAA,6BAA6B,OAAA;AAC7B,uGAAA,UAAU,OAAA;AACV,kHAAA,qBAAqB,OAAA;AACrB,wHAAA,2BAA2B,OAAA;AAC3B,yGAAA,YAAY,OAAA;AACZ,8GAAA,iBAAiB,OAAA;AACjB,qHAAA,wBAAwB,OAAA;AAE1B,yCAAyD;AAAjD,qGAAA,QAAQ,OAAA;AAAE,+GAAA,kBAAkB,OAAA;AACpC,2CAMwB;AALtB,mDAAmD;AACnD,8CAA8C;AAC9C,6GAAA,iBAAiB,OAAA;AACjB,+GAAA,mBAAmB,OAAA;AACnB,4GAAA,gBAAgB,OAAA;AAElB,yCAKqB;AAJnB,8GAAA,iBAAiB,OAAA;AACjB,0HAAA,6BAA6B,OAAA;AAC7B,8GAAA,iBAAiB,OAAA;AACjB,4GAAA,eAAe,OAAA;AAEjB,qCAAkE;AAA1D,6GAAA,kBAAkB,OAAA;AAAE,8GAAA,mBAAmB,OAAA;AAC/C,uCAeoB;AAdlB,wGAAA,YAAY,OAAA;AACZ,sGAAA,UAAU,OAAA;AACV,sGAAA,UAAU,OAAA;AACV,sGAAA,UAAU,OAAA;AACV,2GAAA,eAAe,OAAA;AACf,2GAAA,eAAe,OAAA;AACf,wGAAA,YAAY,OAAA;AACZ,6GAAA,iBAAiB,OAAA;AACjB,0GAAA,cAAc,OAAA;AACd,qGAAA,SAAS,OAAA;AACT,4GAAA,gBAAgB,OAAA;AAChB,0GAAA,cAAc,OAAA;AACd,yGAAA,aAAa,OAAA;AACb,uGAAA,WAAW,OAAA;AAGb,+BAWgB;AAFd,wGAAA,gBAAgB,OAAA;AAChB,wGAAA,gBAAgB,OAAA;AAElB,
|
|
1
|
+
{"version":3,"file":"index.js","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1,49 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Copyright (c) Facebook, Inc. and its affiliates.
|
|
3
|
+
*
|
|
4
|
+
* This source code is licensed under the MIT license found in the
|
|
5
|
+
* LICENSE file in the root directory of this source tree.
|
|
6
|
+
*/
|
|
7
|
+
import { type SluggerOptions } from './slugger';
|
|
8
|
+
/**
|
|
9
|
+
* The syntax to use for heading IDs.
|
|
10
|
+
* - `classic` => `{#id}` (invalid MDX, but commonly supported)
|
|
11
|
+
* - `mdx-comment` => `{/* #id * /}` (valid MDX)
|
|
12
|
+
*/
|
|
13
|
+
export type HeadingIdSyntax = 'classic' | 'mdx-comment';
|
|
14
|
+
/**
|
|
15
|
+
* Parses custom ID from a heading. The ID can contain any characters except
|
|
16
|
+
* `{#` and `}`.
|
|
17
|
+
*
|
|
18
|
+
* @param heading e.g. `## Some heading {#some-heading}` where the last
|
|
19
|
+
* character must be `}` for the ID to be recognized
|
|
20
|
+
* @param syntax which heading ID syntax to recognize
|
|
21
|
+
*/
|
|
22
|
+
export declare function parseMarkdownHeadingId(heading: string, syntax?: HeadingIdSyntax): {
|
|
23
|
+
/**
|
|
24
|
+
* The heading content sans the ID part, right-trimmed. e.g. `## Some heading`
|
|
25
|
+
*/
|
|
26
|
+
text: string;
|
|
27
|
+
/** The heading ID. e.g. `some-heading` */
|
|
28
|
+
id: string | undefined;
|
|
29
|
+
};
|
|
30
|
+
/**
|
|
31
|
+
* For our classic syntax, MDX v2+ now requires escaping { to compile: \{#id}.
|
|
32
|
+
* See https://mdxjs.com/docs/troubleshooting-mdx/#could-not-parse-expression-with-acorn-error
|
|
33
|
+
*/
|
|
34
|
+
export declare function escapeMarkdownHeadingIds(content: string): string;
|
|
35
|
+
export type WriteHeadingIDOptions = SluggerOptions & {
|
|
36
|
+
/** The target syntax to use for heading IDs. */
|
|
37
|
+
syntax?: HeadingIdSyntax;
|
|
38
|
+
/** Migrate the existing heading IDs to the target syntax */
|
|
39
|
+
migrate?: boolean;
|
|
40
|
+
/** Overwrite existing heading IDs by re-generating them from the text. */
|
|
41
|
+
overwrite?: boolean;
|
|
42
|
+
};
|
|
43
|
+
/**
|
|
44
|
+
* Takes Markdown content, returns new content with heading IDs written.
|
|
45
|
+
* Respects existing IDs (unless `overwrite=true`) and never generates colliding
|
|
46
|
+
* IDs (through the slugger).
|
|
47
|
+
*/
|
|
48
|
+
export declare function writeMarkdownHeadingId(content: string, options?: WriteHeadingIDOptions): string;
|
|
49
|
+
//# sourceMappingURL=markdownHeadingIdUtils.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"markdownHeadingIdUtils.d.ts","sourceRoot":"","sources":["../src/markdownHeadingIdUtils.ts"],"names":[],"mappings":"AAAA;;;;;GAKG;AAEH,OAAO,EAA8B,KAAK,cAAc,EAAC,MAAM,WAAW,CAAC;AAE3E;;;;GAIG;AACH,MAAM,MAAM,eAAe,GAAG,SAAS,GAAG,aAAa,CAAC;AAExD;;;;;;;GAOG;AACH,wBAAgB,sBAAsB,CACpC,OAAO,EAAE,MAAM,EACf,MAAM,GAAE,eAA2B,GAClC;IACD;;OAEG;IACH,IAAI,EAAE,MAAM,CAAC;IACb,0CAA0C;IAC1C,EAAE,EAAE,MAAM,GAAG,SAAS,CAAC;CACxB,CA8BA;AAED;;;GAGG;AACH,wBAAgB,wBAAwB,CAAC,OAAO,EAAE,MAAM,GAAG,MAAM,CAShE;AAyCD,MAAM,MAAM,qBAAqB,GAAG,cAAc,GAAG;IACnD,gDAAgD;IAChD,MAAM,CAAC,EAAE,eAAe,CAAC;IACzB,4DAA4D;IAC5D,OAAO,CAAC,EAAE,OAAO,CAAC;IAClB,0EAA0E;IAC1E,SAAS,CAAC,EAAE,OAAO,CAAC;CACrB,CAAC;AAEF;;;;GAIG;AACH,wBAAgB,sBAAsB,CACpC,OAAO,EAAE,MAAM,EACf,OAAO,GAAE,qBAA0B,GAClC,MAAM,CAuER"}
|
|
@@ -0,0 +1,148 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
/**
|
|
3
|
+
* Copyright (c) Facebook, Inc. and its affiliates.
|
|
4
|
+
*
|
|
5
|
+
* This source code is licensed under the MIT license found in the
|
|
6
|
+
* LICENSE file in the root directory of this source tree.
|
|
7
|
+
*/
|
|
8
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
9
|
+
exports.parseMarkdownHeadingId = parseMarkdownHeadingId;
|
|
10
|
+
exports.escapeMarkdownHeadingIds = escapeMarkdownHeadingIds;
|
|
11
|
+
exports.writeMarkdownHeadingId = writeMarkdownHeadingId;
|
|
12
|
+
const slugger_1 = require("./slugger");
|
|
13
|
+
/**
|
|
14
|
+
* Parses custom ID from a heading. The ID can contain any characters except
|
|
15
|
+
* `{#` and `}`.
|
|
16
|
+
*
|
|
17
|
+
* @param heading e.g. `## Some heading {#some-heading}` where the last
|
|
18
|
+
* character must be `}` for the ID to be recognized
|
|
19
|
+
* @param syntax which heading ID syntax to recognize
|
|
20
|
+
*/
|
|
21
|
+
function parseMarkdownHeadingId(heading, syntax = 'classic') {
|
|
22
|
+
// Classic syntax: {#my-id}
|
|
23
|
+
if (syntax === 'classic') {
|
|
24
|
+
const customHeadingIdRegex = /\s*\{#(?<id>(?:.(?!\{#|\}))*.)\}$/;
|
|
25
|
+
const matches = customHeadingIdRegex.exec(heading);
|
|
26
|
+
if (matches) {
|
|
27
|
+
return {
|
|
28
|
+
text: heading.replace(matches[0], ''),
|
|
29
|
+
id: matches.groups.id.trim(),
|
|
30
|
+
};
|
|
31
|
+
}
|
|
32
|
+
}
|
|
33
|
+
// MDX comment syntax: {/* #my-id */}
|
|
34
|
+
// Note: this is only used for the "write-heading-ids" CLI
|
|
35
|
+
// The mdx loader is using a real MDX parser to find these comments
|
|
36
|
+
else if (syntax === 'mdx-comment') {
|
|
37
|
+
const mdxCommentHeadingIdRegex = /\s*\{\/\*\s*#(?<id>\S+)\s*\*\/\}$/;
|
|
38
|
+
const mdxMatches = mdxCommentHeadingIdRegex.exec(heading);
|
|
39
|
+
if (mdxMatches) {
|
|
40
|
+
return {
|
|
41
|
+
text: heading.replace(mdxMatches[0], ''),
|
|
42
|
+
id: mdxMatches.groups.id.trim(),
|
|
43
|
+
};
|
|
44
|
+
}
|
|
45
|
+
}
|
|
46
|
+
// Unhandled cases, shouldn't happen
|
|
47
|
+
else {
|
|
48
|
+
throw new Error(`unknown heading id syntax '${syntax}'`);
|
|
49
|
+
}
|
|
50
|
+
return { text: heading, id: undefined };
|
|
51
|
+
}
|
|
52
|
+
/**
|
|
53
|
+
* For our classic syntax, MDX v2+ now requires escaping { to compile: \{#id}.
|
|
54
|
+
* See https://mdxjs.com/docs/troubleshooting-mdx/#could-not-parse-expression-with-acorn-error
|
|
55
|
+
*/
|
|
56
|
+
function escapeMarkdownHeadingIds(content) {
|
|
57
|
+
const markdownHeadingRegexp = /(?:^|\n)#{1,6}(?!#).*/g;
|
|
58
|
+
return content.replaceAll(markdownHeadingRegexp, (substring) =>
|
|
59
|
+
// TODO probably not the most efficient impl...
|
|
60
|
+
substring
|
|
61
|
+
.replace('{#', '\\{#')
|
|
62
|
+
// prevent duplicate escaping
|
|
63
|
+
.replace('\\\\{#', '\\{#'));
|
|
64
|
+
}
|
|
65
|
+
function addHeadingId(line, slugger, maintainCase, syntax, headingId) {
|
|
66
|
+
let headingLevel = 0;
|
|
67
|
+
while (line.charAt(headingLevel) === '#') {
|
|
68
|
+
headingLevel += 1;
|
|
69
|
+
}
|
|
70
|
+
const headingHashes = line.slice(0, headingLevel);
|
|
71
|
+
const headingContent = line.slice(headingLevel).trimEnd();
|
|
72
|
+
function getHeadingId() {
|
|
73
|
+
if (headingId) {
|
|
74
|
+
return headingId;
|
|
75
|
+
}
|
|
76
|
+
// Unwrap links
|
|
77
|
+
// "[ Hello](https://example.com) World " => "Hello world"
|
|
78
|
+
const headingText = headingContent
|
|
79
|
+
.replace(/\[(?<alt>[^\]]+)\]\([^)]+\)/g, (_match, p1) => p1)
|
|
80
|
+
.trim();
|
|
81
|
+
return slugger.slug(headingText, {
|
|
82
|
+
maintainCase,
|
|
83
|
+
});
|
|
84
|
+
}
|
|
85
|
+
const headingIdSuffix = syntax === 'mdx-comment'
|
|
86
|
+
? `{/* #${getHeadingId()} */}`
|
|
87
|
+
: `{#${getHeadingId()}}`;
|
|
88
|
+
return `${headingHashes}${headingContent} ${headingIdSuffix}`;
|
|
89
|
+
}
|
|
90
|
+
/**
|
|
91
|
+
* Takes Markdown content, returns new content with heading IDs written.
|
|
92
|
+
* Respects existing IDs (unless `overwrite=true`) and never generates colliding
|
|
93
|
+
* IDs (through the slugger).
|
|
94
|
+
*/
|
|
95
|
+
function writeMarkdownHeadingId(content, options = {}) {
|
|
96
|
+
const { syntax = 'classic', // Maybe we'll want to change this default later?
|
|
97
|
+
overwrite = false, migrate = false, maintainCase = false, } = options;
|
|
98
|
+
// For now, we have 2 booleans (retro compatible)
|
|
99
|
+
// but it could be useful to have a "mode" enum instead?
|
|
100
|
+
if (overwrite && migrate) {
|
|
101
|
+
throw new Error('Heading ids can either be overwritten or migrated, not both at the same time');
|
|
102
|
+
}
|
|
103
|
+
const lines = content.split('\n');
|
|
104
|
+
const slugger = (0, slugger_1.createSlugger)();
|
|
105
|
+
// Parse heading ID trying both syntaxes (classic first, then mdx-comment)
|
|
106
|
+
function parseHeadingIdAnySyntax(heading) {
|
|
107
|
+
const classic = parseMarkdownHeadingId(heading, 'classic');
|
|
108
|
+
if (classic.id) {
|
|
109
|
+
return classic;
|
|
110
|
+
}
|
|
111
|
+
return parseMarkdownHeadingId(heading, 'mdx-comment');
|
|
112
|
+
}
|
|
113
|
+
// If we can't overwrite existing slugs, make sure other headings don't
|
|
114
|
+
// generate colliding slugs by first marking these slugs as occupied
|
|
115
|
+
if (!overwrite) {
|
|
116
|
+
lines.forEach((line) => {
|
|
117
|
+
const parsedHeading = parseHeadingIdAnySyntax(line);
|
|
118
|
+
if (parsedHeading.id) {
|
|
119
|
+
slugger.slug(parsedHeading.id);
|
|
120
|
+
}
|
|
121
|
+
});
|
|
122
|
+
}
|
|
123
|
+
let inCode = false;
|
|
124
|
+
return lines
|
|
125
|
+
.map((line) => {
|
|
126
|
+
if (line.startsWith('```')) {
|
|
127
|
+
inCode = !inCode;
|
|
128
|
+
return line;
|
|
129
|
+
}
|
|
130
|
+
// Ignore h1 headings, as we don't create anchor links for those
|
|
131
|
+
if (inCode || !line.startsWith('##')) {
|
|
132
|
+
return line;
|
|
133
|
+
}
|
|
134
|
+
const parsedHeading = parseHeadingIdAnySyntax(line);
|
|
135
|
+
// Preserve the line if id is already there, unless we migrate/overwrite
|
|
136
|
+
if (parsedHeading.id && !overwrite && !migrate) {
|
|
137
|
+
return line;
|
|
138
|
+
}
|
|
139
|
+
const headingId = overwrite
|
|
140
|
+
? undefined
|
|
141
|
+
: migrate
|
|
142
|
+
? parsedHeading.id
|
|
143
|
+
: undefined;
|
|
144
|
+
return addHeadingId(parsedHeading.text, slugger, maintainCase, syntax, headingId);
|
|
145
|
+
})
|
|
146
|
+
.join('\n');
|
|
147
|
+
}
|
|
148
|
+
//# sourceMappingURL=markdownHeadingIdUtils.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"markdownHeadingIdUtils.js","sourceRoot":"","sources":["../src/markdownHeadingIdUtils.ts"],"names":[],"mappings":"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"}
|
package/lib/markdownUtils.d.ts
CHANGED
|
@@ -4,28 +4,7 @@
|
|
|
4
4
|
* This source code is licensed under the MIT license found in the
|
|
5
5
|
* LICENSE file in the root directory of this source tree.
|
|
6
6
|
*/
|
|
7
|
-
import { type SluggerOptions } from './slugger';
|
|
8
7
|
import type { ParseFrontMatter, DefaultParseFrontMatter } from '@docusaurus/types';
|
|
9
|
-
/**
|
|
10
|
-
* Parses custom ID from a heading. The ID can contain any characters except
|
|
11
|
-
* `{#` and `}`.
|
|
12
|
-
*
|
|
13
|
-
* @param heading e.g. `## Some heading {#some-heading}` where the last
|
|
14
|
-
* character must be `}` for the ID to be recognized
|
|
15
|
-
*/
|
|
16
|
-
export declare function parseMarkdownHeadingId(heading: string): {
|
|
17
|
-
/**
|
|
18
|
-
* The heading content sans the ID part, right-trimmed. e.g. `## Some heading`
|
|
19
|
-
*/
|
|
20
|
-
text: string;
|
|
21
|
-
/** The heading ID. e.g. `some-heading` */
|
|
22
|
-
id: string | undefined;
|
|
23
|
-
};
|
|
24
|
-
/**
|
|
25
|
-
* MDX 2 requires escaping { with a \ so our anchor syntax need that now.
|
|
26
|
-
* See https://mdxjs.com/docs/troubleshooting-mdx/#could-not-parse-expression-with-acorn-error
|
|
27
|
-
*/
|
|
28
|
-
export declare function escapeMarkdownHeadingIds(content: string): string;
|
|
29
8
|
/**
|
|
30
9
|
* Hacky temporary escape hatch for Crowdin bad MDX support
|
|
31
10
|
* See https://docusaurus.io/docs/i18n/crowdin#mdx
|
|
@@ -129,15 +108,5 @@ export declare function parseMarkdownFile({ filePath, fileContent, parseFrontMat
|
|
|
129
108
|
*/
|
|
130
109
|
content: string;
|
|
131
110
|
}>;
|
|
132
|
-
export type WriteHeadingIDOptions = SluggerOptions & {
|
|
133
|
-
/** Overwrite existing heading IDs. */
|
|
134
|
-
overwrite?: boolean;
|
|
135
|
-
};
|
|
136
|
-
/**
|
|
137
|
-
* Takes Markdown content, returns new content with heading IDs written.
|
|
138
|
-
* Respects existing IDs (unless `overwrite=true`) and never generates colliding
|
|
139
|
-
* IDs (through the slugger).
|
|
140
|
-
*/
|
|
141
|
-
export declare function writeMarkdownHeadingId(content: string, options?: WriteHeadingIDOptions): string;
|
|
142
111
|
export {};
|
|
143
112
|
//# sourceMappingURL=markdownUtils.d.ts.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"markdownUtils.d.ts","sourceRoot":"","sources":["../src/markdownUtils.ts"],"names":[],"mappings":"AAAA;;;;;GAKG;AAIH,OAAO,
|
|
1
|
+
{"version":3,"file":"markdownUtils.d.ts","sourceRoot":"","sources":["../src/markdownUtils.ts"],"names":[],"mappings":"AAAA;;;;;GAKG;AAIH,OAAO,KAAK,EACV,gBAAgB,EAChB,uBAAuB,EACxB,MAAM,mBAAmB,CAAC;AAM3B;;;;;;;;GAQG;AACH,wBAAgB,mBAAmB,CAAC,OAAO,EAAE,MAAM,GAAG,MAAM,CAc3D;AAED;;;;;;;;GAQG;AACH,wBAAgB,+BAA+B,CAC7C,OAAO,EAAE,MAAM,EACf,6BAA6B,EAAE,MAAM,EAAE,GACtC,MAAM,CAiBR;AAID;;;;;;;;;GASG;AACH,wBAAgB,aAAa,CAAC,UAAU,EAAE,MAAM,GAAG,MAAM,GAAG,SAAS,CA8EpE;AAED;;;;;;;;;;;GAWG;AACH,wBAAgB,2BAA2B,CAAC,WAAW,EAAE,MAAM,GAAG;IAChE,6CAA6C;IAC7C,WAAW,EAAE;QAAC,CAAC,GAAG,EAAE,MAAM,GAAG,OAAO,CAAA;KAAC,CAAC;IACtC,sCAAsC;IACtC,OAAO,EAAE,MAAM,CAAC;CACjB,CAuBA;AAED,eAAO,MAAM,0BAA0B,EAAE,uBAEW,CAAC;AAMrD,KAAK,gCAAgC,GAAG;IACtC;;;;;OAKG;IACH,kBAAkB,CAAC,EAAE,OAAO,CAAC;CAC9B,CAAC;AAEF;;;;;;;;;;GAUG;AACH,wBAAgB,yBAAyB,CACvC,gBAAgB,EAAE,MAAM,EACxB,OAAO,CAAC,EAAE,gCAAgC,GACzC;IACD,yDAAyD;IACzD,OAAO,EAAE,MAAM,CAAC;IAChB,8CAA8C;IAC9C,YAAY,EAAE,MAAM,GAAG,SAAS,CAAC;CAClC,CAyCA;AAED;;;;;GAKG;AACH,wBAAsB,iBAAiB,CAAC,EACtC,QAAQ,EACR,WAAW,EACX,gBAAgB,EAChB,kBAAkB,GACnB,EAAE;IACD,QAAQ,EAAE,MAAM,CAAC;IACjB,WAAW,EAAE,MAAM,CAAC;IACpB,gBAAgB,EAAE,gBAAgB,CAAC;CACpC,GAAG,gCAAgC,GAAG,OAAO,CAAC;IAC7C,oCAAoC;IACpC,WAAW,EAAE;QAAC,CAAC,GAAG,EAAE,MAAM,GAAG,OAAO,CAAA;KAAC,CAAC;IACtC,6CAA6C;IAC7C,YAAY,EAAE,MAAM,GAAG,SAAS,CAAC;IACjC,iCAAiC;IACjC,OAAO,EAAE,MAAM,GAAG,SAAS,CAAC;IAC5B;;;OAGG;IACH,OAAO,EAAE,MAAM,CAAC;CACjB,CAAC,CA2BD"}
|
package/lib/markdownUtils.js
CHANGED
|
@@ -7,53 +7,18 @@
|
|
|
7
7
|
*/
|
|
8
8
|
Object.defineProperty(exports, "__esModule", { value: true });
|
|
9
9
|
exports.DEFAULT_PARSE_FRONT_MATTER = void 0;
|
|
10
|
-
exports.parseMarkdownHeadingId = parseMarkdownHeadingId;
|
|
11
|
-
exports.escapeMarkdownHeadingIds = escapeMarkdownHeadingIds;
|
|
12
10
|
exports.unwrapMdxCodeBlocks = unwrapMdxCodeBlocks;
|
|
13
11
|
exports.admonitionTitleToDirectiveLabel = admonitionTitleToDirectiveLabel;
|
|
14
12
|
exports.createExcerpt = createExcerpt;
|
|
15
13
|
exports.parseFileContentFrontMatter = parseFileContentFrontMatter;
|
|
16
14
|
exports.parseMarkdownContentTitle = parseMarkdownContentTitle;
|
|
17
15
|
exports.parseMarkdownFile = parseMarkdownFile;
|
|
18
|
-
exports.writeMarkdownHeadingId = writeMarkdownHeadingId;
|
|
19
16
|
const tslib_1 = require("tslib");
|
|
20
17
|
const logger_1 = tslib_1.__importDefault(require("@docusaurus/logger"));
|
|
21
18
|
const gray_matter_1 = tslib_1.__importDefault(require("gray-matter"));
|
|
22
|
-
const slugger_1 = require("./slugger");
|
|
23
19
|
// Some utilities for parsing Markdown content. These things are only used on
|
|
24
20
|
// server-side when we infer metadata like `title` and `description` from the
|
|
25
21
|
// content. Most parsing is still done in MDX through the mdx-loader.
|
|
26
|
-
/**
|
|
27
|
-
* Parses custom ID from a heading. The ID can contain any characters except
|
|
28
|
-
* `{#` and `}`.
|
|
29
|
-
*
|
|
30
|
-
* @param heading e.g. `## Some heading {#some-heading}` where the last
|
|
31
|
-
* character must be `}` for the ID to be recognized
|
|
32
|
-
*/
|
|
33
|
-
function parseMarkdownHeadingId(heading) {
|
|
34
|
-
const customHeadingIdRegex = /\s*\{#(?<id>(?:.(?!\{#|\}))*.)\}$/;
|
|
35
|
-
const matches = customHeadingIdRegex.exec(heading);
|
|
36
|
-
if (matches) {
|
|
37
|
-
return {
|
|
38
|
-
text: heading.replace(matches[0], ''),
|
|
39
|
-
id: matches.groups.id,
|
|
40
|
-
};
|
|
41
|
-
}
|
|
42
|
-
return { text: heading, id: undefined };
|
|
43
|
-
}
|
|
44
|
-
/**
|
|
45
|
-
* MDX 2 requires escaping { with a \ so our anchor syntax need that now.
|
|
46
|
-
* See https://mdxjs.com/docs/troubleshooting-mdx/#could-not-parse-expression-with-acorn-error
|
|
47
|
-
*/
|
|
48
|
-
function escapeMarkdownHeadingIds(content) {
|
|
49
|
-
const markdownHeadingRegexp = /(?:^|\n)#{1,6}(?!#).*/g;
|
|
50
|
-
return content.replaceAll(markdownHeadingRegexp, (substring) =>
|
|
51
|
-
// TODO probably not the most efficient impl...
|
|
52
|
-
substring
|
|
53
|
-
.replace('{#', '\\{#')
|
|
54
|
-
// prevent duplicate escaping
|
|
55
|
-
.replace('\\\\{#', '\\{#'));
|
|
56
|
-
}
|
|
57
22
|
/**
|
|
58
23
|
* Hacky temporary escape hatch for Crowdin bad MDX support
|
|
59
24
|
* See https://docusaurus.io/docs/i18n/crowdin#mdx
|
|
@@ -288,58 +253,4 @@ This can happen if you use special characters in front matter values (try using
|
|
|
288
253
|
throw err;
|
|
289
254
|
}
|
|
290
255
|
}
|
|
291
|
-
function unwrapMarkdownLinks(line) {
|
|
292
|
-
return line.replace(/\[(?<alt>[^\]]+)\]\([^)]+\)/g, (match, p1) => p1);
|
|
293
|
-
}
|
|
294
|
-
function addHeadingId(line, slugger, maintainCase) {
|
|
295
|
-
let headingLevel = 0;
|
|
296
|
-
while (line.charAt(headingLevel) === '#') {
|
|
297
|
-
headingLevel += 1;
|
|
298
|
-
}
|
|
299
|
-
const headingText = line.slice(headingLevel).trimEnd();
|
|
300
|
-
const headingHashes = line.slice(0, headingLevel);
|
|
301
|
-
const slug = slugger.slug(unwrapMarkdownLinks(headingText).trim(), {
|
|
302
|
-
maintainCase,
|
|
303
|
-
});
|
|
304
|
-
return `${headingHashes}${headingText} {#${slug}}`;
|
|
305
|
-
}
|
|
306
|
-
/**
|
|
307
|
-
* Takes Markdown content, returns new content with heading IDs written.
|
|
308
|
-
* Respects existing IDs (unless `overwrite=true`) and never generates colliding
|
|
309
|
-
* IDs (through the slugger).
|
|
310
|
-
*/
|
|
311
|
-
function writeMarkdownHeadingId(content, options = { maintainCase: false, overwrite: false }) {
|
|
312
|
-
const { maintainCase = false, overwrite = false } = options;
|
|
313
|
-
const lines = content.split('\n');
|
|
314
|
-
const slugger = (0, slugger_1.createSlugger)();
|
|
315
|
-
// If we can't overwrite existing slugs, make sure other headings don't
|
|
316
|
-
// generate colliding slugs by first marking these slugs as occupied
|
|
317
|
-
if (!overwrite) {
|
|
318
|
-
lines.forEach((line) => {
|
|
319
|
-
const parsedHeading = parseMarkdownHeadingId(line);
|
|
320
|
-
if (parsedHeading.id) {
|
|
321
|
-
slugger.slug(parsedHeading.id);
|
|
322
|
-
}
|
|
323
|
-
});
|
|
324
|
-
}
|
|
325
|
-
let inCode = false;
|
|
326
|
-
return lines
|
|
327
|
-
.map((line) => {
|
|
328
|
-
if (line.startsWith('```')) {
|
|
329
|
-
inCode = !inCode;
|
|
330
|
-
return line;
|
|
331
|
-
}
|
|
332
|
-
// Ignore h1 headings, as we don't create anchor links for those
|
|
333
|
-
if (inCode || !line.startsWith('##')) {
|
|
334
|
-
return line;
|
|
335
|
-
}
|
|
336
|
-
const parsedHeading = parseMarkdownHeadingId(line);
|
|
337
|
-
// Do not process if id is already there
|
|
338
|
-
if (parsedHeading.id && !overwrite) {
|
|
339
|
-
return line;
|
|
340
|
-
}
|
|
341
|
-
return addHeadingId(parsedHeading.text, slugger, maintainCase);
|
|
342
|
-
})
|
|
343
|
-
.join('\n');
|
|
344
|
-
}
|
|
345
256
|
//# sourceMappingURL=markdownUtils.js.map
|
package/lib/markdownUtils.js.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"markdownUtils.js","sourceRoot":"","sources":["../src/markdownUtils.ts"],"names":[],"mappings":";AAAA;;;;;GAKG;;;
|
|
1
|
+
{"version":3,"file":"markdownUtils.js","sourceRoot":"","sources":["../src/markdownUtils.ts"],"names":[],"mappings":"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"}
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@docusaurus/utils",
|
|
3
|
-
"version": "3.9.2-canary-
|
|
3
|
+
"version": "3.9.2-canary-6526",
|
|
4
4
|
"description": "Node utility functions for Docusaurus packages.",
|
|
5
5
|
"main": "./lib/index.js",
|
|
6
6
|
"types": "./lib/index.d.ts",
|
|
@@ -18,9 +18,9 @@
|
|
|
18
18
|
},
|
|
19
19
|
"license": "MIT",
|
|
20
20
|
"dependencies": {
|
|
21
|
-
"@docusaurus/logger": "3.9.2-canary-
|
|
22
|
-
"@docusaurus/types": "3.9.2-canary-
|
|
23
|
-
"@docusaurus/utils-common": "3.9.2-canary-
|
|
21
|
+
"@docusaurus/logger": "3.9.2-canary-6526",
|
|
22
|
+
"@docusaurus/types": "3.9.2-canary-6526",
|
|
23
|
+
"@docusaurus/utils-common": "3.9.2-canary-6526",
|
|
24
24
|
"escape-string-regexp": "^4.0.0",
|
|
25
25
|
"execa": "^5.1.1",
|
|
26
26
|
"file-loader": "^6.2.0",
|
|
@@ -51,5 +51,5 @@
|
|
|
51
51
|
"dedent": "^0.7.0",
|
|
52
52
|
"tmp-promise": "^3.0.3"
|
|
53
53
|
},
|
|
54
|
-
"gitHead": "
|
|
54
|
+
"gitHead": "a37ae138931cb80b31664f86a34f97671c00e409"
|
|
55
55
|
}
|
package/src/index.ts
CHANGED
|
@@ -68,17 +68,20 @@ export {
|
|
|
68
68
|
getTagVisibility,
|
|
69
69
|
} from './tags';
|
|
70
70
|
export {
|
|
71
|
-
parseMarkdownHeadingId,
|
|
72
|
-
escapeMarkdownHeadingIds,
|
|
73
71
|
unwrapMdxCodeBlocks,
|
|
74
72
|
admonitionTitleToDirectiveLabel,
|
|
75
73
|
createExcerpt,
|
|
76
74
|
DEFAULT_PARSE_FRONT_MATTER,
|
|
77
75
|
parseMarkdownContentTitle,
|
|
78
76
|
parseMarkdownFile,
|
|
77
|
+
} from './markdownUtils';
|
|
78
|
+
export {
|
|
79
|
+
parseMarkdownHeadingId,
|
|
80
|
+
escapeMarkdownHeadingIds,
|
|
79
81
|
writeMarkdownHeadingId,
|
|
82
|
+
type HeadingIdSyntax,
|
|
80
83
|
type WriteHeadingIDOptions,
|
|
81
|
-
} from './
|
|
84
|
+
} from './markdownHeadingIdUtils';
|
|
82
85
|
export {
|
|
83
86
|
type ContentPaths,
|
|
84
87
|
type SourceToPermalink,
|
|
@@ -0,0 +1,209 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Copyright (c) Facebook, Inc. and its affiliates.
|
|
3
|
+
*
|
|
4
|
+
* This source code is licensed under the MIT license found in the
|
|
5
|
+
* LICENSE file in the root directory of this source tree.
|
|
6
|
+
*/
|
|
7
|
+
|
|
8
|
+
import {createSlugger, type Slugger, type SluggerOptions} from './slugger';
|
|
9
|
+
|
|
10
|
+
/**
|
|
11
|
+
* The syntax to use for heading IDs.
|
|
12
|
+
* - `classic` => `{#id}` (invalid MDX, but commonly supported)
|
|
13
|
+
* - `mdx-comment` => `{/* #id * /}` (valid MDX)
|
|
14
|
+
*/
|
|
15
|
+
export type HeadingIdSyntax = 'classic' | 'mdx-comment';
|
|
16
|
+
|
|
17
|
+
/**
|
|
18
|
+
* Parses custom ID from a heading. The ID can contain any characters except
|
|
19
|
+
* `{#` and `}`.
|
|
20
|
+
*
|
|
21
|
+
* @param heading e.g. `## Some heading {#some-heading}` where the last
|
|
22
|
+
* character must be `}` for the ID to be recognized
|
|
23
|
+
* @param syntax which heading ID syntax to recognize
|
|
24
|
+
*/
|
|
25
|
+
export function parseMarkdownHeadingId(
|
|
26
|
+
heading: string,
|
|
27
|
+
syntax: HeadingIdSyntax = 'classic',
|
|
28
|
+
): {
|
|
29
|
+
/**
|
|
30
|
+
* The heading content sans the ID part, right-trimmed. e.g. `## Some heading`
|
|
31
|
+
*/
|
|
32
|
+
text: string;
|
|
33
|
+
/** The heading ID. e.g. `some-heading` */
|
|
34
|
+
id: string | undefined;
|
|
35
|
+
} {
|
|
36
|
+
// Classic syntax: {#my-id}
|
|
37
|
+
if (syntax === 'classic') {
|
|
38
|
+
const customHeadingIdRegex = /\s*\{#(?<id>(?:.(?!\{#|\}))*.)\}$/;
|
|
39
|
+
const matches = customHeadingIdRegex.exec(heading);
|
|
40
|
+
if (matches) {
|
|
41
|
+
return {
|
|
42
|
+
text: heading.replace(matches[0]!, ''),
|
|
43
|
+
id: matches.groups!.id!.trim(),
|
|
44
|
+
};
|
|
45
|
+
}
|
|
46
|
+
}
|
|
47
|
+
// MDX comment syntax: {/* #my-id */}
|
|
48
|
+
// Note: this is only used for the "write-heading-ids" CLI
|
|
49
|
+
// The mdx loader is using a real MDX parser to find these comments
|
|
50
|
+
else if (syntax === 'mdx-comment') {
|
|
51
|
+
const mdxCommentHeadingIdRegex = /\s*\{\/\*\s*#(?<id>\S+)\s*\*\/\}$/;
|
|
52
|
+
const mdxMatches = mdxCommentHeadingIdRegex.exec(heading);
|
|
53
|
+
if (mdxMatches) {
|
|
54
|
+
return {
|
|
55
|
+
text: heading.replace(mdxMatches[0]!, ''),
|
|
56
|
+
id: mdxMatches.groups!.id!.trim(),
|
|
57
|
+
};
|
|
58
|
+
}
|
|
59
|
+
}
|
|
60
|
+
// Unhandled cases, shouldn't happen
|
|
61
|
+
else {
|
|
62
|
+
throw new Error(`unknown heading id syntax '${syntax}'`);
|
|
63
|
+
}
|
|
64
|
+
return {text: heading, id: undefined};
|
|
65
|
+
}
|
|
66
|
+
|
|
67
|
+
/**
|
|
68
|
+
* For our classic syntax, MDX v2+ now requires escaping { to compile: \{#id}.
|
|
69
|
+
* See https://mdxjs.com/docs/troubleshooting-mdx/#could-not-parse-expression-with-acorn-error
|
|
70
|
+
*/
|
|
71
|
+
export function escapeMarkdownHeadingIds(content: string): string {
|
|
72
|
+
const markdownHeadingRegexp = /(?:^|\n)#{1,6}(?!#).*/g;
|
|
73
|
+
return content.replaceAll(markdownHeadingRegexp, (substring) =>
|
|
74
|
+
// TODO probably not the most efficient impl...
|
|
75
|
+
substring
|
|
76
|
+
.replace('{#', '\\{#')
|
|
77
|
+
// prevent duplicate escaping
|
|
78
|
+
.replace('\\\\{#', '\\{#'),
|
|
79
|
+
);
|
|
80
|
+
}
|
|
81
|
+
|
|
82
|
+
function addHeadingId(
|
|
83
|
+
line: string,
|
|
84
|
+
slugger: Slugger,
|
|
85
|
+
maintainCase: boolean,
|
|
86
|
+
syntax: HeadingIdSyntax,
|
|
87
|
+
headingId: string | undefined,
|
|
88
|
+
): string {
|
|
89
|
+
let headingLevel = 0;
|
|
90
|
+
while (line.charAt(headingLevel) === '#') {
|
|
91
|
+
headingLevel += 1;
|
|
92
|
+
}
|
|
93
|
+
|
|
94
|
+
const headingHashes = line.slice(0, headingLevel);
|
|
95
|
+
|
|
96
|
+
const headingContent = line.slice(headingLevel).trimEnd();
|
|
97
|
+
|
|
98
|
+
function getHeadingId() {
|
|
99
|
+
if (headingId) {
|
|
100
|
+
return headingId;
|
|
101
|
+
}
|
|
102
|
+
// Unwrap links
|
|
103
|
+
// "[ Hello](https://example.com) World " => "Hello world"
|
|
104
|
+
const headingText = headingContent
|
|
105
|
+
.replace(/\[(?<alt>[^\]]+)\]\([^)]+\)/g, (_match, p1: string) => p1)
|
|
106
|
+
.trim();
|
|
107
|
+
|
|
108
|
+
return slugger.slug(headingText, {
|
|
109
|
+
maintainCase,
|
|
110
|
+
});
|
|
111
|
+
}
|
|
112
|
+
|
|
113
|
+
const headingIdSuffix =
|
|
114
|
+
syntax === 'mdx-comment'
|
|
115
|
+
? `{/* #${getHeadingId()} */}`
|
|
116
|
+
: `{#${getHeadingId()}}`;
|
|
117
|
+
|
|
118
|
+
return `${headingHashes}${headingContent} ${headingIdSuffix}`;
|
|
119
|
+
}
|
|
120
|
+
|
|
121
|
+
export type WriteHeadingIDOptions = SluggerOptions & {
|
|
122
|
+
/** The target syntax to use for heading IDs. */
|
|
123
|
+
syntax?: HeadingIdSyntax;
|
|
124
|
+
/** Migrate the existing heading IDs to the target syntax */
|
|
125
|
+
migrate?: boolean;
|
|
126
|
+
/** Overwrite existing heading IDs by re-generating them from the text. */
|
|
127
|
+
overwrite?: boolean;
|
|
128
|
+
};
|
|
129
|
+
|
|
130
|
+
/**
|
|
131
|
+
* Takes Markdown content, returns new content with heading IDs written.
|
|
132
|
+
* Respects existing IDs (unless `overwrite=true`) and never generates colliding
|
|
133
|
+
* IDs (through the slugger).
|
|
134
|
+
*/
|
|
135
|
+
export function writeMarkdownHeadingId(
|
|
136
|
+
content: string,
|
|
137
|
+
options: WriteHeadingIDOptions = {},
|
|
138
|
+
): string {
|
|
139
|
+
const {
|
|
140
|
+
syntax = 'classic', // Maybe we'll want to change this default later?
|
|
141
|
+
overwrite = false,
|
|
142
|
+
migrate = false,
|
|
143
|
+
maintainCase = false,
|
|
144
|
+
} = options;
|
|
145
|
+
|
|
146
|
+
// For now, we have 2 booleans (retro compatible)
|
|
147
|
+
// but it could be useful to have a "mode" enum instead?
|
|
148
|
+
if (overwrite && migrate) {
|
|
149
|
+
throw new Error(
|
|
150
|
+
'Heading ids can either be overwritten or migrated, not both at the same time',
|
|
151
|
+
);
|
|
152
|
+
}
|
|
153
|
+
|
|
154
|
+
const lines = content.split('\n');
|
|
155
|
+
const slugger = createSlugger();
|
|
156
|
+
|
|
157
|
+
// Parse heading ID trying both syntaxes (classic first, then mdx-comment)
|
|
158
|
+
function parseHeadingIdAnySyntax(heading: string) {
|
|
159
|
+
const classic = parseMarkdownHeadingId(heading, 'classic');
|
|
160
|
+
if (classic.id) {
|
|
161
|
+
return classic;
|
|
162
|
+
}
|
|
163
|
+
return parseMarkdownHeadingId(heading, 'mdx-comment');
|
|
164
|
+
}
|
|
165
|
+
|
|
166
|
+
// If we can't overwrite existing slugs, make sure other headings don't
|
|
167
|
+
// generate colliding slugs by first marking these slugs as occupied
|
|
168
|
+
if (!overwrite) {
|
|
169
|
+
lines.forEach((line) => {
|
|
170
|
+
const parsedHeading = parseHeadingIdAnySyntax(line);
|
|
171
|
+
if (parsedHeading.id) {
|
|
172
|
+
slugger.slug(parsedHeading.id);
|
|
173
|
+
}
|
|
174
|
+
});
|
|
175
|
+
}
|
|
176
|
+
|
|
177
|
+
let inCode = false;
|
|
178
|
+
return lines
|
|
179
|
+
.map((line) => {
|
|
180
|
+
if (line.startsWith('```')) {
|
|
181
|
+
inCode = !inCode;
|
|
182
|
+
return line;
|
|
183
|
+
}
|
|
184
|
+
// Ignore h1 headings, as we don't create anchor links for those
|
|
185
|
+
if (inCode || !line.startsWith('##')) {
|
|
186
|
+
return line;
|
|
187
|
+
}
|
|
188
|
+
const parsedHeading = parseHeadingIdAnySyntax(line);
|
|
189
|
+
|
|
190
|
+
// Preserve the line if id is already there, unless we migrate/overwrite
|
|
191
|
+
if (parsedHeading.id && !overwrite && !migrate) {
|
|
192
|
+
return line;
|
|
193
|
+
}
|
|
194
|
+
const headingId = overwrite
|
|
195
|
+
? undefined
|
|
196
|
+
: migrate
|
|
197
|
+
? parsedHeading.id
|
|
198
|
+
: undefined;
|
|
199
|
+
|
|
200
|
+
return addHeadingId(
|
|
201
|
+
parsedHeading.text,
|
|
202
|
+
slugger,
|
|
203
|
+
maintainCase,
|
|
204
|
+
syntax,
|
|
205
|
+
headingId,
|
|
206
|
+
);
|
|
207
|
+
})
|
|
208
|
+
.join('\n');
|
|
209
|
+
}
|
package/src/markdownUtils.ts
CHANGED
|
@@ -7,7 +7,6 @@
|
|
|
7
7
|
|
|
8
8
|
import logger from '@docusaurus/logger';
|
|
9
9
|
import matter from 'gray-matter';
|
|
10
|
-
import {createSlugger, type Slugger, type SluggerOptions} from './slugger';
|
|
11
10
|
import type {
|
|
12
11
|
ParseFrontMatter,
|
|
13
12
|
DefaultParseFrontMatter,
|
|
@@ -17,47 +16,6 @@ import type {
|
|
|
17
16
|
// server-side when we infer metadata like `title` and `description` from the
|
|
18
17
|
// content. Most parsing is still done in MDX through the mdx-loader.
|
|
19
18
|
|
|
20
|
-
/**
|
|
21
|
-
* Parses custom ID from a heading. The ID can contain any characters except
|
|
22
|
-
* `{#` and `}`.
|
|
23
|
-
*
|
|
24
|
-
* @param heading e.g. `## Some heading {#some-heading}` where the last
|
|
25
|
-
* character must be `}` for the ID to be recognized
|
|
26
|
-
*/
|
|
27
|
-
export function parseMarkdownHeadingId(heading: string): {
|
|
28
|
-
/**
|
|
29
|
-
* The heading content sans the ID part, right-trimmed. e.g. `## Some heading`
|
|
30
|
-
*/
|
|
31
|
-
text: string;
|
|
32
|
-
/** The heading ID. e.g. `some-heading` */
|
|
33
|
-
id: string | undefined;
|
|
34
|
-
} {
|
|
35
|
-
const customHeadingIdRegex = /\s*\{#(?<id>(?:.(?!\{#|\}))*.)\}$/;
|
|
36
|
-
const matches = customHeadingIdRegex.exec(heading);
|
|
37
|
-
if (matches) {
|
|
38
|
-
return {
|
|
39
|
-
text: heading.replace(matches[0]!, ''),
|
|
40
|
-
id: matches.groups!.id!,
|
|
41
|
-
};
|
|
42
|
-
}
|
|
43
|
-
return {text: heading, id: undefined};
|
|
44
|
-
}
|
|
45
|
-
|
|
46
|
-
/**
|
|
47
|
-
* MDX 2 requires escaping { with a \ so our anchor syntax need that now.
|
|
48
|
-
* See https://mdxjs.com/docs/troubleshooting-mdx/#could-not-parse-expression-with-acorn-error
|
|
49
|
-
*/
|
|
50
|
-
export function escapeMarkdownHeadingIds(content: string): string {
|
|
51
|
-
const markdownHeadingRegexp = /(?:^|\n)#{1,6}(?!#).*/g;
|
|
52
|
-
return content.replaceAll(markdownHeadingRegexp, (substring) =>
|
|
53
|
-
// TODO probably not the most efficient impl...
|
|
54
|
-
substring
|
|
55
|
-
.replace('{#', '\\{#')
|
|
56
|
-
// prevent duplicate escaping
|
|
57
|
-
.replace('\\\\{#', '\\{#'),
|
|
58
|
-
);
|
|
59
|
-
}
|
|
60
|
-
|
|
61
19
|
/**
|
|
62
20
|
* Hacky temporary escape hatch for Crowdin bad MDX support
|
|
63
21
|
* See https://docusaurus.io/docs/i18n/crowdin#mdx
|
|
@@ -383,80 +341,3 @@ This can happen if you use special characters in front matter values (try using
|
|
|
383
341
|
throw err;
|
|
384
342
|
}
|
|
385
343
|
}
|
|
386
|
-
|
|
387
|
-
function unwrapMarkdownLinks(line: string): string {
|
|
388
|
-
return line.replace(
|
|
389
|
-
/\[(?<alt>[^\]]+)\]\([^)]+\)/g,
|
|
390
|
-
(match, p1: string) => p1,
|
|
391
|
-
);
|
|
392
|
-
}
|
|
393
|
-
|
|
394
|
-
function addHeadingId(
|
|
395
|
-
line: string,
|
|
396
|
-
slugger: Slugger,
|
|
397
|
-
maintainCase: boolean,
|
|
398
|
-
): string {
|
|
399
|
-
let headingLevel = 0;
|
|
400
|
-
while (line.charAt(headingLevel) === '#') {
|
|
401
|
-
headingLevel += 1;
|
|
402
|
-
}
|
|
403
|
-
|
|
404
|
-
const headingText = line.slice(headingLevel).trimEnd();
|
|
405
|
-
const headingHashes = line.slice(0, headingLevel);
|
|
406
|
-
const slug = slugger.slug(unwrapMarkdownLinks(headingText).trim(), {
|
|
407
|
-
maintainCase,
|
|
408
|
-
});
|
|
409
|
-
|
|
410
|
-
return `${headingHashes}${headingText} {#${slug}}`;
|
|
411
|
-
}
|
|
412
|
-
|
|
413
|
-
export type WriteHeadingIDOptions = SluggerOptions & {
|
|
414
|
-
/** Overwrite existing heading IDs. */
|
|
415
|
-
overwrite?: boolean;
|
|
416
|
-
};
|
|
417
|
-
|
|
418
|
-
/**
|
|
419
|
-
* Takes Markdown content, returns new content with heading IDs written.
|
|
420
|
-
* Respects existing IDs (unless `overwrite=true`) and never generates colliding
|
|
421
|
-
* IDs (through the slugger).
|
|
422
|
-
*/
|
|
423
|
-
export function writeMarkdownHeadingId(
|
|
424
|
-
content: string,
|
|
425
|
-
options: WriteHeadingIDOptions = {maintainCase: false, overwrite: false},
|
|
426
|
-
): string {
|
|
427
|
-
const {maintainCase = false, overwrite = false} = options;
|
|
428
|
-
const lines = content.split('\n');
|
|
429
|
-
const slugger = createSlugger();
|
|
430
|
-
|
|
431
|
-
// If we can't overwrite existing slugs, make sure other headings don't
|
|
432
|
-
// generate colliding slugs by first marking these slugs as occupied
|
|
433
|
-
if (!overwrite) {
|
|
434
|
-
lines.forEach((line) => {
|
|
435
|
-
const parsedHeading = parseMarkdownHeadingId(line);
|
|
436
|
-
if (parsedHeading.id) {
|
|
437
|
-
slugger.slug(parsedHeading.id);
|
|
438
|
-
}
|
|
439
|
-
});
|
|
440
|
-
}
|
|
441
|
-
|
|
442
|
-
let inCode = false;
|
|
443
|
-
return lines
|
|
444
|
-
.map((line) => {
|
|
445
|
-
if (line.startsWith('```')) {
|
|
446
|
-
inCode = !inCode;
|
|
447
|
-
return line;
|
|
448
|
-
}
|
|
449
|
-
// Ignore h1 headings, as we don't create anchor links for those
|
|
450
|
-
if (inCode || !line.startsWith('##')) {
|
|
451
|
-
return line;
|
|
452
|
-
}
|
|
453
|
-
const parsedHeading = parseMarkdownHeadingId(line);
|
|
454
|
-
|
|
455
|
-
// Do not process if id is already there
|
|
456
|
-
if (parsedHeading.id && !overwrite) {
|
|
457
|
-
return line;
|
|
458
|
-
}
|
|
459
|
-
return addHeadingId(parsedHeading.text, slugger, maintainCase);
|
|
460
|
-
})
|
|
461
|
-
.join('\n');
|
|
462
|
-
}
|