From 1a9eb261b528afb4a9fb846fc63fc99eb200f8d3 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=E5=B1=B1=E5=90=B9=E8=89=B2=E5=BE=A1=E5=AE=88?= <85992002+KazariEX@users.noreply.github.com> Date: Sat, 2 Nov 2024 19:26:20 +0800 Subject: [PATCH] fix(language-core): generate script setup starting from last leading comment without `@ts-check` (#4900) --- .../lib/codegen/script/scriptSetup.ts | 2 +- .../lib/parsers/scriptSetupRanges.ts | 8 +++++++- .../tsc/passedFixtures/vue3/#4899/main.vue | 15 +++++++++++++++ 3 files changed, 23 insertions(+), 2 deletions(-) create mode 100644 test-workspace/tsc/passedFixtures/vue3/#4899/main.vue diff --git a/packages/language-core/lib/codegen/script/scriptSetup.ts b/packages/language-core/lib/codegen/script/scriptSetup.ts index 1ed0398144..491a4328ff 100644 --- a/packages/language-core/lib/codegen/script/scriptSetup.ts +++ b/packages/language-core/lib/codegen/script/scriptSetup.ts @@ -249,7 +249,7 @@ function* generateSetupFunction( } setupCodeModifies = setupCodeModifies.sort((a, b) => a[1] - b[1]); - let nextStart = scriptSetupRanges.importSectionEndOffset; + let nextStart = Math.max(scriptSetupRanges.importSectionEndOffset, scriptSetupRanges.leadingCommentEndOffset); for (const [codes, start, end] of setupCodeModifies) { yield generateSfcBlockSection(scriptSetup, nextStart, start, codeFeatures.all); for (const code of codes) { diff --git a/packages/language-core/lib/parsers/scriptSetupRanges.ts b/packages/language-core/lib/parsers/scriptSetupRanges.ts index d3c62def2d..b020a7f24b 100644 --- a/packages/language-core/lib/parsers/scriptSetupRanges.ts +++ b/packages/language-core/lib/parsers/scriptSetupRanges.ts @@ -2,6 +2,8 @@ import type * as ts from 'typescript'; import { collectIdentifiers } from '../codegen/utils'; import type { TextRange, VueCompilerOptions } from '../types'; +const tsCheckReg = /^\/\/\s*@ts-(?:no)?check($|\s)/; + export interface ScriptSetupRanges extends ReturnType { } export function parseScriptSetupRanges( @@ -66,9 +68,13 @@ export function parseScriptSetupRanges( isModel?: boolean; }[] = []; const text = ast.text; - const leadingCommentEndOffset = ts.getLeadingCommentRanges(text, 0)?.reverse()[0].end ?? 0; const importComponentNames = new Set(); + const leadingCommentRanges = ts.getLeadingCommentRanges(text, 0)?.reverse() ?? []; + const leadingCommentEndOffset = leadingCommentRanges.find( + range => tsCheckReg.test(text.slice(range.pos, range.end)) + )?.end ?? 0; + let bindings = parseBindingRanges(ts, ast); ts.forEachChild(ast, node => { diff --git a/test-workspace/tsc/passedFixtures/vue3/#4899/main.vue b/test-workspace/tsc/passedFixtures/vue3/#4899/main.vue new file mode 100644 index 0000000000..d37484012e --- /dev/null +++ b/test-workspace/tsc/passedFixtures/vue3/#4899/main.vue @@ -0,0 +1,15 @@ + \ No newline at end of file