diff --git a/package.json b/package.json index 43a9694..4601b91 100644 --- a/package.json +++ b/package.json @@ -75,7 +75,7 @@ "three": "^0.179.1", "tsparticles": "^3.9.1", "web-vitals": "^5.1.0", - "@lezer/common": "^1.5.0", + "@lezer/common": "1.5.0", "@lezer/highlight": "^1.2.3", "@lezer/lr": "^1.4.8" }, diff --git a/src/codemirror/fcTemplateLang/index.js b/src/codemirror/fcTemplateLang/index.js index 1c0e1ac..93e2bc6 100644 --- a/src/codemirror/fcTemplateLang/index.js +++ b/src/codemirror/fcTemplateLang/index.js @@ -35,11 +35,17 @@ const fcTemplateParser = ejsParser.configure({ }) ], wrap: parseMixed((node) => { + // Mount JS inside EJS bodies if (node.name === 'JavascriptExpression') { return { parser: javascriptLanguage.parser } } - if (node.name === 'Text') { - return { parser: xmlLanguage.parser } + // Overlay XML across all Text regions so tags that wrap EJS + // (e.g. <%= x %>) stay one coherent XML tree. + if (node.type.isTop) { + return { + parser: xmlLanguage.parser, + overlay: (n) => n.name === 'Text' + } } return null }) diff --git a/vite.config.js b/vite.config.js index 33c148b..2594c1e 100644 --- a/vite.config.js +++ b/vite.config.js @@ -35,7 +35,9 @@ const codemirrorSingletons = { '@codemirror/language': esmEntry('@codemirror/language'), '@codemirror/commands': esmEntry('@codemirror/commands'), '@codemirror/autocomplete': esmEntry('@codemirror/autocomplete'), - '@lezer/common': esmEntry('@lezer/common'), + // Must match the @lezer/common used by @codemirror/lang-* parsers (1.5.0). + // 1.5.2 breaks parseMixed tree walking across nested language mounts. + '@lezer/common': path.resolve(__dirname, 'node_modules/@lezer/common/dist/index.js'), '@lezer/lr': esmEntry('@lezer/lr'), '@lezer/highlight': esmEntry('@lezer/highlight') }