From 285cdd7a9ff8bf9f882953e218708442bd1ff2ae Mon Sep 17 00:00:00 2001 From: Danil Nemov Date: Sun, 30 Mar 2025 22:14:41 +0300 Subject: [PATCH] fix: make generics with runtime props in defineComponent work --- .../dts-test/defineComponent.test-d.tsx | 99 ++++++++++++++++--- .../runtime-core/src/apiDefineComponent.ts | 2 +- 2 files changed, 89 insertions(+), 12 deletions(-) diff --git a/packages-private/dts-test/defineComponent.test-d.tsx b/packages-private/dts-test/defineComponent.test-d.tsx index fda3ca4856c..35f6e90026d 100644 --- a/packages-private/dts-test/defineComponent.test-d.tsx +++ b/packages-private/dts-test/defineComponent.test-d.tsx @@ -1373,7 +1373,7 @@ describe('function syntax w/ emits', () => { describe('function syntax w/ runtime props', () => { // with runtime props, the runtime props must match // manual type declaration - defineComponent( + const Comp1 = defineComponent( (_props: { msg: string }) => { return () => {} }, @@ -1382,7 +1382,34 @@ describe('function syntax w/ runtime props', () => { }, ) + // @ts-expect-error bar isn't specified in props definition defineComponent( + (_props: { msg: string }) => { + return () => {} + }, + { + props: ['msg', 'bar'], + }, + ) + + defineComponent( + (_props: { msg: string; bar: string }) => { + return () => {} + }, + { + props: ['msg'], + }, + ) + + expectType() + // @ts-expect-error msg type is incorrect + expectType() + // @ts-expect-error msg is missing + expectType() + // @ts-expect-error bar doesn't exist + expectType() + + const Comp2 = defineComponent( (_props: { msg: T }) => { return () => {} }, @@ -1391,7 +1418,36 @@ describe('function syntax w/ runtime props', () => { }, ) + // @ts-expect-error bar isn't specified in props definition defineComponent( + (_props: { msg: T }) => { + return () => {} + }, + { + props: ['msg', 'bar'], + }, + ) + + defineComponent( + (_props: { msg: T; bar: T }) => { + return () => {} + }, + { + props: ['msg'], + }, + ) + + expectType() + expectType( msg="1" />) + // @ts-expect-error msg type is incorrect + expectType() + // @ts-expect-error msg is missing + expectType() + // @ts-expect-error bar doesn't exist + expectType() + + // Note: generics aren't supported with object runtime props + const Comp3 = defineComponent( (_props: { msg: T }) => { return () => {} }, @@ -1402,37 +1458,58 @@ describe('function syntax w/ runtime props', () => { }, ) - // @ts-expect-error string prop names don't match defineComponent( - (_props: { msg: string }) => { + // @ts-expect-error bar isn't specified in props definition + (_props: { msg: T }) => { return () => {} }, { - props: ['bar'], + props: { + bar: String, + }, }, ) defineComponent( - (_props: { msg: string }) => { + // @ts-expect-error generics aren't supported with object runtime props + (_props: { msg: T; bar: T }) => { return () => {} }, { props: { - // @ts-expect-error prop type mismatch - msg: Number, + msg: String, }, }, ) - // @ts-expect-error prop keys don't match + expectType() + // @ts-expect-error generics aren't supported with object runtime props + expectType( msg="1" />) + // @ts-expect-error msg type is incorrect + expectType() + // @ts-expect-error msg is missing + expectType() + // @ts-expect-error bar doesn't exist + expectType() + + // @ts-expect-error string prop names don't match defineComponent( - (_props: { msg: string }, ctx) => { + (_props: { msg: string }) => { + return () => {} + }, + { + props: ['bar'], + }, + ) + + defineComponent( + (_props: { msg: string }) => { return () => {} }, { props: { - msg: String, - bar: String, + // @ts-expect-error prop type mismatch + msg: Number, }, }, ) diff --git a/packages/runtime-core/src/apiDefineComponent.ts b/packages/runtime-core/src/apiDefineComponent.ts index 2ce870f0141..255d383ff47 100644 --- a/packages/runtime-core/src/apiDefineComponent.ts +++ b/packages/runtime-core/src/apiDefineComponent.ts @@ -157,7 +157,7 @@ export function defineComponent< ctx: SetupContext, ) => RenderFunction | Promise, options?: Pick & { - props?: (keyof Props)[] + props?: (keyof NoInfer)[] emits?: E | EE[] slots?: S },