2022-03-25 15:35:56 +08:00
|
|
|
import { Comment, Fragment, h, nextTick, ref } from 'vue'
|
2022-01-04 09:15:15 +08:00
|
|
|
import { shallowMount } from '@vue/test-utils'
|
2022-04-19 12:46:57 +08:00
|
|
|
import { afterEach, describe, expect, it, vi } from 'vitest'
|
2022-02-11 11:03:15 +08:00
|
|
|
import { debugWarn } from '@element-plus/utils'
|
2022-01-04 09:15:15 +08:00
|
|
|
import { FORWARD_REF_INJECTION_KEY } from '@element-plus/hooks'
|
2022-03-01 21:51:16 +08:00
|
|
|
import { OnlyChild } from '../src/only-child'
|
|
|
|
import type { MountingOptions } from '@vue/test-utils'
|
2022-01-04 09:15:15 +08:00
|
|
|
|
2022-03-01 21:51:16 +08:00
|
|
|
type Slot = NonNullable<NonNullable<MountingOptions<any>['slots']>['default']>
|
2022-01-04 09:15:15 +08:00
|
|
|
|
2022-04-19 12:46:57 +08:00
|
|
|
vi.mock('@element-plus/utils/error', () => ({
|
|
|
|
debugWarn: vi.fn(),
|
2022-01-04 09:15:15 +08:00
|
|
|
}))
|
|
|
|
|
|
|
|
const AXIOM = 'rem is the best girl'
|
|
|
|
|
2022-03-01 21:51:16 +08:00
|
|
|
const defaultProvide = {
|
|
|
|
[FORWARD_REF_INJECTION_KEY as any]: {
|
|
|
|
forwardRef: ref(null),
|
|
|
|
},
|
|
|
|
}
|
|
|
|
const createComponent = (slot: Slot) => {
|
|
|
|
return shallowMount(OnlyChild, {
|
|
|
|
global: {
|
|
|
|
provide: defaultProvide,
|
2022-01-04 09:15:15 +08:00
|
|
|
},
|
2022-03-01 21:51:16 +08:00
|
|
|
// vue test utils adds the entry for us even though default's value is null
|
|
|
|
slots: slot ? { default: slot } : undefined,
|
|
|
|
})
|
|
|
|
}
|
2022-01-04 09:15:15 +08:00
|
|
|
|
2022-03-01 21:51:16 +08:00
|
|
|
describe('ElOnlyChild', () => {
|
2022-01-04 09:15:15 +08:00
|
|
|
let wrapper: ReturnType<typeof createComponent>
|
|
|
|
|
|
|
|
afterEach(() => {
|
|
|
|
wrapper?.unmount()
|
|
|
|
})
|
|
|
|
|
|
|
|
it('should be able to render only one child', async () => {
|
|
|
|
const kls = 'test_kls'
|
2022-03-01 21:51:16 +08:00
|
|
|
wrapper = createComponent(() => [<div class={kls}>{AXIOM}</div>])
|
2022-01-04 09:15:15 +08:00
|
|
|
|
|
|
|
await nextTick()
|
|
|
|
|
|
|
|
expect(debugWarn).not.toHaveBeenCalled()
|
|
|
|
const renderedChild = wrapper.find(`.${kls}`)
|
|
|
|
expect(renderedChild.exists()).toBe(true)
|
|
|
|
expect(renderedChild.text()).toBe(AXIOM)
|
|
|
|
})
|
|
|
|
|
|
|
|
it('should be able to render string type and wrap it into span', async () => {
|
2022-03-01 21:51:16 +08:00
|
|
|
wrapper = createComponent(() => [AXIOM])
|
2022-01-04 09:15:15 +08:00
|
|
|
await nextTick()
|
|
|
|
|
|
|
|
expect(debugWarn).not.toHaveBeenCalled()
|
|
|
|
expect(wrapper.find('span').exists()).toBe(true)
|
|
|
|
})
|
|
|
|
|
|
|
|
it('should be able to unwrap fragmented children', async () => {
|
2022-03-01 21:51:16 +08:00
|
|
|
wrapper = createComponent(() => [<>{AXIOM}</>])
|
2022-01-04 09:15:15 +08:00
|
|
|
await nextTick()
|
|
|
|
|
|
|
|
expect(debugWarn).not.toHaveBeenCalled()
|
|
|
|
expect(wrapper.find('span').exists()).toBe(true)
|
|
|
|
})
|
|
|
|
|
2022-02-21 14:23:20 +08:00
|
|
|
it('should skip svg and child type is svg', async () => {
|
|
|
|
const wrapper = createComponent(() => [
|
2022-03-01 21:51:16 +08:00
|
|
|
<svg
|
|
|
|
xmlns="http://www.w3.org/2000/svg"
|
|
|
|
viewBox="0 0 32 32"
|
|
|
|
width="20"
|
|
|
|
height="20"
|
|
|
|
>
|
|
|
|
<path d="M14.667 14.667v-8h2.667v8h8v2.667h-8v8h-2.667v-8h-8v-2.667z" />
|
|
|
|
</svg>,
|
2022-02-21 14:23:20 +08:00
|
|
|
])
|
|
|
|
await nextTick()
|
|
|
|
|
|
|
|
expect(debugWarn).not.toHaveBeenCalled()
|
|
|
|
expect(wrapper.find('svg').attributes('viewBox')).toEqual('0 0 32 32')
|
|
|
|
expect(wrapper.find('svg').attributes('width')).toEqual('20')
|
|
|
|
expect(wrapper.find('svg').attributes('height')).toEqual('20')
|
|
|
|
|
|
|
|
await wrapper.trigger('hover')
|
|
|
|
await expect(wrapper.find('svg').exists()).toBe(true)
|
|
|
|
})
|
|
|
|
|
2022-01-04 09:15:15 +08:00
|
|
|
it('should skip comment', async () => {
|
|
|
|
wrapper = createComponent(() => [
|
2022-03-01 21:51:16 +08:00
|
|
|
<>
|
|
|
|
{h(Comment, 'some comment')}
|
|
|
|
{AXIOM}
|
|
|
|
</>,
|
2022-01-04 09:15:15 +08:00
|
|
|
])
|
|
|
|
await nextTick()
|
|
|
|
|
|
|
|
expect(debugWarn).not.toHaveBeenCalled()
|
|
|
|
expect(wrapper.find('span').exists()).toBe(true)
|
|
|
|
})
|
|
|
|
|
|
|
|
it('should return nothing and warn when no valid children found', async () => {
|
2022-03-01 21:51:16 +08:00
|
|
|
wrapper = createComponent(() => [<></>])
|
2022-01-04 09:15:15 +08:00
|
|
|
await nextTick()
|
|
|
|
|
|
|
|
expect(debugWarn).toHaveBeenCalled()
|
|
|
|
})
|
|
|
|
|
|
|
|
it('should render nothing when invalid node were found', async () => {
|
|
|
|
wrapper = createComponent(() => [h(Fragment, null)])
|
|
|
|
await nextTick()
|
|
|
|
|
|
|
|
expect(debugWarn).toHaveBeenCalled()
|
|
|
|
})
|
|
|
|
|
|
|
|
it('should warns about having multiple children', async () => {
|
2022-03-01 21:51:16 +08:00
|
|
|
wrapper = createComponent(() => [AXIOM, AXIOM])
|
2022-01-04 09:15:15 +08:00
|
|
|
await nextTick()
|
|
|
|
|
|
|
|
expect(debugWarn).toHaveBeenCalledTimes(1)
|
|
|
|
expect(wrapper.text()).toBe('')
|
|
|
|
})
|
|
|
|
|
|
|
|
it('should render nothing when no children provided', async () => {
|
2022-03-01 21:51:16 +08:00
|
|
|
wrapper = createComponent(null as any)
|
2022-01-04 09:15:15 +08:00
|
|
|
await nextTick()
|
|
|
|
|
|
|
|
expect(debugWarn).not.toHaveBeenCalled()
|
|
|
|
expect(wrapper.text()).toBe('')
|
|
|
|
})
|
|
|
|
})
|