В Vue Router ключ meta предоставляет возможность хранить
дополнительную информацию о маршруте, которая не влияет на работу
маршрутизатора напрямую, но может быть использована для различных целей:
контроля доступа, отображения названий страниц или построения
навигационных элементов, таких как хлебные крошки.
metaМаршруты в Vue Router задаются объектами с полями path,
component и опциональными дополнительными свойствами. Ключ
meta обычно используется как объект с произвольными
данными:
import { createRouter, createWebHistory } from 'vue-router';
import Home from '@/views/Home.vue';
import About from '@/views/About.vue';
import Team from '@/views/Team.vue';
const routes = [
{
path: '/',
component: Home,
meta: { breadcrumb: 'Главная' }
},
{
path: '/about',
component: About,
meta: { breadcrumb: 'О компании' },
children: [
{
path: 'team',
component: Team,
meta: { breadcrumb: 'Команда' }
}
]
}
];
const router = createRouter({
history: createWebHistory(),
routes
});
export default router;
В этом примере для каждого маршрута определено свойство
breadcrumb внутри meta, которое будет
использоваться для отображения текущего пути в виде хлебных крошек.
Для построения хлебных крошек необходимо пройтись по массиву активных
маршрутов, который хранится в
router.currentRoute.value.matched. Каждый объект маршрута в
этом массиве содержит meta, что позволяет извлекать
название для каждой крошки.
import { computed } from 'vue';
import { useRoute } from 'vue-router';
export default {
setup() {
const route = useRoute();
const breadcrumbs = computed(() => {
return route.matched.map(r => ({
name: r.meta.breadcrumb || r.name,
path: r.path
}));
});
return { breadcrumbs };
}
};
Здесь breadcrumbs — это реактивный массив объектов,
содержащих name и path каждой крошки. При
изменении маршрута массив автоматически обновляется.
При работе с вложенными маршрутами важно учитывать, что путь
дочернего маршрута может быть относительным. В таких случаях для хлебных
крошек рекомендуется использовать свойство path из
matched, которое уже содержит полный путь:
const breadcrumbs = computed(() => {
return route.matched.map(r => ({
name: r.meta.breadcrumb || r.name,
path: r.path
}));
});
Такой подход гарантирует корректное построение ссылок даже для многоуровневых маршрутов.
Для маршрутов с параметрами (:id, :slug)
следует подставлять реальные значения из route.params:
const breadcrumbs = computed(() => {
return route.matched.map(r => {
let path = r.path;
Object.keys(route.params).forEach(key => {
path = path.replace(`:${key}`, route.params[key]);
});
return {
name: r.meta.breadcrumb || r.name,
path
};
});
});
Таким образом, крошки автоматически подставляют конкретные
идентификаторы или слаги, например: /about/team/42.
Для отображения хлебных крошек можно использовать простой цикл
v-for в Vue:
<template>
<nav aria-label="breadcrumb">
<ol class="breadcrumb">
<li
v-for="(crumb, index) in breadcrumbs"
:key="crumb.path"
:class="{ 'active': index === breadcrumbs.length - 1 }"
>
<router-link v-if="index !== breadcrumbs.length - 1" :to="crumb.path">
{{ crumb.name }}
</router-link>
<span v-else>{{ crumb.name }}</span>
</li>
</ol>
</nav>
</template>
<script setup>
import { computed } from 'vue';
import { useRoute } from 'vue-router';
const route = useRoute();
const breadcrumbs = computed(() => {
return route.matched.map(r => {
let path = r.path;
Object.keys(route.params).forEach(key => {
path = path.replace(`:${key}`, route.params[key]);
});
return {
name: r.meta.breadcrumb || r.name,
path
};
});
});
</script>
<style scoped>
.breadcrumb {
display: flex;
list-style: none;
padding: 0;
}
.breadcrumb li + li::before {
content: '/';
padding: 0 0.5rem;
}
.breadcrumb .active {
font-weight: bold;
}
</style>
Для мультиязычных приложений можно использовать meta в
сочетании с функцией перевода:
meta: { breadcrumb: t('breadcrumbs.home') }
Или динамически вычислять имя крошки через функцию в
meta:
meta: {
breadcrumb: route => `Пользователь ${route.params.id}`
}
В этом случае при построении массива крошек нужно проверять, является
ли breadcrumb функцией и вызывать её с текущим
маршрутом:
const breadcrumbs = computed(() => {
return route.matched.map(r => {
let name = typeof r.meta.breadcrumb === 'function'
? r.meta.breadcrumb(route)
: r.meta.breadcrumb || r.name;
let path = r.path;
Object.keys(route.params).forEach(key => {
path = path.replace(`:${key}`, route.params[key]);
});
return { name, path };
});
});
Использование meta в Vue Router позволяет строить гибкие
и динамичные хлебные крошки, поддерживающие вложенные маршруты,
динамические параметры и мультиязычные приложения. Комбинация
route.matched, route.params и
meta.breadcrumb обеспечивает простое и масштабируемое
решение для навигационных элементов.