Skip to content

perf(language-core): drop internal component #5532

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Draft
wants to merge 35 commits into
base: master
Choose a base branch
from
Draft
Changes from 1 commit
Commits
Show all changes
35 commits
Select commit Hold shift + click to select a range
7cbcb3f
refactor: use variable `__VLS_export` to receive component and export…
KazariEX Jul 18, 2025
72f9dcc
perf: drop internal component
KazariEX Jul 18, 2025
c0b0b77
test: update snapshot
KazariEX Jul 18, 2025
2c87740
refactor: extract `__VLS_ProxyRefs`
KazariEX Jul 18, 2025
0a3d327
refactor: remove `__VLS_makeOptional`
KazariEX Jul 18, 2025
18a2ddb
fix: generate bindings after template variable collection
KazariEX Jul 18, 2025
fb1f1a3
feat: emits to props and drop internal component for generic
KazariEX Jul 19, 2025
7a9c120
refactor: simplify conditional logic
KazariEX Jul 19, 2025
e992097
fix: `withDefaults` and bypass boolean casting
KazariEX Jul 20, 2025
81854db
refactor: simplify
KazariEX Jul 20, 2025
850c2c6
fix: intersect `__VLS_PublicProps` on demand
KazariEX Jul 20, 2025
ee3eda0
refactor: `Code` to `string` for `.join(' & ')`
KazariEX Jul 20, 2025
d18dd97
fix: runtime props for generic component
KazariEX Jul 22, 2025
011e562
refactor: add `Partial` to inherited attrs in advance
KazariEX Jul 22, 2025
645dcb7
refactor: generate setup function as needed
KazariEX Jul 22, 2025
49b04c1
refactor: reduce usage of `generateIntersectMerge`
KazariEX Jul 22, 2025
4941987
refactor: only generate `ShallowUnwrapRef` for explicitly defined exp…
KazariEX Jul 22, 2025
e1bbf75
refactor: remove outdated fix for #1187
KazariEX Jul 22, 2025
cb72c6f
fix: only generate jsx slot props into `__VLS_PublicProps`
KazariEX Jul 22, 2025
4980a3f
refactor: split `generateModels` and `generatePublicProps`
KazariEX Jul 26, 2025
3843fbd
refactor: generate `__VLS_dollars` on demand
KazariEX Jul 26, 2025
64a0c22
Merge remote-tracking branch 'upstream' into perf/drop-internal-compo…
KazariEX Jul 26, 2025
127e847
refactor: simplify bindings iteration
KazariEX Jul 26, 2025
90f84f6
fix: revert access external variables detection
KazariEX Jul 26, 2025
8c152d4
refactor: remove unnecessary component name conditionals
KazariEX Jul 26, 2025
db1e456
refactor: remove `__VLS_definePublicProps`
KazariEX Jul 26, 2025
8e632ef
fix: jsdoc for export default
KazariEX Jul 27, 2025
66e6fbd
Merge remote-tracking branch 'upstream' into perf/drop-internal-compo…
KazariEX Jul 27, 2025
f987f39
test: update snapshot
KazariEX Jul 27, 2025
d4fc864
refactor: simplify local types generation
KazariEX Jul 27, 2025
a74a459
fix: compatible with class components
KazariEX Jul 28, 2025
97d9889
refactor: simplify template usage variables collection
KazariEX Jul 28, 2025
a892968
refactor: remove unnecessary bound mapping
KazariEX Jul 28, 2025
7da37e2
fix: compatible with script src
KazariEX Aug 1, 2025
990d5ec
Merge remote-tracking branch 'upstream' into perf/drop-internal-compo…
KazariEX Aug 2, 2025
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
Prev Previous commit
Next Next commit
refactor: split generateModels and generatePublicProps
  • Loading branch information
KazariEX committed Jul 26, 2025
commit 4980a3f056ec6ee0698cc8f69ad66e35aad744ea
182 changes: 95 additions & 87 deletions packages/language-core/lib/codegen/script/scriptSetup.ts
Original file line number Diff line number Diff line change
Expand Up @@ -324,8 +324,8 @@ function* generateSetupFunction(
|| options.templateCodegen?.dynamicSlots.length
);

yield* generateComponentProps(options, ctx, scriptSetup, scriptSetupRanges, hasSlots);
yield* generateModelEmit(scriptSetup, scriptSetupRanges);
yield* generateModels(scriptSetup, scriptSetupRanges);
yield* generatePublicProps(options, ctx, scriptSetup, scriptSetupRanges, hasSlots);
yield* generateTemplate(options, ctx);

if (syntax) {
Expand Down Expand Up @@ -436,7 +436,7 @@ function* generateDefineWithType(
}
}

function* generateComponentProps(
function* generatePublicProps(
options: ScriptCodegenOptions,
ctx: ScriptCodegenContext,
scriptSetup: NonNullable<Sfc['scriptSetup']>,
Expand All @@ -454,21 +454,6 @@ function* generateComponentProps(
yield endOfLine;
}

if (scriptSetupRanges.defineModel.length) {
yield `const __VLS_defaultModels = {${newLine}`;
for (const defineModel of scriptSetupRanges.defineModel) {
if (!defineModel.defaultValue) {
continue;
}
const [propName] = getPropAndLocalName(scriptSetup, defineModel);

yield `'${propName}': `;
yield getRangeText(scriptSetup, defineModel.defaultValue);
yield `,${newLine}`;
}
yield `}${endOfLine}`;
}

const propTypes: string[] = [];
if (options.vueCompilerOptions.jsxSlots && hasSlots) {
propTypes.push(`${ctx.localTypes.PropsChildren}<__VLS_Slots>`);
Expand All @@ -477,38 +462,6 @@ function* generateComponentProps(
propTypes.push(`__VLS_Props`);
}
if (scriptSetupRanges.defineModel.length) {
yield `type __VLS_ModelProps = {${newLine}`;
for (const defineModel of scriptSetupRanges.defineModel) {
const [propName, localName] = getPropAndLocalName(scriptSetup, defineModel);

if (defineModel.comments) {
yield scriptSetup.content.slice(defineModel.comments.start, defineModel.comments.end);
yield newLine;
}

if (defineModel.name) {
yield* generateCamelized(
getRangeText(scriptSetup, defineModel.name),
scriptSetup.name,
defineModel.name.start,
codeFeatures.navigation,
);
}
else {
yield propName;
}

yield defineModel.required ? `: ` : `?: `;
yield* generateDefineModelType(scriptSetup, propName, localName, defineModel);
yield `,${newLine}`;

if (defineModel.modifierType) {
const modifierName = `${defineModel.name ? propName : 'model'}Modifiers`;
const modifierType = getRangeText(scriptSetup, defineModel.modifierType);
yield `'${modifierName}'?: Partial<Record<${modifierType}, true>>,${newLine}`;
}
}
yield `}${endOfLine}`;
propTypes.push(`__VLS_ModelProps`);
}
if (propTypes.length) {
Expand All @@ -517,60 +470,115 @@ function* generateComponentProps(
}
}

function* generateModelEmit(
function* generateModels(
scriptSetup: NonNullable<Sfc['scriptSetup']>,
scriptSetupRanges: ScriptSetupRanges,
): Generator<Code> {
if (scriptSetupRanges.defineModel.length) {
yield `type __VLS_ModelEmit = {${newLine}`;
for (const defineModel of scriptSetupRanges.defineModel) {
const [propName, localName] = getPropAndLocalName(scriptSetup, defineModel);
yield `'update:${propName}': [value: `;
yield* generateDefineModelType(scriptSetup, propName, localName, defineModel);
if (!defineModel.required && !defineModel.defaultValue) {
yield ` | undefined`;
}
yield `]${endOfLine}`;
if (!scriptSetupRanges.defineModel.length) {
return;
}

const defaultCodes: string[] = [];
const propCodes: Generator<Code>[] = [];
const emitCodes: Generator<Code>[] = [];

for (const defineModel of scriptSetupRanges.defineModel) {
const propName = defineModel.name
? camelize(getRangeText(scriptSetup, defineModel.name).slice(1, -1))
: 'modelValue';

let modelType: string;
if (defineModel.type) {
// Infer from defineModel<T>
modelType = getRangeText(scriptSetup, defineModel.type);
}
else if (defineModel.runtimeType && defineModel.localName) {
// Infer from actual prop declaration code
modelType = `typeof ${getRangeText(scriptSetup, defineModel.localName)}['value']`;
}
else if (defineModel.defaultValue && propName) {
// Infer from defineModel({ default: T })
modelType = `typeof __VLS_defaultModels['${propName}']`;
}
else {
modelType = `any`;
}

if (defineModel.defaultValue) {
defaultCodes.push(
`'${propName}': ${getRangeText(scriptSetup, defineModel.defaultValue)},${newLine}`,
);
}

propCodes.push(generateModelProp(scriptSetup, defineModel, propName, modelType));
emitCodes.push(generateModelEmit(defineModel, propName, modelType));
}

if (defaultCodes.length) {
yield `const __VLS_defaultModels = {${newLine}`;
yield* defaultCodes;
yield `}${endOfLine}`;
yield `const __VLS_modelEmit = defineEmits<__VLS_ModelEmit>()${endOfLine}`;
}

yield `type __VLS_ModelProps = {${newLine}`;
for (const codes of propCodes) {
yield* codes;
}
yield `}${endOfLine}`;

yield `type __VLS_ModelEmit = {${newLine}`;
for (const codes of emitCodes) {
yield* codes;
}
yield `}${endOfLine}`;
yield `const __VLS_modelEmit = defineEmits<__VLS_ModelEmit>()${endOfLine}`;
}

function* generateDefineModelType(
function* generateModelProp(
scriptSetup: NonNullable<Sfc['scriptSetup']>,
propName: string | undefined,
localName: string | undefined,
defineModel: ScriptSetupRanges['defineModel'][number],
) {
if (defineModel.type) {
// Infer from defineModel<T>
yield getRangeText(scriptSetup, defineModel.type);
}
else if (defineModel.runtimeType && localName) {
// Infer from actual prop declaration code
yield `typeof ${localName}['value']`;
propName: string,
modelType: string,
): Generator<Code> {
if (defineModel.comments) {
yield scriptSetup.content.slice(defineModel.comments.start, defineModel.comments.end);
yield newLine;
}
else if (defineModel.defaultValue && propName) {
// Infer from defineModel({default: T})
yield `typeof __VLS_defaultModels['${propName}']`;

if (defineModel.name) {
yield* generateCamelized(
getRangeText(scriptSetup, defineModel.name),
scriptSetup.name,
defineModel.name.start,
codeFeatures.navigation,
);
}
else {
yield `any`;
yield propName;
}

yield defineModel.required ? `: ` : `?: `;
yield modelType;
yield endOfLine;

if (defineModel.modifierType) {
const modifierName = `${defineModel.name ? propName : `model`}Modifiers`;
const modifierType = getRangeText(scriptSetup, defineModel.modifierType);
yield `'${modifierName}'?: Partial<Record<${modifierType}, true>>${endOfLine}`;
}
}

function getPropAndLocalName(
scriptSetup: NonNullable<Sfc['scriptSetup']>,
function* generateModelEmit(
defineModel: ScriptSetupRanges['defineModel'][number],
) {
const localName = defineModel.localName
? getRangeText(scriptSetup, defineModel.localName)
: undefined;
const propName = defineModel.name
? camelize(getRangeText(scriptSetup, defineModel.name).slice(1, -1))
: 'modelValue';
return [propName, localName] as const;
propName: string,
modelType: string,
): Generator<Code> {
yield `'update:${propName}': [value: `;
yield modelType;
if (!defineModel.required && !defineModel.defaultValue) {
yield ` | undefined`;
}
yield `]${endOfLine}`;
}

function getRangeText(
Expand Down