Встроенные директивы Vue (v-if, v-show,
v-for, v-model, v-bind,
v-on, v-slot и другие) являются
фундаментальной частью декларативного шаблонного синтаксиса. При
тестировании компонентов через Vue Test Utils они не тестируются
напрямую как отдельные сущности, а проверяются через их влияние
на DOM, состояние компонента и пользовательское поведение.
Ключевой принцип: в тестах проверяется результат работы директивы, а не факт её использования.
v-ifДиректива v-if управляет условным рендерингом и
физически добавляет или удаляет элементы из DOM.
Компонент:
<template>
<div>
<p v-if="visible">Текст</p>
</div>
</template>
<script>
export default {
data() {
return { visible: false }
}
}
</script>
Тест:
import { mount } from '@vue/test-utils'
import Component from '@/Component.vue'
test('v-if скрывает и показывает элемент', async () => {
const wrapper = mount(Component)
expect(wrapper.find('p').exists()).toBe(false)
await wrapper.setData({ visible: true })
expect(wrapper.find('p').exists()).toBe(true)
})
Ключевые моменты:
exists() — основной метод для проверки
v-ifawait)v-showv-show не удаляет элемент из DOM, а
управляет CSS-свойством display.
Компонент:
<p v-show="visible">Текст</p>
Тест:
test('v-show управляет display', async () => {
const wrapper = mount(Component)
const p = wrapper.find('p')
expect(p.exists()).toBe(true)
expect(p.isVisible()).toBe(false)
await wrapper.setData({ visible: true })
expect(p.isVisible()).toBe(true)
})
Отличие от v-if:
isVisible()v-forv-for генерирует списки элементов на основе массива или
объекта.
Компонент:
<ul>
<li v-for="item in items" :key="item.id">
{{ item.name }}
</li>
</ul>
Тест:
test('v-for рендерит список', () => {
const wrapper = mount(Component, {
data() {
return {
items: [
{ id: 1, name: 'A' },
{ id: 2, name: 'B' }
]
}
}
})
const items = wrapper.findAll('li')
expect(items).toHaveLength(2)
expect(items[0].text()).toBe('A')
expect(items[1].text()).toBe('B')
})
Практика:
findAllkey не тестируется напрямуюv-bindv-bind динамически связывает атрибуты, классы и
стили.
Компонент:
<button :disabled="isDisabled">Кнопка</button>
Тест:
test('v-bind устанавливает атрибуты', async () => {
const wrapper = mount(Component, {
data() {
return { isDisabled: false }
}
})
const button = wrapper.find('button')
expect(button.attributes('disabled')).toBeUndefined()
await wrapper.setData({ isDisabled: true })
expect(button.attributes('disabled')).toBeDefined()
})
Для классов:
<div :class="{ active: isActive }"></div>
expect(wrapper.find('div').classes()).not.toContain('active')
v-onv-on связывает события с методами компонента.
Компонент:
<button @click="increment">+</button>
Тест:
test('v-on вызывает метод', async () => {
const wrapper = mount(Component)
await wrapper.find('button').trigger('click')
expect(wrapper.vm.count).toBe(1)
})
Подходы:
v-modelv-model — синтаксический сахар для :value +
@input (или других событий).
Компонент:
<input v-model="text" />
Тест:
test('v-model обновляет data', async () => {
const wrapper = mount(Component)
const input = wrapper.find('input')
await input.setValue('hello')
expect(wrapper.vm.text).toBe('hello')
})
Обратная проверка:
await wrapper.setData({ text: 'world' })
expect(input.element.value).toBe('world')
Важно:
setValue, а не
trigger('input')v-modelv-slotСлоты — механизм передачи разметки в дочерние компоненты.
Компонент:
<slot name="header"></slot>
Тест:
mount(Component, {
slots: {
header: '<h1>Заголовок</h1>'
}
})
Проверка:
expect(wrapper.find('h1').text()).toBe('Заголовок')
Для scoped slots:
slots: {
default: ({ value }) => `<span>${value}</span>`
}
Встроенные директивы:
Пользовательские директивы:
global.directivesВстроенные директивы никогда не мокаются и не подменяются.
Все директивы, влияющие на DOM, работают в рамках реактивного цикла Vue.
Обязательные правила:
awaitsetData, setProps,
trigger — асинхронныПример ошибки:
wrapper.setData({ visible: true })
expect(wrapper.find('p').exists()).toBe(true) // ❌
Корректно:
await wrapper.setData({ visible: true })
Правильный фокус:
Неправильный фокус:
v-if в шаблонеВстроенные директивы Vue не являются объектами тестирования — они являются механизмами, корректность которых подтверждается через наблюдаемое поведение компонента.