SEO и мета-теги: useHead и useSeoMeta
Поисковики и соцсети читают тег <title> и мета-теги в <head> страницы: по ним строится заголовок в выдаче и карточка ссылки. Nuxt выводит эти теги на сервере, поэтому их видят даже программы, которые не выполняют JavaScript. Задают теги функциями useHead и useSeoMeta.
Заголовок страницы
<!-- app/pages/about.vue -->
<script setup lang="ts">
useHead({
title: 'О блоге'
})
</script>Откройте /about — на вкладке браузера будет «О блоге». В исходном коде страницы появится <title>О блоге</title>.
Шаблон заголовка
Чтобы к каждому заголовку добавлялось имя сайта, задайте шаблон в app/app.vue:
<!-- app/app.vue -->
<script setup lang="ts">
useHead({
titleTemplate: (title) => (title ? `${title} — Мой блог` : 'Мой блог')
})
</script>Теперь вкладка покажет «О блоге — Мой блог», а у страниц без своего заголовка — просто «Мой блог».
Мета-теги для поиска и соцсетей
useSeoMeta задаёт описание и теги Open Graph — по ним соцсети и мессенджеры строят карточку ссылки:
<!-- app/pages/about.vue -->
<script setup lang="ts">
useSeoMeta({
title: 'О блоге',
description: 'Анна и Олег пишут о веб-разработке.',
ogTitle: 'О блоге',
ogDescription: 'Анна и Олег пишут о веб-разработке.',
ogImage: 'https://example.com/cover.png'
})
</script>Каждое свойство превращается в нужный тег, например ogTitle — в <meta property="og:title">. Редактор подсказывает имена свойств и не даст ошибиться в написании.
Теги из загруженных данных
На странице статьи заголовок берётся из ответа API. Передавайте функцию, чтобы тег обновлялся вместе с данными:
<!-- app/pages/posts/[id].vue -->
<script setup lang="ts">
const route = useRoute()
const { data: post } = await useFetch(() => `/api/posts/${route.params.id}`)
useSeoMeta({
title: () => post.value?.title,
description: () => post.value?.text.slice(0, 150)
})
</script>Откройте /posts/1 — на вкладке будет «Первый пост — Мой блог».
Теги для всего сайта
Общие теги, например язык страницы, задают в nuxt.config.ts:
// nuxt.config.ts
export default defineNuxtConfig({
app: {
head: {
htmlAttrs: { lang: 'ru' },
link: [{ rel: 'icon', href: '/favicon.ico' }]
}
}
})| Где | Что задавать |
|---|---|
nuxt.config.ts, app.head | Язык, иконка, общие теги |
app/app.vue | Шаблон заголовка |
| Страница | Заголовок, описание, Open Graph |
Частая ошибка
Написать title: post.value?.title без функции. Значение прочитается один раз при создании компонента. Если пользователь перейдёт с одной статьи на другую, заголовок вкладки останется прежним. Для данных, которые могут измениться, передавайте функцию: title: () => post.value?.title.