h.test-d.ts 4.4 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182
  1. import {
  2. describe,
  3. h,
  4. defineComponent,
  5. ref,
  6. Fragment,
  7. Teleport,
  8. Suspense,
  9. Component,
  10. expectError,
  11. expectAssignable
  12. } from './index'
  13. describe('h inference w/ element', () => {
  14. // key
  15. h('div', { key: 1 })
  16. h('div', { key: 'foo' })
  17. // @ts-expect-error
  18. expectError(h('div', { key: [] }))
  19. // @ts-expect-error
  20. expectError(h('div', { key: {} }))
  21. // ref
  22. h('div', { ref: 'foo' })
  23. h('div', { ref: ref(null) })
  24. h('div', { ref: el => {} })
  25. // @ts-expect-error
  26. expectError(h('div', { ref: [] }))
  27. // @ts-expect-error
  28. expectError(h('div', { ref: {} }))
  29. // @ts-expect-error
  30. expectError(h('div', { ref: 123 }))
  31. })
  32. describe('h inference w/ Fragment', () => {
  33. // only accepts array children
  34. h(Fragment, ['hello'])
  35. h(Fragment, { key: 123 }, ['hello'])
  36. // @ts-expect-error
  37. expectError(h(Fragment, 'foo'))
  38. // @ts-expect-error
  39. expectError(h(Fragment, { key: 123 }, 'bar'))
  40. })
  41. describe('h inference w/ Teleport', () => {
  42. h(Teleport, { to: '#foo' }, 'hello')
  43. // @ts-expect-error
  44. expectError(h(Teleport))
  45. // @ts-expect-error
  46. expectError(h(Teleport, {}))
  47. // @ts-expect-error
  48. expectError(h(Teleport, { to: '#foo' }))
  49. })
  50. describe('h inference w/ Suspense', () => {
  51. h(Suspense, { onRecede: () => {}, onResolve: () => {} }, 'hello')
  52. h(Suspense, 'foo')
  53. h(Suspense, () => 'foo')
  54. h(Suspense, null, {
  55. default: () => 'foo'
  56. })
  57. // @ts-expect-error
  58. expectError(h(Suspense, { onResolve: 1 }))
  59. })
  60. describe('h inference w/ functional component', () => {
  61. const Func = (_props: { foo: string; bar?: number }) => ''
  62. h(Func, { foo: 'hello' })
  63. h(Func, { foo: 'hello', bar: 123 })
  64. // @ts-expect-error
  65. expectError(h(Func, { foo: 123 }))
  66. // @ts-expect-error
  67. expectError(h(Func, {}))
  68. // @ts-expect-error
  69. expectError(h(Func, { bar: 123 }))
  70. })
  71. describe('h support w/ plain object component', () => {
  72. const Foo = {
  73. props: {
  74. foo: String
  75. }
  76. }
  77. h(Foo, { foo: 'ok' })
  78. h(Foo, { foo: 'ok', class: 'extra' })
  79. // no inference in this case
  80. })
  81. describe('h inference w/ defineComponent', () => {
  82. const Foo = defineComponent({
  83. props: {
  84. foo: String,
  85. bar: {
  86. type: Number,
  87. required: true
  88. }
  89. }
  90. })
  91. h(Foo, { bar: 1 })
  92. h(Foo, { bar: 1, foo: 'ok' })
  93. // should allow extraneous props (attrs fallthrough)
  94. h(Foo, { bar: 1, foo: 'ok', class: 'extra' })
  95. // @ts-expect-error should fail on missing required prop
  96. expectError(h(Foo, {}))
  97. // @ts-expect-error
  98. expectError(h(Foo, { foo: 'ok' }))
  99. // @ts-expect-error should fail on wrong type
  100. expectError(h(Foo, { bar: 1, foo: 1 }))
  101. })
  102. describe('h inference w/ defineComponent + optional props', () => {
  103. const Foo = defineComponent({
  104. setup(_props: { foo?: string; bar: number }) {}
  105. })
  106. h(Foo, { bar: 1 })
  107. h(Foo, { bar: 1, foo: 'ok' })
  108. // should allow extraneous props (attrs fallthrough)
  109. h(Foo, { bar: 1, foo: 'ok', class: 'extra' })
  110. // @ts-expect-error should fail on missing required prop
  111. expectError(h(Foo, {}))
  112. // @ts-expect-error
  113. expectError(h(Foo, { foo: 'ok' }))
  114. // @ts-expect-error should fail on wrong type
  115. expectError(h(Foo, { bar: 1, foo: 1 }))
  116. })
  117. describe('h inference w/ defineComponent + direct function', () => {
  118. const Foo = defineComponent((_props: { foo?: string; bar: number }) => {})
  119. h(Foo, { bar: 1 })
  120. h(Foo, { bar: 1, foo: 'ok' })
  121. // should allow extraneous props (attrs fallthrough)
  122. h(Foo, { bar: 1, foo: 'ok', class: 'extra' })
  123. // @ts-expect-error should fail on missing required prop
  124. expectError(h(Foo, {}))
  125. // @ts-expect-error
  126. expectError(h(Foo, { foo: 'ok' }))
  127. // @ts-expect-error should fail on wrong type
  128. expectError(h(Foo, { bar: 1, foo: 1 }))
  129. })
  130. // #922
  131. describe('h support for generic component type', () => {
  132. function foo(bar: Component) {
  133. h(bar)
  134. h(bar, 'hello')
  135. h(bar, { id: 'ok' }, 'hello')
  136. }
  137. foo({})
  138. })
  139. // #993
  140. describe('describeComponent extends Component', () => {
  141. // functional
  142. expectAssignable<Component>(
  143. defineComponent((_props: { foo?: string; bar: number }) => {})
  144. )
  145. // typed props
  146. expectAssignable<Component>(defineComponent({}))
  147. // prop arrays
  148. expectAssignable<Component>(
  149. defineComponent({
  150. props: ['a', 'b']
  151. })
  152. )
  153. // prop object
  154. expectAssignable<Component>(
  155. defineComponent({
  156. props: {
  157. foo: String,
  158. bar: {
  159. type: Number,
  160. required: true
  161. }
  162. }
  163. })
  164. )
  165. })