From 1408f225d9c9bf296b5e2a69f0e25f7f8097abfb Mon Sep 17 00:00:00 2001 From: Johnson Chu Date: Tue, 4 Feb 2025 22:20:05 +0800 Subject: [PATCH 001/127] wip [skip ci] --- .../dts-test/defineComponent.test-d.tsx | 57 +- .../runtime-core/__tests__/apiOptions.spec.ts | 2 +- .../runtime-core/src/apiDefineComponent.ts | 299 ++++++----- packages/runtime-core/src/apiSetupHelpers.ts | 36 +- packages/runtime-core/src/componentOptions.ts | 508 ++++-------------- .../src/componentPublicInstance.ts | 215 +++----- packages/runtime-core/src/h.ts | 16 +- packages/runtime-core/src/index.ts | 7 +- .../__tests__/customElement.spec.ts | 3 +- packages/runtime-dom/src/apiCustomElement.ts | 76 ++- packages/shared/src/typeUtils.ts | 6 - 11 files changed, 420 insertions(+), 805 deletions(-) diff --git a/packages-private/dts-test/defineComponent.test-d.tsx b/packages-private/dts-test/defineComponent.test-d.tsx index fda3ca4856c..75bbcd09d92 100644 --- a/packages-private/dts-test/defineComponent.test-d.tsx +++ b/packages-private/dts-test/defineComponent.test-d.tsx @@ -1663,7 +1663,6 @@ declare const MyButton: DefineComponent< ComponentOptionsMixin, ComponentOptionsMixin, EmitsOptions, - string, VNodeProps & AllowedComponentProps & ComponentCustomProps, Readonly>, {}, @@ -1852,7 +1851,7 @@ interface ErrorMessageSlotProps { * relying on legacy CreateComponentPublicInstance signature */ declare const ErrorMessage: { - new (...args: any[]): vue.CreateComponentPublicInstance< + new (...args: any[]): vue.CreateComponentPublicInstanceWithMixins< Readonly< vue.ExtractPropTypes<{ as: { @@ -1916,58 +1915,7 @@ declare const ErrorMessage: { }, true, {}, - {}, - { - P: {} - B: {} - D: {} - C: {} - M: {} - Defaults: {} - }, - Readonly< - vue.ExtractPropTypes<{ - as: { - type: StringConstructor - default: any - } - name: { - type: StringConstructor - required: true - } - }> - >, - () => - | VNode< - vue.RendererNode, - vue.RendererElement, - { - [key: string]: any - } - > - | vue.Slot - | VNode< - vue.RendererNode, - vue.RendererElement, - { - [key: string]: any - } - >[] - | { - default: () => VNode< - vue.RendererNode, - vue.RendererElement, - { - [key: string]: any - } - >[] - }, - {}, - {}, - {}, - { - as: string - } + {} > __isFragment?: never __isTeleport?: never @@ -2020,7 +1968,6 @@ declare const ErrorMessage: { { as: string }, - {}, string, {} > & diff --git a/packages/runtime-core/__tests__/apiOptions.spec.ts b/packages/runtime-core/__tests__/apiOptions.spec.ts index 1d4e805efce..ce00acf9e2b 100644 --- a/packages/runtime-core/__tests__/apiOptions.spec.ts +++ b/packages/runtime-core/__tests__/apiOptions.spec.ts @@ -1060,7 +1060,7 @@ describe('api: options', () => { }, data() { return { - plusOne: (this as any).count + 1, + plusOne: this.count + 1, } }, computed: { diff --git a/packages/runtime-core/src/apiDefineComponent.ts b/packages/runtime-core/src/apiDefineComponent.ts index 2ce870f0141..d5ee0a7d572 100644 --- a/packages/runtime-core/src/apiDefineComponent.ts +++ b/packages/runtime-core/src/apiDefineComponent.ts @@ -1,47 +1,53 @@ +import { extend, isFunction, LooseRequired } from '@vue/shared' +import type { ComponentTypeEmits } from './apiSetupHelpers' +import type { + AllowedComponentProps, + Component, + ComponentCustomProps, + GlobalComponents, + GlobalDirectives, + SetupContext, +} from './component' +import type { + EmitsOptions, + EmitsToProps, + ObjectEmitsOptions, + TypeEmitsToOptions, +} from './componentEmits' import type { ComponentInjectOptions, ComponentOptions, ComponentOptionsBase, - ComponentOptionsMixin, ComponentProvideOptions, ComputedOptions, MethodOptions, RenderFunction, } from './componentOptions' -import type { - AllowedComponentProps, - Component, - ComponentCustomProps, - GlobalComponents, - GlobalDirectives, - SetupContext, -} from './component' import type { ComponentObjectPropsOptions, ComponentPropsOptions, ExtractDefaultPropTypes, ExtractPropTypes, } from './componentProps' -import type { - EmitsOptions, - EmitsToProps, - TypeEmitsToOptions, -} from './componentEmits' -import { type IsKeyValues, extend, isFunction } from '@vue/shared' -import type { VNodeProps } from './vnode' import type { ComponentPublicInstanceConstructor, CreateComponentPublicInstanceWithMixins, + EnsureNonVoid, + ExtractMixinComputed, + ExtractMixinData, + ExtractMixinMethods, + ExtractMixinProps, + ExtractMixinSetupBindings, } from './componentPublicInstance' import type { SlotsType } from './componentSlots' import type { Directive } from './directives' -import type { ComponentTypeEmits } from './apiSetupHelpers' +import type { VNodeProps } from './vnode' export type PublicProps = VNodeProps & AllowedComponentProps & ComponentCustomProps -type ResolveProps = Readonly< +type ResolveProps = Readonly< PropsOrPropOptions extends ComponentPropsOptions ? ExtractPropTypes : PropsOrPropOptions @@ -54,10 +60,9 @@ export type DefineComponent< D = {}, C extends ComputedOptions = ComputedOptions, M extends MethodOptions = MethodOptions, - Mixin extends ComponentOptionsMixin = ComponentOptionsMixin, - Extends extends ComponentOptionsMixin = ComponentOptionsMixin, - E extends EmitsOptions = {}, - EE extends string = string, + Mixin = {}, + Extends = {}, + E extends ObjectEmitsOptions = {}, PP = PublicProps, Props = ResolveProps, Defaults = ExtractDefaultPropTypes, @@ -90,31 +95,25 @@ export type DefineComponent< TypeRefs, TypeEl > -> & - ComponentOptionsBase< - Props, - RawBindings, - D, - C, - M, - Mixin, - Extends, - E, - EE, - Defaults, - {}, - string, - S, - LC & GlobalComponents, - Directives & GlobalDirectives, - Exposed, - Provide - > & +> & { + computed?: C + methods?: M + mixins?: Mixin[] + extends?: Extends + inject?: {} + slots?: S + components?: LC & GlobalComponents + directives?: Directives & GlobalDirectives + expose?: Exposed[] + provide?: Provide + setup?: () => RawBindings + data?: () => D +} & ComponentOptionsBase & PP export type DefineSetupFnComponent< P extends Record, - E extends EmitsOptions = {}, + E extends ObjectEmitsOptions = {}, S extends SlotsType = SlotsType, Props = P & EmitsToProps, PP = PublicProps, @@ -126,8 +125,8 @@ export type DefineSetupFnComponent< {}, {}, {}, - ComponentOptionsMixin, - ComponentOptionsMixin, + {}, + {}, E, PP, {}, @@ -148,7 +147,7 @@ type ToResolvedProps = Readonly & // (uses user defined props interface) export function defineComponent< Props extends Record, - E extends EmitsOptions = {}, + E extends ObjectEmitsOptions = {}, EE extends string = string, S extends SlotsType = {}, >( @@ -164,7 +163,7 @@ export function defineComponent< ): DefineSetupFnComponent export function defineComponent< Props extends Record, - E extends EmitsOptions = {}, + E extends ObjectEmitsOptions = {}, EE extends string = string, S extends SlotsType = {}, >( @@ -181,22 +180,25 @@ export function defineComponent< // overload 2: defineComponent with options object, infer props from options export function defineComponent< - // props + // type options TypeProps, + TypeEmits extends ComponentTypeEmits | unknown = unknown, + TypeRefs extends Record = {}, + TypeEl extends Element = any, + // props RuntimePropsOptions extends ComponentObjectPropsOptions = ComponentObjectPropsOptions, RuntimePropsKeys extends string = string, // emits - TypeEmits extends ComponentTypeEmits = {}, - RuntimeEmitsOptions extends EmitsOptions = {}, + RuntimeEmitsOptions extends ObjectEmitsOptions = {}, RuntimeEmitsKeys extends string = string, // other options Data = {}, SetupBindings = {}, Computed extends ComputedOptions = {}, Methods extends MethodOptions = {}, - Mixin extends ComponentOptionsMixin = ComponentOptionsMixin, - Extends extends ComponentOptionsMixin = ComponentOptionsMixin, + Mixin = {}, + Extends = {}, InjectOptions extends ComponentInjectOptions = {}, InjectKeys extends string = string, Slots extends SlotsType = {}, @@ -205,21 +207,110 @@ export function defineComponent< Exposed extends string = string, Provide extends ComponentProvideOptions = ComponentProvideOptions, // resolved types - ResolvedEmits extends EmitsOptions = {} extends RuntimeEmitsOptions - ? TypeEmitsToOptions - : RuntimeEmitsOptions, - InferredProps = IsKeyValues extends true - ? TypeProps - : string extends RuntimePropsKeys + NormalizedEmitsOptions extends EmitsOptions = unknown extends TypeEmits + ? string extends RuntimeEmitsKeys + ? RuntimeEmitsOptions + : RuntimeEmitsKeys[] + : TypeEmitsToOptions< + TypeEmits extends ComponentTypeEmits ? TypeEmits : never + >, + InferredProps = unknown extends TypeProps + ? string extends RuntimePropsKeys ? ComponentObjectPropsOptions extends RuntimePropsOptions ? {} : ExtractPropTypes - : { [key in RuntimePropsKeys]?: any }, - TypeRefs extends Record = {}, - TypeEl extends Element = any, + : { [key in RuntimePropsKeys]?: any } + : TypeProps, + ResolvedProps = ToResolvedProps, + // mixin inference + PublicP = ExtractMixinProps & + ExtractMixinProps & + EnsureNonVoid, + PublicB = ExtractMixinSetupBindings & + ExtractMixinSetupBindings & + EnsureNonVoid, + PublicD = ExtractMixinData & + ExtractMixinData & + EnsureNonVoid, + PublicC extends ComputedOptions = ExtractMixinComputed & + ExtractMixinComputed & + EnsureNonVoid, + PublicM extends MethodOptions = ExtractMixinMethods & + ExtractMixinMethods & + EnsureNonVoid, + PublicDefaults = {}, // TODO + // vm + DataVM = CreateComponentPublicInstanceWithMixins< + ResolvedProps, + SetupBindings, + {}, // Data + {}, // Computed + MethodOptions, + Mixin, + Extends, + NormalizedEmitsOptions + >, + OptionsVM = CreateComponentPublicInstanceWithMixins< + ResolvedProps, + SetupBindings, + Data, + Computed, + Methods, + Mixin, + Extends, + NormalizedEmitsOptions, + {}, // PublicProps + {}, // Defaults + false, + InjectOptions, + Slots, + LocalComponents, + Directives, + Exposed + >, + ReturnVM = CreateComponentPublicInstanceWithMixins< + ResolvedProps, + SetupBindings, + Data, + Computed, + Methods, + Mixin, + Extends, + NormalizedEmitsOptions, + PublicProps, + ExtractDefaultPropTypes, + // MakeDefaultsOptional - if TypeProps is provided, set to false to use + // user props types verbatim + unknown extends TypeProps ? true : false, + {}, // InjectOptions + Slots, + LocalComponents & GlobalComponents, + Directives & GlobalDirectives, + Exposed, + TypeRefs, + TypeEl, + Provide + >, >( options: { props?: (RuntimePropsOptions & ThisType) | RuntimePropsKeys[] + emits?: (RuntimeEmitsOptions & ThisType) | RuntimeEmitsKeys[] + components?: LocalComponents + directives?: Directives + slots?: Slots + expose?: Exposed[] + computed?: Computed + methods?: Methods + provide?: Provide + inject?: InjectOptions | InjectKeys[] + mixins?: Mixin[] + extends?: Extends + setup?: ( + this: void, + props: LooseRequired, + ctx: SetupContext, + ) => Promise | SetupBindings | RenderFunction | void + data?: (this: DataVM, vm: DataVM) => Data /** * @private for language-tools use only */ @@ -236,69 +327,29 @@ export function defineComponent< * @private for language-tools use only */ __typeEl?: TypeEl - } & ComponentOptionsBase< - ToResolvedProps, - SetupBindings, - Data, - Computed, - Methods, - Mixin, - Extends, - RuntimeEmitsOptions, - RuntimeEmitsKeys, - {}, // Defaults - InjectOptions, - InjectKeys, - Slots, - LocalComponents, - Directives, - Exposed, - Provide - > & - ThisType< - CreateComponentPublicInstanceWithMixins< - ToResolvedProps, - SetupBindings, - Data, - Computed, - Methods, - Mixin, - Extends, - ResolvedEmits, - {}, - {}, - false, - InjectOptions, - Slots, - LocalComponents, - Directives, - Exposed - > - >, -): DefineComponent< - InferredProps, - SetupBindings, - Data, - Computed, - Methods, - Mixin, - Extends, - ResolvedEmits, - RuntimeEmitsKeys, - PublicProps, - ToResolvedProps, - ExtractDefaultPropTypes, - Slots, - LocalComponents, - Directives, - Exposed, - Provide, - // MakeDefaultsOptional - if TypeProps is provided, set to false to use - // user props types verbatim - unknown extends TypeProps ? true : false, - TypeRefs, - TypeEl -> + } & ComponentOptionsBase & + ThisType, +): { + props?: string extends RuntimePropsKeys + ? ComponentObjectPropsOptions extends RuntimePropsOptions + ? {} + : RuntimePropsOptions + : RuntimePropsKeys[] + emits?: NormalizedEmitsOptions + components?: LocalComponents & GlobalComponents + directives?: Directives & GlobalDirectives + slots?: Slots + expose?: Exposed[] + computed?: Computed + methods?: Methods + provide?: Provide + inject?: string extends InjectKeys ? InjectOptions : InjectKeys[] + mixins?: Mixin[] + extends?: Extends + setup?(): SetupBindings + data?(): Data +} & ComponentOptionsBase & + ComponentPublicInstanceConstructor // implementation, close to no-op /*! #__NO_SIDE_EFFECTS__ */ diff --git a/packages/runtime-core/src/apiSetupHelpers.ts b/packages/runtime-core/src/apiSetupHelpers.ts index 2ddaeb509ad..0f3ca2839fa 100644 --- a/packages/runtime-core/src/apiSetupHelpers.ts +++ b/packages/runtime-core/src/apiSetupHelpers.ts @@ -18,7 +18,6 @@ import { import type { EmitFn, EmitsOptions, ObjectEmitsOptions } from './componentEmits' import type { ComponentOptionsBase, - ComponentOptionsMixin, ComputedOptions, MethodOptions, } from './componentOptions' @@ -31,6 +30,7 @@ import type { import { warn } from './warning' import type { SlotsType, StrictUnwrapSlotsType } from './componentSlots' import type { Ref } from '@vue/reactivity' +import { CreateComponentPublicInstanceWithMixins } from './componentPublicInstance' // dev only const warnRuntimeUsage = (method: string) => @@ -189,23 +189,31 @@ export function defineExpose< * @see {@link https://vuejs.org/api/sfc-script-setup.html#defineoptions} */ export function defineOptions< - RawBindings = {}, D = {}, C extends ComputedOptions = {}, M extends MethodOptions = {}, - Mixin extends ComponentOptionsMixin = ComponentOptionsMixin, - Extends extends ComponentOptionsMixin = ComponentOptionsMixin, ->( - options?: ComponentOptionsBase< + Mixin = {}, + Extends = {}, + DataVM = CreateComponentPublicInstanceWithMixins< + {}, + {}, + {}, {}, - RawBindings, - D, - C, - M, + MethodOptions, Mixin, - Extends, - {} - > & { + Extends + >, +>( + options?: { + computed?: C + methods?: M + mixins?: Mixin[] + extends?: Extends + data?: (this: DataVM, vm: DataVM) => D + /** + * setup should be defined via `