diff --git a/components/anchor/__tests__/Anchor.test.js b/components/anchor/__tests__/Anchor.test.js index 91b259319..60ab0e03c 100644 --- a/components/anchor/__tests__/Anchor.test.js +++ b/components/anchor/__tests__/Anchor.test.js @@ -18,8 +18,10 @@ describe('Anchor Render', () => { Vue.nextTick(() => { wrapper.find('a[href="#API"]').trigger('click') wrapper.vm.$refs.anchor.handleScroll() - expect(wrapper.vm.$refs.anchor.$data.activeLink).not.toBe(null) - done() + setTimeout(() => { + expect(wrapper.vm.$refs.anchor.$data.activeLink).not.toBe(null) + done() + }, 1000) }) }) diff --git a/components/table/__tests__/Table.rowSelection.test.js b/components/table/__tests__/Table.rowSelection.test.js new file mode 100644 index 000000000..c02cdc7bc --- /dev/null +++ b/components/table/__tests__/Table.rowSelection.test.js @@ -0,0 +1,400 @@ +import Vue from 'vue' +import { mount } from '@vue/test-utils' +import { asyncExpect } from '@/tests/utils' +import Table from '..' + +describe('Table.rowSelection', () => { + const columns = [{ + title: 'Name', + dataIndex: 'name', + }] + + const data = [ + { key: 0, name: 'Jack' }, + { key: 1, name: 'Lucy' }, + { key: 2, name: 'Tom' }, + { key: 3, name: 'Jerry' }, + ] + function getTableOptions (props = {}, listeners = {}) { + return { + propsData: { + columns, + dataSource: data, + rowSelection: {}, + ...props, + }, + listeners: { + ...listeners, + }, + sync: false, + attachedToDocument: true, + } + } + function renderedNames (wrapper) { + return wrapper.findAll({ name: 'TableRow' }).wrappers.map(row => { + return row.props().record.name + }) + } + + function getStore (wrapper) { + return wrapper.vm._vnode.componentInstance.store + } + + it('select by checkbox', async () => { + const wrapper = mount(Table, getTableOptions()) + const checkboxes = wrapper.findAll('input') + const checkboxAll = checkboxes.at(0) + checkboxAll.element.checked = true + checkboxAll.trigger('change') + await asyncExpect(() => { + expect(getStore(wrapper).getState()).toEqual({ + selectedRowKeys: [0, 1, 2, 3], + selectionDirty: true, + }) + }) + checkboxes.at(1).element.checked = false + checkboxes.at(1).trigger('change') + await asyncExpect(() => { + expect(getStore(wrapper).getState()).toEqual({ + selectedRowKeys: [1, 2, 3], + selectionDirty: true, + }) + }) + checkboxes.at(1).element.checked = true + checkboxes.at(1).trigger('change') + await asyncExpect(() => { + expect(getStore(wrapper).getState()).toEqual({ + selectedRowKeys: [1, 2, 3, 0], + selectionDirty: true, + }) + }) + }) + + it('select by radio', async () => { + const wrapper = mount(Table, getTableOptions({ rowSelection: { type: 'radio' }})) + const radios = wrapper.findAll('input') + + expect(radios.length).toBe(4) + radios.at(0).element.checked = true + radios.at(0).trigger('change') + await asyncExpect(() => { + expect(getStore(wrapper).getState()).toEqual({ + selectedRowKeys: [0], + selectionDirty: true, + }) + }) + radios.at(radios.length - 1).element.checked = true + radios.at(radios.length - 1).trigger('change') + await asyncExpect(() => { + expect(getStore(wrapper).getState()).toEqual({ + selectedRowKeys: [3], + selectionDirty: true, + }) + }) + }) + + it('pass getCheckboxProps to checkbox', () => { + const rowSelection = { + getCheckboxProps: record => ({ props: { + disabled: record.name === 'Lucy', + name: record.name, + }}), + } + + const wrapper = mount(Table, getTableOptions({ rowSelection })) + const checkboxes = wrapper.findAll('input').wrappers + expect(checkboxes[1].vnode.data.attrs.disabled).toBe(false) + expect(checkboxes[1].vnode.data.attrs.name).toEqual(data[0].name) + expect(checkboxes[2].vnode.data.attrs.disabled).toBe(true) + expect(checkboxes[2].vnode.data.attrs.name).toEqual(data[1].name) + }) + + it('works with pagination', async () => { + const wrapper = mount(Table, getTableOptions({ pagination: { pageSize: 2 }})) + + const checkboxAll = wrapper.find({ name: 'SelectionCheckboxAll' }) + const pagers = wrapper.findAll({ name: 'Pager' }) + checkboxAll.find('input').element.checked = true + checkboxAll.find('input').trigger('change') + await asyncExpect(() => { + expect(checkboxAll.vm.$data).toEqual({ checked: true, indeterminate: false }) + }) + pagers.at(1).trigger('click') + await asyncExpect(() => { + expect(checkboxAll.vm.$data).toEqual({ checked: false, indeterminate: false }) + }) + pagers.at(0).trigger('click') + await asyncExpect(() => { + expect(checkboxAll.vm.$data).toEqual({ checked: true, indeterminate: false }) + }) + }) + + // https://github.com/ant-design/ant-design/issues/4020 + it('handles defaultChecked', async () => { + const rowSelection = { + getCheckboxProps: record => ({ + defaultChecked: record.key === 0, + }), + } + + const wrapper = mount(Table, getTableOptions({ rowSelection })) + + await asyncExpect(() => { + const checkboxs = wrapper.findAll('input') + expect(checkboxs.at(1).vnode.data.domProps.checked).toBe(true) + expect(checkboxs.at(2).vnode.data.domProps.checked).toBe(false) + checkboxs.at(2).element.checked = true + checkboxs.at(2).trigger('change') + }) + + await asyncExpect(() => { + const checkboxs = wrapper.findAll('input') + expect(checkboxs.at(1).vnode.data.domProps.checked).toBe(true) + expect(checkboxs.at(2).vnode.data.domProps.checked).toBe(true) + }) + }) + + it('can be controlled', async () => { + const wrapper = mount(Table, getTableOptions({ rowSelection: { selectedRowKeys: [0] }})) + + expect(getStore(wrapper).getState()).toEqual({ + selectedRowKeys: [0], + selectionDirty: false, + }) + + wrapper.setProps({ rowSelection: { selectedRowKeys: [1] }}) + await asyncExpect(() => { + expect(getStore(wrapper).getState()).toEqual({ + selectedRowKeys: [1], + selectionDirty: false, + }) + }) + }) + + it('fires change & select events', async () => { + const handleChange = jest.fn() + const handleSelect = jest.fn() + const rowSelection = { + onChange: handleChange, + onSelect: handleSelect, + } + const wrapper = mount(Table, getTableOptions({ rowSelection })) + const checkboxs = wrapper.findAll('input') + checkboxs.at(checkboxs.length - 1).element.checked = true + checkboxs.at(checkboxs.length - 1).trigger('change') + await asyncExpect(() => { + expect(handleChange).toBeCalledWith([3], [{ key: 3, name: 'Jerry' }]) + expect(handleSelect.mock.calls.length).toBe(1) + expect(handleSelect.mock.calls[0][0]).toEqual({ key: 3, name: 'Jerry' }) + expect(handleSelect.mock.calls[0][1]).toEqual(true) + expect(handleSelect.mock.calls[0][2]).toEqual([{ key: 3, name: 'Jerry' }]) + }) + }) + + it('fires selectAll event', async () => { + const handleSelectAll = jest.fn() + const rowSelection = { + onSelectAll: handleSelectAll, + } + const wrapper = mount(Table, getTableOptions({ rowSelection })) + const checkboxs = wrapper.findAll('input') + checkboxs.at(0).element.checked = true + checkboxs.at(0).trigger('change') + await asyncExpect(() => { + expect(handleSelectAll).toBeCalledWith(true, data, data) + }) + checkboxs.at(0).element.checked = false + checkboxs.at(0).trigger('change') + await asyncExpect(() => { + expect(handleSelectAll).toBeCalledWith(false, [], data) + }) + }) + + it('render with default selection correctly', async () => { + const rowSelection = { + selections: true, + } + const wrapper = mount(Table, getTableOptions({ rowSelection })) + const dropdownWrapper = mount({ + render () { + return wrapper.find({ name: 'Trigger' }).vm.getComponent() + }, + }, { sync: false }) + await asyncExpect(() => { + expect(dropdownWrapper.html()).toMatchSnapshot() + }) + + await asyncExpect(() => { + + }) + }) + + it('click select all selection', () => { + const handleSelectAll = jest.fn() + const rowSelection = { + onSelectAll: handleSelectAll, + selections: true, + } + const wrapper = mount(Table, getTableOptions({ rowSelection })) + + const dropdownWrapper = mount({ + render () { + return wrapper.find({ name: 'Trigger' }).vm.getComponent() + }, + }, { sync: false }) + dropdownWrapper.findAll('.ant-dropdown-menu-item > div').at(0).trigger('click') + + expect(handleSelectAll).toBeCalledWith(true, data, data) + }) + + it('fires selectInvert event', () => { + const handleSelectInvert = jest.fn() + const rowSelection = { + onSelectInvert: handleSelectInvert, + selections: true, + } + const wrapper = mount(Table, getTableOptions({ rowSelection })) + const checkboxes = wrapper.findAll('input') + checkboxes.at(1).element.checked = true + checkboxes.at(1).trigger('change') + const dropdownWrapper = mount({ + render () { + return wrapper.find({ name: 'Trigger' }).vm.getComponent() + }, + }, { sync: false }) + const div = dropdownWrapper.findAll('.ant-dropdown-menu-item > div') + div.at(div.length - 1).trigger('click') + + expect(handleSelectInvert).toBeCalledWith([1, 2, 3]) + }) + + // it('fires selection event', () => { + // const handleSelectOdd = jest.fn() + // const handleSelectEven = jest.fn() + // const rowSelection = { + // selections: [{ + // key: 'odd', + // text: '奇数项', + // onSelect: handleSelectOdd, + // }, { + // key: 'even', + // text: '偶数项', + // onSelect: handleSelectEven, + // }], + // } + // const wrapper = mount(Table, getTableOptions({ rowSelection })) + + // const dropdownWrapper = mount({ + // render () { + // return wrapper.find({ name: 'Trigger' }).vm.getComponent() + // }, + // }) + // expect(dropdownWrapper.find('.ant-dropdown-menu-item').length).toBe(4) + + // dropdownWrapper.find('.ant-dropdown-menu-item > div').at(2).trigger('click') + // expect(handleSelectOdd).toBeCalledWith([0, 1, 2, 3]) + + // dropdownWrapper.find('.ant-dropdown-menu-item > div').at(3).trigger('click') + // expect(handleSelectEven).toBeCalledWith([0, 1, 2, 3]) + // }) + + // it('could hide default selection options', () => { + // const rowSelection = { + // hideDefaultSelections: true, + // selections: [{ + // key: 'odd', + // text: '奇数项', + // }, { + // key: 'even', + // text: '偶数项', + // }], + // } + // const wrapper = mount(Table, getTableOptions({ rowSelection })) + // const dropdownWrapper = mount({ + // render () { + // return wrapper.find({ name: 'Trigger' }).vm.getComponent() + // }, + // }) + // expect(dropdownWrapper.find('.ant-dropdown-menu-item').length).toBe(2) + // }) + + // it('handle custom selection onSelect correctly when hide default selection options', () => { + // const handleSelectOdd = jest.fn() + // const handleSelectEven = jest.fn() + // const rowSelection = { + // hideDefaultSelections: true, + // selections: [{ + // key: 'odd', + // text: '奇数项', + // onSelect: handleSelectOdd, + // }, { + // key: 'even', + // text: '偶数项', + // onSelect: handleSelectEven, + // }], + // } + // const wrapper = mount(Table, getTableOptions({ rowSelection })) + + // const dropdownWrapper = mount({ + // render () { + // return wrapper.find({ name: 'Trigger' }).vm.getComponent() + // }, + // }) + // expect(dropdownWrapper.find('.ant-dropdown-menu-item').length).toBe(2) + + // dropdownWrapper.find('.ant-dropdown-menu-item > div').at(0).trigger('click') + // expect(handleSelectOdd).toBeCalledWith([0, 1, 2, 3]) + + // dropdownWrapper.find('.ant-dropdown-menu-item > div').at(1).trigger('click') + // expect(handleSelectEven).toBeCalledWith([0, 1, 2, 3]) + // }) + + // // https://github.com/ant-design/ant-design/issues/4245 + // it('handles disabled checkbox correctly when dataSource changes', () => { + // const rowSelection = { + // getCheckboxProps: record => ({ disabled: record.disabled }), + // } + // const wrapper = mount(Table, getTableOptions({ rowSelection })) + // const newData = [ + // { key: 0, name: 'Jack', disabled: true }, + // { key: 1, name: 'Lucy', disabled: true }, + // ] + // wrapper.setProps({ dataSource: newData }) + // wrapper.find('input').forEach((checkbox) => { + // expect(checkbox.props().disabled).toBe(true) + // }) + // }) + + // // https://github.com/ant-design/ant-design/issues/4779 + // it('should not switch pagination when select record', () => { + // const newData = [] + // for (let i = 0; i < 20; i += 1) { + // newData.push({ + // key: i.toString(), + // name: i.toString(), + // }) + // } + // const wrapper = mount(Table, getTableOptions({ + // rowSelection: {}, + // dataSource: newData, + // })) + // wrapper.find('Pager').last().trigger('click') // switch to second page + // wrapper.find('input').first().trigger('change', { target: { checked: true }}) + // wrapper.update() + // expect(renderedNames(wrapper)).toEqual(['10', '11', '12', '13', '14', '15', '16', '17', '18', '19']) + // }) + + // it('highlight selected row', () => { + // const wrapper = mount(Table, getTableOptions()) + // wrapper.find('input').at(1).trigger('change', { target: { checked: true }}) + // expect(wrapper.find('tbody tr').at(0).hasClass('ant-table-row-selected')).toBe(true) + // }) + + // it('fix selection column on the left', () => { + // const wrapper = mount(Table, getTableOptions({ + // rowSelection: { fixed: true }, + // })) + + // expect(wrapper).toMatchSnapshot() + // }) +}) diff --git a/components/table/__tests__/__snapshots__/Table.rowSelection.test.js.snap b/components/table/__tests__/__snapshots__/Table.rowSelection.test.js.snap new file mode 100644 index 000000000..a30f3646f --- /dev/null +++ b/components/table/__tests__/__snapshots__/Table.rowSelection.test.js.snap @@ -0,0 +1,16 @@ +// Jest Snapshot v1, https://goo.gl/fbAQLP + +exports[`Table.rowSelection render with default selection correctly 1`] = ` +
+ +
+`;