From 7ca2ccf2a965e0fd13486bcbd05d9ab7aebeae3c Mon Sep 17 00:00:00 2001
From: Parv Ahuja <17094219+parvahuja@users.noreply.github.com>
Date: Fri, 24 Jul 2026 17:51:52 -0700
Subject: [PATCH] fix: keep generated Markdown content-only
---
.github/workflows/verify.yml | 2 +-
package.json | 2 +-
pnpm-lock.yaml | 10 +++---
scripts/check-markdown-components.mjs | 25 +++++++++++--
src/lib/markdown-output.test.ts | 51 +++++++++++++++++++++++++++
src/lib/markdown-output.ts | 5 ++-
6 files changed, 84 insertions(+), 11 deletions(-)
diff --git a/.github/workflows/verify.yml b/.github/workflows/verify.yml
index 25feda19..da6bd7b8 100644
--- a/.github/workflows/verify.yml
+++ b/.github/workflows/verify.yml
@@ -58,7 +58,7 @@ jobs:
NODE_OPTIONS: --max-old-space-size=4096
VERCEL_ENV: production
- - name: Audit Markdown components
+ - name: Audit generated Markdown
run: pnpm run check:markdown
- name: Check generated public links
diff --git a/package.json b/package.json
index 96ff2007..6e476e51 100644
--- a/package.json
+++ b/package.json
@@ -64,7 +64,7 @@
"unplugin-auto-import": "^21.0.0",
"unplugin-icons": "^23.0.1",
"viem": "^2.54.6",
- "vocs": "https://pkg.pr.new/wevm/vocs/vocs@e1a70dc00507fade986b2f9b033f26906d037748",
+ "vocs": "https://pkg.pr.new/wevm/vocs/vocs@60cc0b17cd78f4cf8da0eb20f47e64f4d701e028",
"wagmi": "3.6.20",
"waku": "^1.0.0-beta.6",
"webauthx": "~0.1.2",
diff --git a/pnpm-lock.yaml b/pnpm-lock.yaml
index 0737404d..30e72a17 100644
--- a/pnpm-lock.yaml
+++ b/pnpm-lock.yaml
@@ -139,8 +139,8 @@ importers:
specifier: ^2.54.6
version: 2.54.6(typescript@6.0.3)(zod@4.4.3)
vocs:
- specifier: https://pkg.pr.new/wevm/vocs/vocs@e1a70dc00507fade986b2f9b033f26906d037748
- version: https://pkg.pr.new/wevm/vocs/vocs@e1a70dc00507fade986b2f9b033f26906d037748(@cfworker/json-schema@4.1.1)(@types/react@19.2.17)(@vue/compiler-sfc@3.5.38)(change-case@5.4.4)(esbuild@0.28.1)(idb-keyval@6.2.2)(mermaid@11.14.0)(react-dom@19.2.7(react@19.2.7))(react-server-dom-webpack@19.2.7(react-dom@19.2.7(react@19.2.7))(react@19.2.7)(webpack@5.104.1(esbuild@0.28.1)))(react@19.2.7)(rolldown@1.1.4)(rollup@4.60.1)(typescript@6.0.3)(vite@8.1.0(@types/node@26.0.1)(esbuild@0.28.1)(jiti@2.7.0)(terser@5.48.0)(tsx@4.22.4)(yaml@2.9.0))(waku@1.0.0-beta.6(@types/node@26.0.1)(esbuild@0.28.1)(jiti@2.7.0)(react-dom@19.2.7(react@19.2.7))(react-server-dom-webpack@19.2.7(react-dom@19.2.7(react@19.2.7))(react@19.2.7)(webpack@5.104.1(esbuild@0.28.1)))(react@19.2.7)(terser@5.48.0)(tsx@4.22.4)(yaml@2.9.0))(webpack@5.104.1(esbuild@0.28.1))
+ specifier: https://pkg.pr.new/wevm/vocs/vocs@60cc0b17cd78f4cf8da0eb20f47e64f4d701e028
+ version: https://pkg.pr.new/wevm/vocs/vocs@60cc0b17cd78f4cf8da0eb20f47e64f4d701e028(@cfworker/json-schema@4.1.1)(@types/react@19.2.17)(@vue/compiler-sfc@3.5.38)(change-case@5.4.4)(esbuild@0.28.1)(idb-keyval@6.2.2)(mermaid@11.14.0)(react-dom@19.2.7(react@19.2.7))(react-server-dom-webpack@19.2.7(react-dom@19.2.7(react@19.2.7))(react@19.2.7)(webpack@5.104.1(esbuild@0.28.1)))(react@19.2.7)(rolldown@1.1.4)(rollup@4.60.1)(typescript@6.0.3)(vite@8.1.0(@types/node@26.0.1)(esbuild@0.28.1)(jiti@2.7.0)(terser@5.48.0)(tsx@4.22.4)(yaml@2.9.0))(waku@1.0.0-beta.6(@types/node@26.0.1)(esbuild@0.28.1)(jiti@2.7.0)(react-dom@19.2.7(react@19.2.7))(react-server-dom-webpack@19.2.7(react-dom@19.2.7(react@19.2.7))(react@19.2.7)(webpack@5.104.1(esbuild@0.28.1)))(react@19.2.7)(terser@5.48.0)(tsx@4.22.4)(yaml@2.9.0))(webpack@5.104.1(esbuild@0.28.1))
wagmi:
specifier: 3.6.20
version: 3.6.20(@tanstack/query-core@5.101.2)(@tanstack/react-query@5.101.2(react@19.2.7))(@types/react@19.2.17)(accounts@0.14.11)(react@19.2.7)(typescript@6.0.3)(viem@2.54.6(typescript@6.0.3)(zod@4.4.3))
@@ -4980,8 +4980,8 @@ packages:
waku:
optional: true
- vocs@https://pkg.pr.new/wevm/vocs/vocs@e1a70dc00507fade986b2f9b033f26906d037748:
- resolution: {integrity: sha512-uMzPryXH0HfyTiOlTom5aeMcYXgVZGlJFjKz+gq+XRLhxCkqf8PUiSyU5EBqTx+TRx6NkXdUaFlOuP53E0aN7g==, tarball: https://pkg.pr.new/wevm/vocs/vocs@e1a70dc00507fade986b2f9b033f26906d037748}
+ vocs@https://pkg.pr.new/wevm/vocs/vocs@60cc0b17cd78f4cf8da0eb20f47e64f4d701e028:
+ resolution: {integrity: sha512-wPhE/6Uc1zYq38lt9mgs3Z6gYCYFx1cOeZY+BOAcfFqPkm782P7aEKu5a7p9TzRtoG+wRZUqM2fqAksqPp/aKw==, tarball: https://pkg.pr.new/wevm/vocs/vocs@60cc0b17cd78f4cf8da0eb20f47e64f4d701e028}
version: 2.6.2
hasBin: true
peerDependencies:
@@ -10548,7 +10548,7 @@ snapshots:
- vue-template-es2015-compiler
- webpack
- vocs@https://pkg.pr.new/wevm/vocs/vocs@e1a70dc00507fade986b2f9b033f26906d037748(@cfworker/json-schema@4.1.1)(@types/react@19.2.17)(@vue/compiler-sfc@3.5.38)(change-case@5.4.4)(esbuild@0.28.1)(idb-keyval@6.2.2)(mermaid@11.14.0)(react-dom@19.2.7(react@19.2.7))(react-server-dom-webpack@19.2.7(react-dom@19.2.7(react@19.2.7))(react@19.2.7)(webpack@5.104.1(esbuild@0.28.1)))(react@19.2.7)(rolldown@1.1.4)(rollup@4.60.1)(typescript@6.0.3)(vite@8.1.0(@types/node@26.0.1)(esbuild@0.28.1)(jiti@2.7.0)(terser@5.48.0)(tsx@4.22.4)(yaml@2.9.0))(waku@1.0.0-beta.6(@types/node@26.0.1)(esbuild@0.28.1)(jiti@2.7.0)(react-dom@19.2.7(react@19.2.7))(react-server-dom-webpack@19.2.7(react-dom@19.2.7(react@19.2.7))(react@19.2.7)(webpack@5.104.1(esbuild@0.28.1)))(react@19.2.7)(terser@5.48.0)(tsx@4.22.4)(yaml@2.9.0))(webpack@5.104.1(esbuild@0.28.1)):
+ vocs@https://pkg.pr.new/wevm/vocs/vocs@60cc0b17cd78f4cf8da0eb20f47e64f4d701e028(@cfworker/json-schema@4.1.1)(@types/react@19.2.17)(@vue/compiler-sfc@3.5.38)(change-case@5.4.4)(esbuild@0.28.1)(idb-keyval@6.2.2)(mermaid@11.14.0)(react-dom@19.2.7(react@19.2.7))(react-server-dom-webpack@19.2.7(react-dom@19.2.7(react@19.2.7))(react@19.2.7)(webpack@5.104.1(esbuild@0.28.1)))(react@19.2.7)(rolldown@1.1.4)(rollup@4.60.1)(typescript@6.0.3)(vite@8.1.0(@types/node@26.0.1)(esbuild@0.28.1)(jiti@2.7.0)(terser@5.48.0)(tsx@4.22.4)(yaml@2.9.0))(waku@1.0.0-beta.6(@types/node@26.0.1)(esbuild@0.28.1)(jiti@2.7.0)(react-dom@19.2.7(react@19.2.7))(react-server-dom-webpack@19.2.7(react-dom@19.2.7(react@19.2.7))(react@19.2.7)(webpack@5.104.1(esbuild@0.28.1)))(react@19.2.7)(terser@5.48.0)(tsx@4.22.4)(yaml@2.9.0))(webpack@5.104.1(esbuild@0.28.1)):
dependencies:
'@base-ui/react': 1.6.0(@types/react@19.2.17)(react-dom@19.2.7(react@19.2.7))(react@19.2.7)
'@codesandbox/sandpack-react': 2.20.0(react-dom@19.2.7(react@19.2.7))(react@19.2.7)
diff --git a/scripts/check-markdown-components.mjs b/scripts/check-markdown-components.mjs
index 9e10e7c6..cf4ecfdd 100644
--- a/scripts/check-markdown-components.mjs
+++ b/scripts/check-markdown-components.mjs
@@ -57,24 +57,43 @@ if (unresolvedIncludes.length > 0) {
}
const generatedComponents = new Set()
+const generatedEsmFiles = new Set()
+const generatedExpressions = new Set()
+const generatedPresentationElements = []
for (const file of generatedFiles) {
const content = await readFile(file, 'utf8')
const parseableContent = maskHtmlComments(content)
const tree = unified().use(remarkParse).use(remarkMdx).parse(parseableContent)
visit(tree, (node) => {
+ if (node.type === 'mdxjsEsm') generatedEsmFiles.add(file)
+ if (node.type === 'mdxFlowExpression' || node.type === 'mdxTextExpression')
+ generatedExpressions.add(file)
if (node.type !== 'mdxJsxFlowElement' && node.type !== 'mdxJsxTextElement') return
+ if (/^(?:meta|script|style|title)$/.test(node.name ?? ''))
+ generatedPresentationElements.push({ file, name: node.name })
if (!/^[A-Z][A-Za-z0-9]*(?:\.[A-Za-z0-9]+)*$/.test(node.name ?? '')) return
generatedComponents.add(node.name)
})
}
-if (generatedComponents.size > 0) {
- console.error('Generated Markdown component audit failed.')
+if (
+ generatedComponents.size > 0 ||
+ generatedEsmFiles.size > 0 ||
+ generatedExpressions.size > 0 ||
+ generatedPresentationElements.length > 0
+) {
+ console.error('Generated Markdown syntax audit failed.')
for (const name of generatedComponents) console.error(`- ${name}: unresolved component`)
+ for (const file of generatedEsmFiles) console.error(`- ${file}: executable import or export`)
+ for (const file of generatedExpressions) console.error(`- ${file}: executable expression`)
+ for (const { file, name } of generatedPresentationElements)
+ console.error(`- ${file}: presentation-only <${name}> element`)
process.exit(1)
}
-console.log('Markdown output audit passed (no unresolved component types or includes).')
+console.log(
+ 'Markdown output audit passed (no unresolved components, includes, executable MDX, or presentation-only elements).',
+)
function maskHtmlComments(content) {
const ranges = []
diff --git a/src/lib/markdown-output.test.ts b/src/lib/markdown-output.test.ts
index a64daa27..85fa2347 100644
--- a/src/lib/markdown-output.test.ts
+++ b/src/lib/markdown-output.test.ts
@@ -95,6 +95,57 @@ Status: