| 123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180 |
- import Vue from '@vue/compat'
- import type { ComponentOptions } from '../../runtime-core/src/component'
- import { nextTick } from '../../runtime-core/src/scheduler'
- import {
- DeprecationTypes,
- deprecationData,
- toggleDeprecationWarning,
- } from '../../runtime-core/src/compat/compatConfig'
- import { triggerEvent } from './utils'
- beforeEach(() => {
- toggleDeprecationWarning(true)
- Vue.configureCompat({
- MODE: 2,
- GLOBAL_MOUNT: 'suppress-warning',
- })
- })
- afterEach(() => {
- toggleDeprecationWarning(false)
- Vue.configureCompat({ MODE: 3 })
- })
- describe('COMPONENT_V_MODEL', () => {
- async function runTest(CustomInput: ComponentOptions) {
- const vm = new Vue({
- data() {
- return {
- text: 'foo',
- }
- },
- components: { CustomInput },
- template: `
- <div>
- <span>{{ text }}</span>
- <custom-input v-model="text"></custom-input>
- </div>
- `,
- }).$mount() as any
- const input = vm.$el.querySelector('input')
- const span = vm.$el.querySelector('span')
- expect(input.value).toBe('foo')
- expect(span.textContent).toBe('foo')
- expect(
- (deprecationData[DeprecationTypes.COMPONENT_V_MODEL].message as Function)(
- CustomInput,
- ),
- ).toHaveBeenWarned()
- input.value = 'bar'
- triggerEvent(input, 'input')
- await nextTick()
- expect(input.value).toBe('bar')
- expect(span.textContent).toBe('bar')
- vm.text = 'baz'
- await nextTick()
- expect(input.value).toBe('baz')
- expect(span.textContent).toBe('baz')
- }
- test('basic usage', async () => {
- await runTest({
- name: 'CustomInput',
- props: ['value'],
- template: `<input :value="value" @input="$emit('input', $event.target.value)">`,
- })
- })
- test('with model option', async () => {
- await runTest({
- name: 'CustomInput',
- props: ['input'],
- model: {
- prop: 'input',
- event: 'update',
- },
- template: `<input :value="input" @input="$emit('update', $event.target.value)">`,
- })
- })
- async function runTestWithModifier(CustomInput: ComponentOptions) {
- const vm = new Vue({
- data() {
- return {
- text: ' foo ',
- }
- },
- components: {
- CustomInput,
- },
- template: `
- <div>
- <span>{{ text }}</span>
- <custom-input v-model.trim="text"></custom-input>
- </div>
- `,
- }).$mount() as any
- const input = vm.$el.querySelector('input')
- const span = vm.$el.querySelector('span')
- expect(input.value).toBe(' foo ')
- expect(span.textContent).toBe(' foo ')
- expect(
- (deprecationData[DeprecationTypes.COMPONENT_V_MODEL].message as Function)(
- CustomInput,
- ),
- ).toHaveBeenWarned()
- input.value = ' bar '
- triggerEvent(input, 'input')
- await nextTick()
- expect(input.value).toBe('bar')
- expect(span.textContent).toBe('bar')
- }
- test('with model modifiers', async () => {
- await runTestWithModifier({
- name: 'CustomInput',
- props: ['value'],
- template: `<input :value="value" @input="$emit('input', $event.target.value)">`,
- })
- })
- test('with model modifiers and model option', async () => {
- await runTestWithModifier({
- name: 'CustomInput',
- props: ['foo'],
- model: {
- prop: 'foo',
- event: 'bar',
- },
- template: `<input :value="foo" @input="$emit('bar', $event.target.value)">`,
- })
- })
- // #14202
- test('should handle v-model deprecation warning with missing appContext', async () => {
- const ChildComponent = {
- template: `<div @click="$emit('input', 'new val')">{{ value }}</div>`,
- props: ['value'],
- }
- const vm = new Vue({
- components: { ChildComponent },
- data() {
- return {
- myVal: 'initial',
- }
- },
- template: `
- <div>
- <child-component v-model="myVal"></child-component>
- </div>
- `,
- }).$mount() as any
- expect(vm.$el.textContent).toContain('initial')
- expect(
- (deprecationData[DeprecationTypes.COMPONENT_V_MODEL].message as Function)(
- ChildComponent,
- ),
- ).toHaveBeenWarned()
- // Should work correctly
- const child = vm.$el.querySelector('div')
- child.click()
- await nextTick()
- expect(vm.myVal).toBe('new val')
- expect(vm.$el.textContent).toContain('new val')
- })
- })
|