vue 2.7.3 → 2.7.6

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (39) hide show
  1. package/dist/vue.common.dev.js +3371 -3281
  2. package/dist/vue.common.prod.js +3 -3
  3. package/dist/vue.esm.browser.js +3581 -3492
  4. package/dist/vue.esm.browser.min.js +3 -3
  5. package/dist/vue.esm.js +3722 -3631
  6. package/dist/vue.js +3611 -3519
  7. package/dist/vue.min.js +3 -3
  8. package/dist/vue.runtime.common.dev.js +2768 -2678
  9. package/dist/vue.runtime.common.prod.js +3 -3
  10. package/dist/vue.runtime.esm.js +3066 -2975
  11. package/dist/vue.runtime.js +2761 -2669
  12. package/dist/vue.runtime.min.js +3 -3
  13. package/dist/vue.runtime.mjs +73 -8602
  14. package/package.json +2 -2
  15. package/packages/compiler-sfc/dist/compiler-sfc.js +1036 -1029
  16. package/packages/compiler-sfc/package.json +1 -1
  17. package/packages/compiler-sfc/src/parseComponent.ts +7 -4
  18. package/packages/compiler-sfc/test/parseComponent.spec.ts +6 -7
  19. package/src/core/components/keep-alive.ts +5 -4
  20. package/src/core/global-api/extend.ts +3 -1
  21. package/src/core/instance/init.ts +1 -1
  22. package/src/core/instance/lifecycle.ts +8 -3
  23. package/src/core/instance/render-helpers/render-static.ts +1 -1
  24. package/src/core/observer/index.ts +1 -1
  25. package/src/core/observer/traverse.ts +3 -0
  26. package/src/core/util/debug.ts +2 -1
  27. package/src/core/vdom/create-component.ts +5 -1
  28. package/src/platforms/web/runtime/components/transition-group.ts +2 -1
  29. package/src/v3/apiAsyncComponent.ts +117 -0
  30. package/src/v3/apiWatch.ts +6 -8
  31. package/src/v3/index.ts +6 -0
  32. package/src/v3/reactivity/ref.ts +11 -2
  33. package/types/options.d.ts +5 -3
  34. package/types/v3-component-public-instance.d.ts +36 -32
  35. package/types/v3-define-async-component.d.ts +26 -0
  36. package/types/v3-define-component.d.ts +25 -1
  37. package/types/v3-generated.d.ts +23 -0
  38. package/types/v3-setup-context.d.ts +1 -0
  39. package/types/vue.d.ts +36 -13
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@vue/compiler-sfc",
3
- "version": "2.7.3",
3
+ "version": "2.7.6",
4
4
  "description": "compiler-sfc for Vue 2",
5
5
  "main": "dist/compiler-sfc.js",
6
6
  "types": "dist/compiler-sfc.d.ts",
@@ -10,7 +10,6 @@ export const DEFAULT_FILENAME = 'anonymous.vue'
10
10
  const splitRE = /\r?\n/g
11
11
  const replaceRE = /./g
12
12
  const isSpecialTag = makeMap('script,style,template', true)
13
- const isNeedIndentLang = makeMap('pug,jade')
14
13
 
15
14
  export interface SFCCustomBlock {
16
15
  type: string
@@ -179,9 +178,13 @@ export function parseComponent(
179
178
  currentBlock.end = start
180
179
  let text = source.slice(currentBlock.start, currentBlock.end)
181
180
  if (
182
- options.deindent ||
183
- // certain langs like pug are indent sensitive, preserve old behavior
184
- (currentBlock.lang && isNeedIndentLang(currentBlock.lang))
181
+ options.deindent === true ||
182
+ // by default, deindent unless it's script with default lang or ts
183
+ (options.deindent !== false &&
184
+ !(
185
+ currentBlock.type === 'script' &&
186
+ (!currentBlock.lang || currentBlock.lang === 'ts')
187
+ ))
185
188
  ) {
186
189
  text = deindent(text)
187
190
  }
@@ -25,8 +25,7 @@ describe('Single File Component parser', () => {
25
25
  <div>
26
26
  <style>nested should be ignored</style>
27
27
  </div>
28
- `,
29
- { deindent: true }
28
+ `
30
29
  )
31
30
  expect(res.template!.content.trim()).toBe('<div>hi</div>')
32
31
  expect(res.styles.length).toBe(4)
@@ -76,8 +75,7 @@ describe('Single File Component parser', () => {
76
75
  </style>
77
76
  `
78
77
  const deindentDefault = parseComponent(content.trim(), {
79
- pad: false,
80
- deindent: true
78
+ pad: false
81
79
  })
82
80
  const deindentEnabled = parseComponent(content.trim(), {
83
81
  pad: false,
@@ -89,7 +87,9 @@ describe('Single File Component parser', () => {
89
87
  })
90
88
 
91
89
  expect(deindentDefault.template!.content).toBe('\n<div></div>\n')
92
- expect(deindentDefault.script!.content).toBe('\nexport default {}\n')
90
+ expect(deindentDefault.script!.content).toBe(
91
+ '\n export default {}\n '
92
+ )
93
93
  expect(deindentDefault.styles[0].content).toBe('\nh1 { color: red }\n')
94
94
  expect(deindentEnabled.template!.content).toBe('\n<div></div>\n')
95
95
  expect(deindentEnabled.script!.content).toBe('\nexport default {}\n')
@@ -203,8 +203,7 @@ describe('Single File Component parser', () => {
203
203
  }
204
204
  </test>
205
205
  <custom src="./x.json"></custom>
206
- `,
207
- { deindent: true }
206
+ `
208
207
  )
209
208
  expect(res.customBlocks.length).toBe(4)
210
209
 
@@ -3,6 +3,7 @@ import { getFirstComponentChild } from 'core/vdom/helpers/index'
3
3
  import type VNode from 'core/vdom/vnode'
4
4
  import type { VNodeComponentOptions } from 'types/vnode'
5
5
  import type { Component } from 'types/component'
6
+ import { getComponentName } from '../vdom/create-component'
6
7
 
7
8
  type CacheEntry = {
8
9
  name?: string
@@ -12,8 +13,8 @@ type CacheEntry = {
12
13
 
13
14
  type CacheEntryMap = Record<string, CacheEntry | null>
14
15
 
15
- function getComponentName(opts?: VNodeComponentOptions): string | null {
16
- return opts && (opts.Ctor.options.name || opts.tag)
16
+ function _getComponentName(opts?: VNodeComponentOptions): string | null {
17
+ return opts && (getComponentName(opts.Ctor.options as any) || opts.tag)
17
18
  }
18
19
 
19
20
  function matches(
@@ -81,7 +82,7 @@ export default {
81
82
  if (vnodeToCache) {
82
83
  const { tag, componentInstance, componentOptions } = vnodeToCache
83
84
  cache[keyToCache] = {
84
- name: getComponentName(componentOptions),
85
+ name: _getComponentName(componentOptions),
85
86
  tag,
86
87
  componentInstance
87
88
  }
@@ -126,7 +127,7 @@ export default {
126
127
  const componentOptions = vnode && vnode.componentOptions
127
128
  if (componentOptions) {
128
129
  // check pattern
129
- const name = getComponentName(componentOptions)
130
+ const name = _getComponentName(componentOptions)
130
131
  const { include, exclude } = this
131
132
  if (
132
133
  // not included
@@ -3,6 +3,7 @@ import type { Component } from 'types/component'
3
3
  import type { GlobalAPI } from 'types/global-api'
4
4
  import { defineComputed, proxy } from '../instance/state'
5
5
  import { extend, mergeOptions, validateComponentName } from '../util/index'
6
+ import { getComponentName } from '../vdom/create-component'
6
7
 
7
8
  export function initExtend(Vue: GlobalAPI) {
8
9
  /**
@@ -25,7 +26,8 @@ export function initExtend(Vue: GlobalAPI) {
25
26
  return cachedCtors[SuperId]
26
27
  }
27
28
 
28
- const name = extendOptions.name || Super.options.name
29
+ const name =
30
+ getComponentName(extendOptions) || getComponentName(Super.options)
29
31
  if (__DEV__ && name) {
30
32
  validateComponentName(name)
31
33
  }
@@ -58,7 +58,7 @@ export function initMixin(Vue: typeof Component) {
58
58
  initLifecycle(vm)
59
59
  initEvents(vm)
60
60
  initRender(vm)
61
- callHook(vm, 'beforeCreate')
61
+ callHook(vm, 'beforeCreate', undefined, false /* setContext */)
62
62
  initInjections(vm) // resolve injections before data/props
63
63
  initState(vm)
64
64
  initProvide(vm) // resolve provide after data/props
@@ -375,11 +375,16 @@ export function deactivateChildComponent(vm: Component, direct?: boolean) {
375
375
  }
376
376
  }
377
377
 
378
- export function callHook(vm: Component, hook: string, args?: any[]) {
378
+ export function callHook(
379
+ vm: Component,
380
+ hook: string,
381
+ args?: any[],
382
+ setContext = true
383
+ ) {
379
384
  // #7573 disable dep collection when invoking lifecycle hooks
380
385
  pushTarget()
381
386
  const prev = currentInstance
382
- setCurrentInstance(vm)
387
+ setContext && setCurrentInstance(vm)
383
388
  const handlers = vm.$options[hook]
384
389
  const info = `${hook} hook`
385
390
  if (handlers) {
@@ -390,6 +395,6 @@ export function callHook(vm: Component, hook: string, args?: any[]) {
390
395
  if (vm._hasHookEvent) {
391
396
  vm.$emit('hook:' + hook)
392
397
  }
393
- setCurrentInstance(prev)
398
+ setContext && setCurrentInstance(prev)
394
399
  popTarget()
395
400
  }
@@ -18,7 +18,7 @@ export function renderStatic(
18
18
  // otherwise, render a fresh tree.
19
19
  tree = cached[index] = this.$options.staticRenderFns[index].call(
20
20
  this._renderProxy,
21
- null,
21
+ this._c,
22
22
  this // for render fns generated for functional component templates
23
23
  )
24
24
  markStatic(tree, `__static__${index}`, false)
@@ -241,7 +241,7 @@ export function set(
241
241
  target.length = Math.max(target.length, key)
242
242
  target.splice(key, 1, val)
243
243
  // when mocking for SSR, array methods are not hijacked
244
- if (!ob.shallow && ob.mock) {
244
+ if (ob && !ob.shallow && ob.mock) {
245
245
  observe(val, false, true)
246
246
  }
247
247
  return val
@@ -1,6 +1,7 @@
1
1
  import { _Set as Set, isObject, isArray } from '../util/index'
2
2
  import type { SimpleSet } from '../util/index'
3
3
  import VNode from '../vdom/vnode'
4
+ import { isRef } from '../../v3'
4
5
 
5
6
  const seenObjects = new Set()
6
7
 
@@ -35,6 +36,8 @@ function _traverse(val: any, seen: SimpleSet) {
35
36
  if (isA) {
36
37
  i = val.length
37
38
  while (i--) _traverse(val[i], seen)
39
+ } else if (isRef(val)) {
40
+ _traverse(val.value, seen)
38
41
  } else {
39
42
  keys = Object.keys(val)
40
43
  i = keys.length
@@ -2,6 +2,7 @@ import config from '../config'
2
2
  import { noop, isArray, isFunction } from 'shared/util'
3
3
  import type { Component } from 'types/component'
4
4
  import { currentInstance } from 'v3/currentInstance'
5
+ import { getComponentName } from '../vdom/create-component'
5
6
 
6
7
  export let warn: (msg: string, vm?: Component | null) => void = noop
7
8
  export let tip = noop
@@ -40,7 +41,7 @@ if (__DEV__) {
40
41
  : vm._isVue
41
42
  ? vm.$options || (vm.constructor as any).options
42
43
  : vm
43
- let name = options.name || options._componentTag
44
+ let name = getComponentName(options)
44
45
  const file = options.__file
45
46
  if (!name && file) {
46
47
  const match = file.match(/([^/\\]+)\.vue$/)
@@ -28,6 +28,10 @@ import type {
28
28
  import type { Component } from 'types/component'
29
29
  import type { ComponentOptions, InternalComponentOptions } from 'types/options'
30
30
 
31
+ export function getComponentName(options: ComponentOptions) {
32
+ return options.name || options.__name || options._componentTag
33
+ }
34
+
31
35
  // inline hooks to be invoked on component VNodes during patch
32
36
  const componentVNodeHooks = {
33
37
  init(vnode: VNodeWithData, hydrating: boolean): boolean | void {
@@ -188,7 +192,7 @@ export function createComponent(
188
192
 
189
193
  // return a placeholder vnode
190
194
  // @ts-expect-error
191
- const name = Ctor.options.name || tag
195
+ const name = getComponentName(Ctor.options) || tag
192
196
  const vnode = new VNode(
193
197
  // @ts-expect-error
194
198
  `vue-component-${Ctor.cid}${name ? `-${name}` : ''}`,
@@ -23,6 +23,7 @@ import {
23
23
  } from 'web/runtime/transition-util'
24
24
  import VNode from 'core/vdom/vnode'
25
25
  import { VNodeWithData } from 'types/vnode'
26
+ import { getComponentName } from 'core/vdom/create-component'
26
27
 
27
28
  const props = extend(
28
29
  {
@@ -72,7 +73,7 @@ export default {
72
73
  } else if (__DEV__) {
73
74
  const opts = c.componentOptions
74
75
  const name: string = opts
75
- ? opts.Ctor.options.name || opts.tag || ''
76
+ ? getComponentName(opts.Ctor.options as any) || opts.tag || ''
76
77
  : c.tag
77
78
  warn(`<transition-group> children must be keyed: <${name}>`)
78
79
  }
@@ -0,0 +1,117 @@
1
+ import { warn, isFunction, isObject } from 'core/util'
2
+
3
+ interface AsyncComponentOptions {
4
+ loader: Function
5
+ loadingComponent?: any
6
+ errorComponent?: any
7
+ delay?: number
8
+ timeout?: number
9
+ suspensible?: boolean
10
+ onError?: (
11
+ error: Error,
12
+ retry: () => void,
13
+ fail: () => void,
14
+ attempts: number
15
+ ) => any
16
+ }
17
+
18
+ type AsyncComponentFactory = () => {
19
+ component: Promise<any>
20
+ loading?: any
21
+ error?: any
22
+ delay?: number
23
+ timeout?: number
24
+ }
25
+
26
+ /**
27
+ * v3-compatible async component API.
28
+ * @internal the type is manually declared in <root>/types/v3-define-async-component.d.ts
29
+ * because it relies on existing manual types
30
+ */
31
+ export function defineAsyncComponent(
32
+ source: (() => any) | AsyncComponentOptions
33
+ ): AsyncComponentFactory {
34
+ if (isFunction(source)) {
35
+ source = { loader: source } as AsyncComponentOptions
36
+ }
37
+
38
+ const {
39
+ loader,
40
+ loadingComponent,
41
+ errorComponent,
42
+ delay = 200,
43
+ timeout, // undefined = never times out
44
+ suspensible = false, // in Vue 3 default is true
45
+ onError: userOnError
46
+ } = source
47
+
48
+ if (__DEV__ && suspensible) {
49
+ warn(
50
+ `The suspensiblbe option for async components is not supported in Vue2. It is ignored.`
51
+ )
52
+ }
53
+
54
+ let pendingRequest: Promise<any> | null = null
55
+
56
+ let retries = 0
57
+ const retry = () => {
58
+ retries++
59
+ pendingRequest = null
60
+ return load()
61
+ }
62
+
63
+ const load = (): Promise<any> => {
64
+ let thisRequest: Promise<any>
65
+ return (
66
+ pendingRequest ||
67
+ (thisRequest = pendingRequest =
68
+ loader()
69
+ .catch(err => {
70
+ err = err instanceof Error ? err : new Error(String(err))
71
+ if (userOnError) {
72
+ return new Promise((resolve, reject) => {
73
+ const userRetry = () => resolve(retry())
74
+ const userFail = () => reject(err)
75
+ userOnError(err, userRetry, userFail, retries + 1)
76
+ })
77
+ } else {
78
+ throw err
79
+ }
80
+ })
81
+ .then((comp: any) => {
82
+ if (thisRequest !== pendingRequest && pendingRequest) {
83
+ return pendingRequest
84
+ }
85
+ if (__DEV__ && !comp) {
86
+ warn(
87
+ `Async component loader resolved to undefined. ` +
88
+ `If you are using retry(), make sure to return its return value.`
89
+ )
90
+ }
91
+ // interop module default
92
+ if (
93
+ comp &&
94
+ (comp.__esModule || comp[Symbol.toStringTag] === 'Module')
95
+ ) {
96
+ comp = comp.default
97
+ }
98
+ if (__DEV__ && comp && !isObject(comp) && !isFunction(comp)) {
99
+ throw new Error(`Invalid async component load result: ${comp}`)
100
+ }
101
+ return comp
102
+ }))
103
+ )
104
+ }
105
+
106
+ return () => {
107
+ const component = load()
108
+
109
+ return {
110
+ component,
111
+ delay,
112
+ timeout,
113
+ error: errorComponent,
114
+ loading: loadingComponent
115
+ }
116
+ }
117
+ }
@@ -196,12 +196,10 @@ function doWatch(
196
196
  getter = () => source.value
197
197
  forceTrigger = isShallow(source)
198
198
  } else if (isReactive(source)) {
199
- getter = isArray(source)
200
- ? () => {
201
- ;(source as any).__ob__.dep.depend()
202
- return source
203
- }
204
- : () => source
199
+ getter = () => {
200
+ ;(source as any).__ob__.dep.depend()
201
+ return source
202
+ }
205
203
  deep = true
206
204
  } else if (isArray(source)) {
207
205
  isMultiSource = true
@@ -320,8 +318,8 @@ function doWatch(
320
318
  } else {
321
319
  // pre
322
320
  watcher.update = () => {
323
- if (instance && instance === currentInstance) {
324
- // pre-watcher triggered inside setup()
321
+ if (instance && instance === currentInstance && !instance._isMounted) {
322
+ // pre-watcher triggered before
325
323
  const buffer = instance._preWatchers || (instance._preWatchers = [])
326
324
  if (buffer.indexOf(watcher) < 0) buffer.push(watcher)
327
325
  } else {
package/src/v3/index.ts CHANGED
@@ -1,3 +1,7 @@
1
+ /**
2
+ * Note: also update dist/vue.runtime.mjs when adding new exports to this file.
3
+ */
4
+
1
5
  export const version: string = '__VERSION__'
2
6
 
3
7
  export {
@@ -87,4 +91,6 @@ export function defineComponent(options: any) {
87
91
  return options
88
92
  }
89
93
 
94
+ export { defineAsyncComponent } from './apiAsyncComponent'
95
+
90
96
  export * from './apiLifecycle'
@@ -68,7 +68,7 @@ function createRef(rawValue: unknown, shallow: boolean) {
68
68
  }
69
69
  const ref: any = {}
70
70
  def(ref, RefFlag, true)
71
- def(ref, ReactiveFlags.IS_SHALLOW, true)
71
+ def(ref, ReactiveFlags.IS_SHALLOW, shallow)
72
72
  def(
73
73
  ref,
74
74
  'dep',
@@ -119,7 +119,16 @@ export function proxyWithRefUnwrap(
119
119
  Object.defineProperty(target, key, {
120
120
  enumerable: true,
121
121
  configurable: true,
122
- get: () => unref(source[key]),
122
+ get: () => {
123
+ const val = source[key]
124
+ if (isRef(val)) {
125
+ return val.value
126
+ } else {
127
+ const ob = val && val.__ob__
128
+ if (ob) ob.dep.depend()
129
+ return val
130
+ }
131
+ },
123
132
  set: value => {
124
133
  const oldValue = source[key]
125
134
  if (isRef(oldValue) && !isRef(value)) {
@@ -20,7 +20,7 @@ export type Component<
20
20
  | typeof Vue
21
21
  | FunctionalComponentOptions<Props>
22
22
  | ComponentOptions<never, Data, Methods, Computed, Props, SetupBindings>
23
- | DefineComponent<any, any, any, any, any>
23
+ | DefineComponent<any, any, any, any, any, any, any, any, any, any, any>
24
24
 
25
25
  type EsModule<T> = T | { default: T }
26
26
 
@@ -201,9 +201,9 @@ export interface ComponentOptions<
201
201
  directives?: { [key: string]: DirectiveFunction | DirectiveOptions }
202
202
  components?: {
203
203
  [key: string]:
204
- | Component<any, any, any, any>
204
+ | {}
205
+ | Component<any, any, any, any, any>
205
206
  | AsyncComponent<any, any, any, any>
206
- | DefineComponent<any, any, any, any, any, any, any, any, any, any>
207
207
  }
208
208
  transitions?: { [key: string]: object }
209
209
  filters?: { [key: string]: Function }
@@ -219,6 +219,8 @@ export interface ComponentOptions<
219
219
  parent?: Vue
220
220
  mixins?: (ComponentOptions<Vue> | typeof Vue)[]
221
221
  name?: string
222
+ // for SFC auto name inference w/ ts-loader check
223
+ __name?: string
222
224
  // TODO: support properly inferred 'extends'
223
225
  extends?: ComponentOptions<Vue> | typeof Vue
224
226
  delimiters?: [string, string]
@@ -1,15 +1,11 @@
1
- import { ExtractDefaultPropTypes, ExtractPropTypes } from './v3-component-props'
2
1
  import {
3
2
  DebuggerEvent,
4
- nextTick,
5
3
  ShallowUnwrapRef,
6
- UnwrapNestedRefs,
7
- WatchOptions,
8
- WatchStopHandle
4
+ UnwrapNestedRefs
9
5
  } from './v3-generated'
10
- import { Data, UnionToIntersection } from './common'
6
+ import { UnionToIntersection } from './common'
11
7
 
12
- import { VueConstructor } from './vue'
8
+ import { Vue, VueConstructor } from './vue'
13
9
  import {
14
10
  ComputedOptions,
15
11
  MethodOptions,
@@ -17,7 +13,7 @@ import {
17
13
  ComponentOptionsMixin,
18
14
  ComponentOptionsBase
19
15
  } from './v3-component-options'
20
- import { EmitFn, EmitsOptions, Slots } from './v3-setup-context'
16
+ import { EmitFn, EmitsOptions } from './v3-setup-context'
21
17
 
22
18
  /**
23
19
  * Custom properties added to component instances in any way and can be accessed through `this`
@@ -152,36 +148,44 @@ export type ComponentPublicInstance<
152
148
  any,
153
149
  any
154
150
  >
155
- > = {
156
- // $: ComponentInternalInstance
157
- $data: D
158
- $props: Readonly<
159
- MakeDefaultsOptional extends true
160
- ? Partial<Defaults> & Omit<P & PublicProps, keyof Defaults>
161
- : P & PublicProps
162
- >
163
- $attrs: Data
164
- $refs: Data
165
- $slots: Slots
166
- $root: ComponentPublicInstance | null
167
- $parent: ComponentPublicInstance | null
168
- $emit: EmitFn<E>
169
- $el: any
170
- $options: Options & MergedComponentOptionsOverride
171
- $forceUpdate: () => void
172
- $nextTick: typeof nextTick
173
- $watch(
174
- source: string | Function,
175
- cb: Function,
176
- options?: WatchOptions
177
- ): WatchStopHandle
178
- } & Readonly<P> &
151
+ > = Vue3Instance<
152
+ D,
153
+ P,
154
+ PublicProps,
155
+ E,
156
+ Defaults,
157
+ MakeDefaultsOptional,
158
+ Options
159
+ > &
160
+ Readonly<P> &
179
161
  ShallowUnwrapRef<B> &
180
162
  UnwrapNestedRefs<D> &
181
163
  ExtractComputedReturns<C> &
182
164
  M &
183
165
  ComponentCustomProperties
184
166
 
167
+ interface Vue3Instance<
168
+ D,
169
+ P,
170
+ PublicProps,
171
+ E,
172
+ Defaults,
173
+ MakeDefaultsOptional,
174
+ Options
175
+ > extends Vue<
176
+ D,
177
+ Readonly<
178
+ MakeDefaultsOptional extends true
179
+ ? Partial<Defaults> & Omit<P & PublicProps, keyof Defaults>
180
+ : P & PublicProps
181
+ >,
182
+ ComponentPublicInstance | null,
183
+ ComponentPublicInstance,
184
+ ComponentPublicInstance[],
185
+ Options & MergedComponentOptionsOverride,
186
+ EmitFn<E>
187
+ > {}
188
+
185
189
  type MergedHook<T = () => void> = T | T[]
186
190
 
187
191
  export type MergedComponentOptionsOverride = {
@@ -0,0 +1,26 @@
1
+ import { AsyncComponent, Component } from './options'
2
+
3
+ export type AsyncComponentResolveResult<T = Component> = T | { default: T } // es modules
4
+
5
+ export type AsyncComponentLoader<T = any> = () => Promise<
6
+ AsyncComponentResolveResult<T>
7
+ >
8
+
9
+ export interface AsyncComponentOptions {
10
+ loader: AsyncComponentLoader
11
+ loadingComponent?: Component
12
+ errorComponent?: Component
13
+ delay?: number
14
+ timeout?: number
15
+ // suspensible?: boolean
16
+ onError?: (
17
+ error: Error,
18
+ retry: () => void,
19
+ fail: () => void,
20
+ attempts: number
21
+ ) => any
22
+ }
23
+
24
+ export function defineAsyncComponent(
25
+ source: AsyncComponentLoader | AsyncComponentOptions
26
+ ): AsyncComponent
@@ -1,4 +1,3 @@
1
- import { Component } from '..'
2
1
  import {
3
2
  ComponentPropsOptions,
4
3
  ExtractDefaultPropTypes,
@@ -19,6 +18,7 @@ import {
19
18
  } from './v3-component-public-instance'
20
19
  import { Data, HasDefined } from './common'
21
20
  import { EmitsOptions } from './v3-setup-context'
21
+ import { CreateElement, RenderContext } from './umd'
22
22
 
23
23
  type DefineComponent<
24
24
  PropsOrPropOptions = {},
@@ -67,6 +67,30 @@ type DefineComponent<
67
67
  props: PropsOrPropOptions
68
68
  }
69
69
 
70
+ /**
71
+ * overload 0.0: functional component with array props
72
+ */
73
+ export function defineComponent<
74
+ PropNames extends string,
75
+ Props = Readonly<{ [key in PropNames]?: any }>
76
+ >(options: {
77
+ functional: true
78
+ props?: PropNames[]
79
+ render?: (h: CreateElement, context: RenderContext<Props>) => any
80
+ }): DefineComponent<Props>
81
+
82
+ /**
83
+ * overload 0.1: functional component with object props
84
+ */
85
+ export function defineComponent<
86
+ PropsOptions extends ComponentPropsOptions = ComponentPropsOptions,
87
+ Props = ExtractPropTypes<PropsOptions>
88
+ >(options: {
89
+ functional: true
90
+ props?: PropsOptions
91
+ render?: (h: CreateElement, context: RenderContext<Props>) => any
92
+ }): DefineComponent<PropsOptions>
93
+
70
94
  /**
71
95
  * overload 1: object format with no props
72
96
  */