Статическая генерация сайтов (Static Site Generation - SSG) в Nuxt
Статическая генерация сайтов (SSG) - это режим развертывания Nuxt, при котором все необходимые HTML-файлы генерируются во время сборки проекта. В отличие от Server-Side Rendering (SSR), где HTML генерируется по запросу клиента, статические сайты уже готовы к отдаче браузеру без необходимости выполнять какой-либо серверный код.
Преимущества SSG
- Высокая производительность: Статические файлы очень быстро загружаются браузером, так как нет задержки, связанной с генерацией HTML на сервере.
- Улучшенное SEO: Поисковые боты могут легко индексировать предварительно сгенерированный HTML-контент.
- Повышенная безопасность: Отсутствие серверной логики снижает поверхность атаки и устраняет многие распространенные уязвимости.
- Простое и дешевое развертывание: Статические сайты можно размещать на CDN (Content Delivery Network) или на любом статическом хостинге, что обычно дешевле и проще, чем обслуживание Node.js сервера.
- Отличный UX: Быстрая первоначальная загрузка страницы обеспечивает лучший пользовательский опыт.
Как работает SSG в Nuxt
При сборке проекта в режиме SSG (nuxt generate), Nuxt проходит по всем вашим страницам (определенным в каталоге pages) и генерирует соответствующий HTML-файл для каждого маршрута. Если ваши страницы зависят от динамических данных, Nuxt предоставляет механизмы для предварительной генерации этих данных во время сборки.
Настройка SSG
Чтобы использовать SSG, убедитесь, что в вашем файле nuxt.config.js установлен режим static:
export default {
target: 'static', // Указываем Nuxt, что нужно генерировать статический сайт
// ... другие настройки
}Затем для сборки статического сайта выполните команду:
npm run generate
# или
yarn generateNuxt создаст каталог dist/ с вашим статическим сайтом, готовым к развертыванию.
Предварительная генерация динамических маршрутов
Если у вас есть страницы с динамическими маршрутами (например, /posts/:id), Nuxt необходимо знать, для каких конкретных значений :id нужно сгенерировать HTML-файлы. Для этого используется хук asyncData или fetch в ваших страницах.
Пример с asyncData:
Предположим, у вас есть страница /posts/_id.vue, которая отображает информацию о посте с определенным ID. Вы можете предварительно сгенерировать HTML для нескольких постов следующим образом:
<template>
<div>
<h1>{{ post.title }}</h1>
<p>{{ post.body }}</p>
</div>
</template>
<script>
export default {
async asyncData({ $axios, params, error }) {
try {
const { data: post } = await $axios.$get(`/api/posts/${params.id}`);
return { post };
} catch (e) {
error({ statusCode: 404, message: 'Пост не найден' });
}
},
}
</script>Чтобы Nuxt знал, для каких id генерировать страницы, вам нужно предоставить функцию generate.routes в nuxt.config.js:
export default {
target: 'static',
modules: ['@nuxtjs/axios'],
generate: {
async routes() {
const { data: posts } = await this.$axios.$get('/api/posts');
return posts.map(post => `/posts/${post.id}`);
},
},
// ... другие настройки
}В этом примере generate.routes делает запрос к API для получения списка всех постов и затем возвращает массив маршрутов для предварительной генерации (/posts/1, /posts/2, и т.д.).
Пример с fetch:
<template>
<div>
<h1>{{ post.title }}</h1>
<p>{{ post.body }}</p>
</div>
</template>
<script>
export default {
data() {
return {
post: null,
loading: true,
error: null,
};
},
async fetch() {
try {
this.post = await this.$axios.$get(`/api/posts/${this.$route.params.id}`);
} catch (e) {
this.error = 'Пост не найден';
} finally {
this.loading = false;
}
},
};
</script>
<script setup>
import { useAsyncData } from '#app';
const route = useRoute();
const { data: post, pending: loading, error } = useAsyncData(
'post',
() => $fetch(`/api/posts/${route.params.id}`)
);
</script>В nuxt.config.js функция generate.routes остается аналогичной примеру с asyncData.
Получение данных во время сборки
Как вы видели в примерах выше, для предварительной генерации страниц с динамическими данными часто требуется получать эти данные во время сборки. Nuxt предоставляет доступ к различным инструментам и контексту внутри asyncData и fetch, а также в функции generate.routes в nuxt.config.js, включая $axios (если установлен модуль @nuxtjs/axios) и другие полезные утилиты.
Особенности SSG
- API-запросы во время сборки: Любые API-запросы, выполняемые в
asyncData,fetchилиgenerate.routes, происходят во время сборки, а не на стороне клиента при каждом посещении страницы. - Интерактивность на стороне клиента: Хотя HTML генерируется статически, вы все равно можете добавлять интерактивность на стороне клиента с помощью Vue.js.
- Динамические данные после загрузки: Если вам нужны динамические данные, которые часто обновляются, вы можете подгружать их на стороне клиента после первоначальной загрузки статической страницы.
Когда использовать SSG
- Блоги и портфолио: Сайты с относительно статичным контентом, который редко меняется.
- Документация: Сайты с большим количеством текстового контента.
- Лендинговые страницы: Сайты, ориентированные на маркетинг и SEO.
- Небольшие и средние веб-сайты: Большинство сайтов, где контент не требует постоянного обновления в реальном времени.
Ограничения SSG
- Сложность с часто обновляемым контентом: Если ваш контент обновляется очень часто, перестройка и повторное развертывание всего сайта может быть неэффективным. В таких случаях может лучше подойти SSR или гибридный подход.
- Время сборки: Для очень больших сайтов с большим количеством динамических маршрутов время сборки может значительно увеличиться.
Заключение
Статическая генерация сайтов (SSG) в Nuxt - это отличный способ создания быстрых, безопасных и SEO-дружественных веб-сайтов. Правильное использование nuxt generate и механизмов предварительной генерации данных позволяет создавать статические сайты даже с динамическим контентом, обеспечивая превосходный пользовательский опыт и простое развертывание.