From 1393ee52ca20b956ae3ef4775192ad645dbdcaf8 Mon Sep 17 00:00:00 2001 From: Evan You Date: Tue, 8 Oct 2019 09:26:09 -0400 Subject: [PATCH] types: improve typing --- .../runtime-core/src/apiCreateComponent.ts | 4 ++-- packages/runtime-core/src/apiOptions.ts | 8 ++++---- packages/runtime-core/src/componentProps.ts | 6 +++++- packages/runtime-core/src/createRenderer.ts | 5 +++-- packages/runtime-core/src/h.ts | 4 ++-- packages/runtime-core/src/index.ts | 9 +++++++-- packages/runtime-core/src/vnode.ts | 10 +++++++--- packages/runtime-core/src/warning.ts | 20 +++++++++++-------- 8 files changed, 42 insertions(+), 24 deletions(-) diff --git a/packages/runtime-core/src/apiCreateComponent.ts b/packages/runtime-core/src/apiCreateComponent.ts index 5752da8f0..4f70224db 100644 --- a/packages/runtime-core/src/apiCreateComponent.ts +++ b/packages/runtime-core/src/apiCreateComponent.ts @@ -3,7 +3,7 @@ import { MethodOptions, ComponentOptionsWithoutProps, ComponentOptionsWithArrayProps, - ComponentOptionsWithProps + ComponentOptionsWithObjectProps } from './apiOptions' import { SetupContext } from './component' import { VNodeChild } from './vnode' @@ -62,7 +62,7 @@ export function createComponent< C extends ComputedOptions = {}, M extends MethodOptions = {} >( - options: ComponentOptionsWithProps + options: ComponentOptionsWithObjectProps ): { // for Vetur and TSX support new (): ComponentPublicInstance< diff --git a/packages/runtime-core/src/apiOptions.ts b/packages/runtime-core/src/apiOptions.ts index 87902f7f8..30b6521d4 100644 --- a/packages/runtime-core/src/apiOptions.ts +++ b/packages/runtime-core/src/apiOptions.ts @@ -27,7 +27,7 @@ import { onRenderTriggered } from './apiLifecycle' import { DebuggerEvent, reactive } from '@vue/reactivity' -import { ComponentPropsOptions, ExtractPropTypes } from './componentProps' +import { ComponentObjectPropsOptions, ExtractPropTypes } from './componentProps' import { Directive } from './directives' import { VNodeChild } from './vnode' import { ComponentPublicInstance } from './componentProxy' @@ -78,8 +78,8 @@ export type ComponentOptionsWithArrayProps< props: PropNames[] } & ThisType> -export type ComponentOptionsWithProps< - PropsOptions = ComponentPropsOptions, +export type ComponentOptionsWithObjectProps< + PropsOptions = ComponentObjectPropsOptions, RawBindings = {}, D = {}, C extends ComputedOptions = {}, @@ -91,7 +91,7 @@ export type ComponentOptionsWithProps< export type ComponentOptions = | ComponentOptionsWithoutProps - | ComponentOptionsWithProps + | ComponentOptionsWithObjectProps | ComponentOptionsWithArrayProps // TODO legacy component definition also supports constructors with .options diff --git a/packages/runtime-core/src/componentProps.ts b/packages/runtime-core/src/componentProps.ts index 511e66dd5..25e00ee2f 100644 --- a/packages/runtime-core/src/componentProps.ts +++ b/packages/runtime-core/src/componentProps.ts @@ -16,7 +16,11 @@ import { import { warn } from './warning' import { Data, ComponentInternalInstance } from './component' -export type ComponentPropsOptions

= { +export type ComponentPropsOptions

= + | ComponentObjectPropsOptions

+ | string[] + +export type ComponentObjectPropsOptions

= { [K in keyof P]: Prop | null } diff --git a/packages/runtime-core/src/createRenderer.ts b/packages/runtime-core/src/createRenderer.ts index 00280955c..2d230ec71 100644 --- a/packages/runtime-core/src/createRenderer.ts +++ b/packages/runtime-core/src/createRenderer.ts @@ -13,7 +13,8 @@ import { ComponentInternalInstance, createComponentInstance, setupStatefulComponent, - handleSetupResult + handleSetupResult, + Component } from './component' import { renderComponentRoot, @@ -1006,7 +1007,7 @@ export function createRenderer< } // resolve props and slots for setup context - const propsOptions = (initialVNode.type as any).props + const propsOptions = (initialVNode.type as Component).props resolveProps(instance, initialVNode.props, propsOptions) resolveSlots(instance, initialVNode.children) diff --git a/packages/runtime-core/src/h.ts b/packages/runtime-core/src/h.ts index 6c9c8c9bd..3a29607a5 100644 --- a/packages/runtime-core/src/h.ts +++ b/packages/runtime-core/src/h.ts @@ -13,7 +13,7 @@ import { FunctionalComponent } from './component' import { ComponentOptionsWithoutProps, ComponentOptionsWithArrayProps, - ComponentOptionsWithProps, + ComponentOptionsWithObjectProps, ComponentOptions } from './apiOptions' import { ExtractPropTypes } from './componentProps' @@ -121,7 +121,7 @@ export function h

( children?: RawChildren | RawSlots ): VNode export function h

( - type: ComponentOptionsWithProps

, + type: ComponentOptionsWithObjectProps

, props?: (RawProps & ExtractPropTypes

) | null, children?: RawChildren | RawSlots ): VNode diff --git a/packages/runtime-core/src/index.ts b/packages/runtime-core/src/index.ts index 25204c10e..7ce44b9a7 100644 --- a/packages/runtime-core/src/index.ts +++ b/packages/runtime-core/src/index.ts @@ -63,14 +63,19 @@ export { export { ComponentOptions, ComponentOptionsWithoutProps, - ComponentOptionsWithProps, + ComponentOptionsWithObjectProps as ComponentOptionsWithProps, ComponentOptionsWithArrayProps } from './apiOptions' export { ComponentPublicInstance } from './componentProxy' export { RendererOptions } from './createRenderer' export { Slot, Slots } from './componentSlots' -export { Prop, PropType, ComponentPropsOptions } from './componentProps' +export { + Prop, + PropType, + ComponentPropsOptions, + ComponentObjectPropsOptions +} from './componentProps' export { Directive, DirectiveBinding, diff --git a/packages/runtime-core/src/vnode.ts b/packages/runtime-core/src/vnode.ts index 3a74985c7..2229fbcdc 100644 --- a/packages/runtime-core/src/vnode.ts +++ b/packages/runtime-core/src/vnode.ts @@ -7,7 +7,12 @@ import { extend, PatchFlags } from '@vue/shared' -import { ComponentInternalInstance, Data, SetupProxySymbol } from './component' +import { + ComponentInternalInstance, + Data, + SetupProxySymbol, + Component +} from './component' import { RawSlots } from './componentSlots' import { ShapeFlags } from './shapeFlags' import { isReactive } from '@vue/reactivity' @@ -22,8 +27,7 @@ export const Suspense = __DEV__ ? Symbol('Suspense') : Symbol() export type VNodeTypes = | string - | Function - | Object + | Component | typeof Fragment | typeof Portal | typeof Text diff --git a/packages/runtime-core/src/warning.ts b/packages/runtime-core/src/warning.ts index e1d6f9e9a..09cf34e58 100644 --- a/packages/runtime-core/src/warning.ts +++ b/packages/runtime-core/src/warning.ts @@ -1,18 +1,22 @@ import { VNode } from './vnode' -import { Data, ComponentInternalInstance } from './component' -import { isString } from '@vue/shared' +import { Data, ComponentInternalInstance, Component } from './component' +import { isString, isFunction } from '@vue/shared' import { toRaw } from '@vue/reactivity' +type ComponentVNode = VNode & { + type: Component +} + let stack: VNode[] = [] type TraceEntry = { - vnode: VNode + vnode: ComponentVNode recurseCount: number } type ComponentTraceStack = TraceEntry[] -export function pushWarningContext(vnode: VNode) { +export function pushWarningContext(vnode: ComponentVNode) { stack.push(vnode) } @@ -117,9 +121,9 @@ const classifyRE = /(?:^|[-_])(\w)/g const classify = (str: string): string => str.replace(classifyRE, c => c.toUpperCase()).replace(/[-_]/g, '') -function formatComponentName(vnode: VNode, file?: string): string { - const Component = vnode.type as any - let name = Component.displayName || Component.name +function formatComponentName(vnode: ComponentVNode, file?: string): string { + const Component = vnode.type + let name = isFunction(Component) ? Component.displayName : Component.name if (!name && file) { const match = file.match(/([^/\\]+)\.vue$/) if (match) { @@ -136,7 +140,7 @@ function formatProps(props: Data): string[] { if (isString(value)) { res.push(`${key}=${JSON.stringify(value)}`) } else { - res.push(`${key}=`, toRaw(value) as any) + res.push(`${key}=`, String(toRaw(value))) } } return res