From a2b1490a01f6a62300ee99403bce61578ba94eb1 Mon Sep 17 00:00:00 2001 From: Otabek <60849894+otabekoff@users.noreply.github.com> Date: Fri, 1 Jul 2022 21:19:42 +0500 Subject: [PATCH 1/2] docs: add documentation for prev-next links (#889) Co-authored-by: Percy Ma Co-authored-by: Divyansh Singh <40380293+brc-dd@users.noreply.github.com> --- docs/guide/theme-prev-next-link.md | 52 +++++++++++++++++++++++++++++- 1 file changed, 51 insertions(+), 1 deletion(-) diff --git a/docs/guide/theme-prev-next-link.md b/docs/guide/theme-prev-next-link.md index c248d1f3..3c6454a0 100644 --- a/docs/guide/theme-prev-next-link.md +++ b/docs/guide/theme-prev-next-link.md @@ -1,3 +1,53 @@ # Prev Next Link -Documentation coming soon... +Prev or Next Link allows you to add buttons at the end of each page that allow you to go to the previous or next topic. To enable it, add `themeConfig.prev` or `themeConfig.next` to your configuration. + + +## prev + +- Type: `NavLink | string` + +- Details: + + Specify the link of the previous page. + + If you don't set this frontmatter, the link will be inferred from the sidebar config. + + To configure the prev link manually, you can set this frontmatter to a `NavLink` object or a string: + + - A `NavLink` object should have a `text` field and a `link` field. + - A string should be the path to the target page file. It will be converted to a `NavLink` object, whose `text` is the page title, and `link` is the page route path. + +- Example: + +```md +--- +# NavLink +prev: + text: Get Started + link: /guide/getting-started.html + +# NavLink - external url +prev: + text: GitHub + link: https://github.com + +# string - page file path +prev: /guide/getting-started.md + +# string - page file relative path +prev: ../../guide/getting-started.md +--- +``` + +## next + +- Type: `NavLink | string` + +- Details: + + Specify the link of the next page. + + If you don't set this frontmatter, the link will be inferred from the sidebar config. + + The type is the same as [prev](#prev) frontmatter. From 9d9db6227dff40734bf7129abb69f26412424486 Mon Sep 17 00:00:00 2001 From: meteorlxy Date: Sat, 2 Jul 2022 00:21:45 +0800 Subject: [PATCH 2/2] fix(build): handle vite constants replacement (#419) (#888) --- src/node/markdownToVue.ts | 72 ++++++++++++++++++++++++--------------- 1 file changed, 44 insertions(+), 28 deletions(-) diff --git a/src/node/markdownToVue.ts b/src/node/markdownToVue.ts index 049bd8d8..86a07750 100644 --- a/src/node/markdownToVue.ts +++ b/src/node/markdownToVue.ts @@ -34,14 +34,7 @@ export async function createMarkdownToVueRenderFn( pages = pages.map((p) => slash(p.replace(/\.md$/, ''))) - const userDefineRegex = userDefines - ? new RegExp( - `\\b(${Object.keys(userDefines) - .map((key) => key.replace(/[-[\]/{}()*+?.\\^$|]/g, '\\$&')) - .join('|')})`, - 'g' - ) - : null + const replaceRegex = genReplaceRegexp(userDefines, isBuild) return async ( src: string, @@ -74,24 +67,9 @@ export async function createMarkdownToVueRenderFn( md.__path = file md.__relativePath = relativePath - let html = md.render(content) + const html = md.render(content) const data = md.__data - if (isBuild) { - // avoid env variables being replaced by vite - html = html - .replace(/\bimport\.meta/g, 'import.meta') - .replace(/\bprocess\.env/g, 'process.env') - - // also avoid replacing vite user defines - if (userDefineRegex) { - html = html.replace( - userDefineRegex, - (_) => `${_[0]}${_.slice(1)}` - ) - } - } - // validate data.links const deadLinks: string[] = [] const recordDeadLink = (url: string) => { @@ -149,8 +127,14 @@ export async function createMarkdownToVueRenderFn( } const vueSrc = - genPageDataCode(data.hoistedTags || [], pageData).join('\n') + - `\n` + genPageDataCode(data.hoistedTags || [], pageData, replaceRegex).join( + '\n' + ) + + `\n` debug(`[render] ${file} in ${Date.now() - start}ms.`) @@ -171,10 +155,42 @@ const scriptSetupRE = /<\s*script[^>]*\bsetup\b[^>]*/ const scriptClientRE = /<\s*script[^>]*\bclient\b[^>]*/ const defaultExportRE = /((?:^|\n|;)\s*)export(\s*)default/ const namedDefaultExportRE = /((?:^|\n|;)\s*)export(.+)as(\s*)default/ +const jsStringBreaker = '\u200b' +const vueTemplateBreaker = '' + +function genReplaceRegexp( + userDefines: Record = {}, + isBuild: boolean +): RegExp { + // `process.env` need to be handled in both dev and build + // @see https://github.com/vitejs/vite/blob/cad27ee8c00bbd5aeeb2be9bfb3eb164c1b77885/packages/vite/src/node/plugins/clientInjections.ts#L57-L64 + const replacements = ['process.env'] + if (isBuild) { + replacements.push('import.meta', ...Object.keys(userDefines)) + } + return new RegExp( + `\\b(${replacements + .map((key) => key.replace(/[-[\]/{}()*+?.\\^$|]/g, '\\$&')) + .join('|')})`, + 'g' + ) +} + +/** + * To avoid env variables being replaced by vite: + * - insert `'\u200b'` char into those strings inside js string (page data) + * - insert `` tag into those strings inside html string (vue template) + * + * @see https://vitejs.dev/guide/env-and-mode.html#production-replacement + */ +function replaceConstants(str: string, replaceRegex: RegExp, breaker: string) { + return str.replace(replaceRegex, (_) => `${_[0]}${breaker}${_.slice(1)}`) +} -function genPageDataCode(tags: string[], data: PageData) { +function genPageDataCode(tags: string[], data: PageData, replaceRegex: RegExp) { + const dataJson = JSON.stringify(data) const code = `\nexport const __pageData = JSON.parse(${JSON.stringify( - JSON.stringify(data) + replaceConstants(dataJson, replaceRegex, jsStringBreaker) )})` const existingScriptIndex = tags.findIndex((tag) => {