UNPKG

bootstrap-vue-3

Version:

Early (but lovely) implementation of Vue 3, Bootstrap 5 and Typescript

403 lines (335 loc) 12 kB
import {afterEach, describe, expect, it} from 'vitest' import {enableAutoUnmount, mount} from '@vue/test-utils' import {createContainer} from '../../../tests/utils' import {nextTick} from 'vue' import BFormRadioGroup from './BFormRadioGroup.vue' import BFormRadio from './BFormRadio.vue' const global = {components: {BFormRadio}} describe('form-radio-group', () => { enableAutoUnmount(afterEach) // --- Structure, class and attributes tests --- it('default has structure <div></div>', () => { const wrapper = mount(BFormRadioGroup, {global}) expect(wrapper).toBeDefined() expect(wrapper.element.tagName).toBe('DIV') expect(wrapper.element.children.length).toEqual(0) }) it('default has no classes on wrapper other than focus ring', () => { const wrapper = mount(BFormRadioGroup, {global}) expect(wrapper.classes().length).toEqual(1) expect(wrapper.classes()).toContain('bv-no-focus-ring') }) it('default has auto Id set', async () => { const wrapper = mount(BFormRadioGroup, { attachTo: createContainer(), global, }) await nextTick() expect(wrapper.attributes('id')).toBeDefined() }) it('default has tabindex set to -1', () => { const wrapper = mount(BFormRadioGroup, {global}) expect(wrapper.attributes('tabindex')).toBeDefined() expect(wrapper.attributes('tabindex')).toBe('-1') }) it('default does not have aria-required set', () => { const wrapper = mount(BFormRadioGroup, {global}) expect(wrapper.attributes('aria-required')).toBeUndefined() }) it('default does not have aria-invalid set', () => { const wrapper = mount(BFormRadioGroup, {global}) expect(wrapper.attributes('aria-invalid')).toBeUndefined() }) it('default has attribute role=radiogroup', () => { const wrapper = mount(BFormRadioGroup, {global}) expect(wrapper.attributes('role')).toBeDefined() expect(wrapper.attributes('role')).toBe('radiogroup') }) it('default has user provided Id', () => { const wrapper = mount(BFormRadioGroup, { attachTo: createContainer(), global, props: { id: 'test', }, }) expect(wrapper.attributes('id')).toBeDefined() expect(wrapper.attributes('id')).toBe('test') }) it('default has class was-validated when validated=true', () => { const wrapper = mount(BFormRadioGroup, { attachTo: createContainer(), global, props: { validated: true, }, }) expect(wrapper.classes()).toBeDefined() expect(wrapper.classes()).toContain('was-validated') }) it('default has attribute aria-invalid=true when state=false', () => { const wrapper = mount(BFormRadioGroup, { attachTo: createContainer(), global, props: { state: false, }, }) expect(wrapper.attributes('aria-invalid')).toBeDefined() expect(wrapper.attributes('aria-invalid')).toBe('true') }) it('default does not have attribute aria-invalid when state=true', () => { const wrapper = mount(BFormRadioGroup, { attachTo: createContainer(), global, props: { state: true, }, }) expect(wrapper.attributes('aria-invalid')).toBeUndefined() }) it('default does not have attribute aria-invalid when state=undefined', () => { const wrapper = mount(BFormRadioGroup, { attachTo: createContainer(), global, props: { state: undefined, }, }) expect(wrapper.attributes('aria-invalid')).toBeUndefined() }) it('default has attribute aria-invalid=true when aria-invalid=true', () => { const wrapper = mount(BFormRadioGroup, { attachTo: createContainer(), global, props: { ariaInvalid: true, }, }) expect(wrapper.attributes('aria-invalid')).toBeDefined() expect(wrapper.attributes('aria-invalid')).toBe('true') }) it('default has attribute aria-invalid=true when aria-invalid="true"', () => { const wrapper = mount(BFormRadioGroup, { attachTo: createContainer(), global, props: { ariaInvalid: 'true', }, }) expect(wrapper.attributes('aria-invalid')).toBeDefined() expect(wrapper.attributes('aria-invalid')).toBe('true') }) it('default has attribute aria-invalid=true when aria-invalid=""', () => { const wrapper = mount(BFormRadioGroup, { attachTo: createContainer(), global, props: { ariaInvalid: '', }, }) expect(wrapper.attributes('aria-invalid')).toBeDefined() expect(wrapper.attributes('aria-invalid')).toBe('true') }) // --- Button mode structure --- it('button mode has classes button-group and button-group-toggle', () => { const wrapper = mount(BFormRadioGroup, { attachTo: createContainer(), global, props: { buttons: true, }, }) expect(wrapper.classes()).toBeDefined() expect(wrapper.classes().length).toBe(2) expect(wrapper.classes()).toContain('btn-group') expect(wrapper.classes()).toContain('bv-no-focus-ring') }) it('button mode has classes button-group-vertical and button-group-toggle when stacked=true', () => { const wrapper = mount(BFormRadioGroup, { attachTo: createContainer(), global, props: { buttons: true, stacked: true, }, }) expect(wrapper.classes()).toBeDefined() expect(wrapper.classes().length).toBe(2) expect(wrapper.classes()).toContain('btn-group-vertical') expect(wrapper.classes()).toContain('bv-no-focus-ring') }) it('button mode has size class when size prop set', () => { const wrapper = mount(BFormRadioGroup, { attachTo: createContainer(), global, props: { buttons: true, size: 'lg', }, }) expect(wrapper.classes()).toBeDefined() expect(wrapper.classes().length).toBe(3) expect(wrapper.classes()).toContain('btn-group') expect(wrapper.classes()).toContain('btn-group-lg') expect(wrapper.classes()).toContain('bv-no-focus-ring') }) it('button mode has size class when size prop set and stacked', () => { const wrapper = mount(BFormRadioGroup, { attachTo: createContainer(), global, props: { buttons: true, stacked: true, size: 'lg', }, }) expect(wrapper.classes()).toBeDefined() expect(wrapper.classes().length).toBe(3) expect(wrapper.classes()).toContain('btn-group-vertical') expect(wrapper.classes()).toContain('btn-group-lg') expect(wrapper.classes()).toContain('bv-no-focus-ring') }) it('button mode button variant works', async () => { const wrapper = mount(BFormRadioGroup, { attachTo: createContainer(), global, props: { modelValue: '', buttons: true, buttonVariant: 'primary', options: [ {text: 'button 1', value: 'first'}, {text: 'button 2', value: 'second'}, {text: 'button 3', value: 'third', props: {buttonVariant: 'danger'}}, ], }, }) expect(wrapper).toBeDefined() await nextTick() // Find all the labels with .btn class const $buttons = wrapper.findAll('label.btn') expect($buttons).toBeDefined() expect($buttons.length).toBe(3) // Expect them to have the correct variant classes expect($buttons[0].classes()).toContain('btn-primary') expect($buttons[1].classes()).toContain('btn-primary') expect($buttons[2].classes()).toContain('btn-danger') }) // --- Functionality testing --- it('has radios via options array', () => { const wrapper = mount(BFormRadioGroup, { attachTo: createContainer(), global, props: { options: ['one', 'two', 'three'], modelValue: '', }, }) expect(wrapper.vm.modelValue).toEqual('') expect(wrapper.findAll('input[type=radio]').length).toBe(3) }) it('has radios via options array which respect disabled', () => { const wrapper = mount(BFormRadioGroup, { attachTo: createContainer(), global, props: { options: [{text: 'one'}, {text: 'two'}, {text: 'three', disabled: true}], modelValue: '', }, }) expect(wrapper.vm.modelValue).toEqual('') expect(wrapper.classes()).toBeDefined() const $radios = wrapper.findAll('input[type=radio]') expect($radios.length).toBe(3) expect($radios[0].attributes('disabled')).toBeUndefined() expect($radios[1].attributes('disabled')).toBeUndefined() expect($radios[2].attributes('disabled')).toBeDefined() }) it('has radios with attribute required when prop required set', async () => { const wrapper = mount(BFormRadioGroup, { attachTo: createContainer(), global, props: { options: ['one', 'two', 'three'], modelValue: '', required: true, }, }) // We need `$nextTick()` here since auto generated name is // computed in a `$nextTick()` on mount await nextTick() expect(wrapper.vm.modelValue).toEqual('') expect(wrapper.classes()).toBeDefined() const $radios = wrapper.findAll('input[type=radio]') expect($radios.length).toBe(3) $radios.forEach(($radio) => { expect($radio.attributes('required')).toBeDefined() expect($radio.attributes('aria-required')).toBe('true') }) }) it('emits change event when radio clicked', async () => { const wrapper = mount(BFormRadioGroup, { attachTo: createContainer(), global, props: { options: ['one', 'two', 'three'], modelValue: '', }, attrs: { 'onUpdate:modelValue': (modelValue) => wrapper.setProps({modelValue}), }, }) expect(wrapper.vm.modelValue).toEqual('') expect(wrapper.classes()).toBeDefined() const $radios = wrapper.findAll('input[type=radio]') expect($radios.length).toBe(3) await $radios[0].trigger('click') expect(wrapper.vm.modelValue).toEqual('one') expect(wrapper.emitted('change')).toBeDefined() expect(wrapper.emitted('change').length).toBe(1) expect(wrapper.emitted('change')[0][0]).toEqual('one') expect(wrapper.emitted('update:modelValue')).toBeDefined() expect(wrapper.emitted('update:modelValue').length).toBe(1) expect(wrapper.emitted('update:modelValue')[0][0]).toEqual('one') await $radios[2].trigger('click') expect(wrapper.vm.modelValue).toEqual('three') expect(wrapper.emitted('change').length).toBe(2) expect(wrapper.emitted('change')[1][0]).toEqual('three') expect(wrapper.emitted('update:modelValue').length).toBe(2) expect(wrapper.emitted('update:modelValue')[1][0]).toEqual('three') await $radios[0].trigger('click') expect(wrapper.vm.modelValue).toEqual('one') expect(wrapper.emitted('change').length).toBe(3) expect(wrapper.emitted('change')[2][0]).toEqual('one') expect(wrapper.emitted('update:modelValue').length).toBe(3) expect(wrapper.emitted('update:modelValue')[2][0]).toEqual('one') }) it('radios reflect group checked v-model', async () => { const wrapper = mount(BFormRadioGroup, { attachTo: createContainer(), global, props: { options: ['one', 'two', 'three'], modelValue: 'two', }, attrs: { 'onUpdate:modelValue': (modelValue) => wrapper.setProps({modelValue}), }, }) expect(wrapper.vm.modelValue).toEqual('two') expect(wrapper.classes()).toBeDefined() const $radios = wrapper.findAll('input[type=radio]') expect($radios.length).toBe(3) expect($radios[0].element.checked).toBe(false) expect($radios[1].element.checked).toBe(true) expect($radios[2].element.checked).toBe(false) await wrapper.setProps({modelValue: 'three'}) await nextTick() await nextTick() expect(wrapper.vm.modelValue).toEqual('three') expect($radios[0].element.checked).toBe(false) expect($radios[1].element.checked).toBe(false) expect($radios[2].element.checked).toBe(true) }) })