# gt-next: General Translation Next.js SDK: Статическая генерация сайта URL: https://generaltranslation.com/ru/docs/next/guides/ssg.mdx --- title: Статическая генерация сайта description: Предварительно рендерьте локализованные страницы на этапе сборки для максимальной производительности --- ## Обзор Статическая генерация сайта (SSG) предварительно рендерит страницы на этапе сборки, создавая статические HTML-файлы, которые можно отдавать напрямую без серверной обработки. В сочетании с интернационализацией SSG создает предварительно отрендеренные версии для каждой локали. **Обратите внимание на следующие проблемы при настройке SSG:** * [Совместимость версий Next.js](#nextjs-version-compatibility) * [Страницы не генерируются статически](#pages-not-generating-statically) * [Ошибка времени выполнения в production: "DYNAMIC_SERVER_USAGE"](#production-runtime-error-dynamic_server_usage) * ["Export locale doesn't exist in target module"](#export-locale-doesnt-exist-in-target-module) * [Маршруты изображений метаданных (OG-изображения) завершаются ошибкой с `getLocale()`](#metadata-image-routes-og-images-fail-with-getlocale) *** ## Сетап ### Требования к настройке Чтобы включить SSG с GT, вам потребуется: 1. **App Router с маршрутизацией через middleware** — см. [руководство по middleware](/docs/next/guides/middleware) 2. **Пользовательская функция `getLocale`** — для определения локали при статическом рендеринге 3. **Отключить `getRegion`** — определение региона не поддерживается при статическом рендеринге 4. **Функция `generateStaticParams`** — для генерации статических параметров для каждой локали 5. **Файлы layout в директории `/[locale]`** — все файлы layout (обычно это `layout.tsx` и `page.tsx`) должны находиться в директории `/[locale]` ### Шаг 1: Настройте middleware Настройте middleware для динамических запросов (см. [руководство по настройке middleware](/docs/next/guides/middleware)): ```ts // proxy.ts (Next.js 16+) или middleware.ts (Next.js 15 и ниже) import { createNextMiddleware } from 'gt-next/middleware'; export default createNextMiddleware(); export const config = { matcher: ['/((?!api|static|.*\\..*|_next).*)'], }; ``` ### Шаг 2: Настройте определение локали и региона Создайте функции `getLocale` и `getRegion` для определения локали и региона при статическом рендеринге: #### Next.js 15.5+ ```ts // getLocale.ts import { locale } from 'next/root-params'; export default async function getLocale() { return await locale(); } ``` #### Next.js 15.1-15.4 ```ts // getLocale.ts import { unstable_rootParams } from 'next/server'; export default async function getLocale() { return (await unstable_rootParams())?.locale; } ``` ### Шаг 3: Отключите getRegion Так как во время статического рендеринга определение региона не поддерживается, переопределите функцию `getRegion`, чтобы она возвращала фиксированный регион. ```ts // getRegion.ts export default async function getRegion() { return undefined; } ``` ### Шаг 4: Настройте generateStaticParams Убедитесь, что [`generateStaticParams`](https://nextjs.org/docs/app/api-reference/functions/generate-static-params) настроен для ваших локалей. ```tsx title="page.tsx" import { getLocales } from 'gt-next/server'; export async function generateStaticParams() { return getLocales().map((locale) => ({ locale })); } export default async function Page() { ... } ``` ### Шаг 5: Переместите все файлы layout в директорию `/[locale]` Все файлы должны иметь доступ к локали пользователя через сегмент `/[locale]` в URL. Поэтому они должны находиться в директории `/[locale]`. Убедитесь, что вы переместили корневой файл layout в `/[locale]/layout.tsx`. *** ## Дополнительные настройки Если вы не хотите хранить `getLocale.ts` и `getRegion.ts` в корневой директории, можно указать другую директорию в файле `next.config.js`. ```js // next.config.js export default withGTConfig(nextConfig, { getLocalePath: './src/i18n/getLocale.ts', getRegionPath: './src/i18n/getRegion.ts', }); ``` ## Типичные проблемы [#common-issues] ### Совместимость версий Next.js В версиях ниже Next.js 15.1 нельзя получить доступ к параметрам URL-пути во время статической генерации. Чтобы использовать SSG с gt-next, вам нужно обновиться до Next.js 15.1 или более поздней версии. ### Страницы не генерируются при статической сборке Если ваши страницы не генерируются статически, убедитесь, что: * функции `getLocale` и `getRegion` настроены правильно ### Ошибка времени выполнения в production: "DYNAMIC_SERVER_USAGE" ``` ⨯ [Error: An error occurred in the Server Components render. The specific message is omitted in production builds to avoid leaking sensitive details. A digest property is included on this error instance which may provide additional details about the nature of the error.] { digest: 'DYNAMIC_SERVER_USAGE' } ``` Эта ошибка возникает, когда файлы `getLocale` или `getRegion` отсутствуют либо настроены неправильно. Еще раз проверьте, что [шаг 2](#step-2-define-locale-and-region-detection) и [шаг 3](#step-3-disable-getregion) выполнены. ### "Экспортируемая локаль отсутствует в целевом модуле" ``` ./getLocale.ts:2:1 Export locale doesn't exist in target module 1 | // getLocale.ts > 2 | import { locale } from 'next/root-params'; | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ 3 | export default async function getLocale() { 4 | return await locale(); 5 | } ``` Эта ошибка обычно возникает, если файл `layout.tsx`, `page.tsx` и т. п. находится вне директории `/[locale]`. Чтобы исправить проблему, убедитесь, что все файлы сегментов маршрута (обычно это `layout.tsx` и `page.tsx`) находятся внутри директории `/[locale]`. Во время SSG единственный способ определить локаль пользователя — по URL-пути. Поэтому, если попытаться выполнить файл `layout.tsx` вне директории `/[locale]`, возникнет ошибка, потому что у него нет доступа к этому корневому параметру. Здесь неочевидно то, что при рендеринге страницы рендерятся и все файлы `layout.tsx`, которые ее оборачивают. То есть вы могли включить SSG для файла `page.tsx`, который точно находится внутри директории `/[locale]`, но фактической причиной ошибки может быть другой файл `layout.tsx`, расположенный в другом месте. Мы настоятельно не рекомендуем так делать. При использовании SSG все файлы сегментов маршрута (кроме `not-found.tsx`) должны находиться внутри директории `/[locale]`. Но если без этого не обойтись, вам понадобятся два отдельных корневых файла layout: один внутри директории `/[locale]`, а другой — вне ее. В таком случае SSG будет выполнять только layout внутри директории `/[locale]`. Кроме того, вам может понадобиться изменить middleware, чтобы направлять запросы к сегментам, расположенным вне директории `/[locale]`, в обход middleware локализации. ### Маршруты изображений метаданных (OG-изображения) не работают с `getLocale()` ``` Error: Route /[locale]/.../opengraph-image used import('next/root-params').locale() inside a Route Handler. ``` Маршруты изображений метаданных в Next.js (`opengraph-image.tsx`, `twitter-image.tsx`) внутри представляют собой обработчики маршрутов, а `next/root-params` в обработчиках маршрутов не поддерживается. Это означает, что `getLocale()`, `getMessages()` и `getGT()` в этих случаях не будут работать. **Исправление:** Используйте `registerLocale()`, чтобы явно задать локаль в начале handler: ```tsx title="app/[locale]/opengraph-image.tsx" import { ImageResponse } from 'next/og'; import { registerLocale, getMessages, msg } from 'gt-next/server'; const HEADING = msg('Welcome to our site'); export default async function OGImage({ params, }: { params: Promise<{ locale: string }>; }) { const { locale } = await params; registerLocale(locale); const m = await getMessages(); return new ImageResponse( (
{m(HEADING)}
), { width: 1200, height: 630 } ); } ``` Это также относится к `twitter-image.tsx` и любым другим маршрутам изображений метаданных. *** ## Дополнительные материалы **Посмотрите в действии:** Ознакомьтесь с [примером приложения со Статической генерацией сайта](https://github.com/gt-examples/static-site-generation) — это рабочее демо; доступен [живой предпросмотр](https://static-site-generation.generaltranslation.dev). * Ознакомьтесь с [руководством по middleware](/docs/next/guides/middleware), которое требуется для маршрутизации по локалям * Ознакомьтесь с [примечаниями к выпуску](/devlog/gt-next_v6_10_0), если переходите с прежнего шаблона SSG * Пример приложения в monorepo можно посмотреть [здесь](https://github.com/generaltranslation/gt/tree/main/examples/next-ssg)