Новый ментальный подход к кэшированию
В версии 16 модель кэширования в Next.js кардинально изменилась: вместо привязки к страницам теперь кэш привязывается к отдельным запросам fetch. Каждый вызов может работать в одном из трёх режимов – статическом с пере‑валидацией, полностью динамическом или гибридном, где кэшируемый результат помечается тегами. Такая декомпозиция упрощает управление данными, делает их более предсказуемыми и масштабируемыми.
Управление кэшем через fetch
Статический кэш с пере‑валидацией
По умолчанию в продакшене запрос fetch кэшируется. Чтобы явно задать период пере‑валидации, достаточно добавить объект next:
const res = await fetch('https://api.example.com/posts', {
next: { revalidate: 60 } // обновление каждые 60 секунд
});
Такой запрос будет храниться в кэше и автоматически обновляться раз в минуту, что полностью заменяет старый ISR‑паттерн, но с более точным контролем.
Полностью динамический запрос
Если данные меняются слишком часто или зависят от конкретного пользователя, кэшировать их не имеет смысла. В этом случае применяется параметр cache: 'no-store':
const res = await fetch('https://api.example.com/user/profile', {
cache: 'no-store' // отключение кэширования
});
Запрос будет отдаваться каждый раз заново, гарантируя актуальность информации в личных кабинетах, аналитических панелях и прочих сценариях, где важна свежесть данных.
Теги кэша: гибкая инвалидация
Новый механизм тегов позволяет группировать кэшированные запросы и инвалидировать их пакетно. Тег присваивается в параметрах next:
const res = await fetch('https://api.example.com/posts', {
next: { tags: ['posts'] }
});
Любой запрос, помеченный тегом posts, может быть очищен одной командой, без необходимости знать конкретные URL. Это особенно полезно при изменении контента: после публикации новой статьи достаточно вызвать инвалидацию тега posts, и все страницы, использующие этот запрос, получат обновлённые данные при следующем рендере.
Инвалидация тегов в реальном времени
Для принудительного сброса кэша используется API revalidateTag:
import { revalidateTag } from 'next/cache';
export async function POST(request) {
// После изменения поста в базе
await revalidateTag('posts');
return new Response('Cache cleared');
}
Вызов можно разместить в веб‑хуке CMS, в админ‑панели или в любой сервер‑функции, где происходит изменение данных. Это обеспечивает мгновенную консистентность между источником данных и пользовательским интерфейсом.
Запросы по требованию: on‑demand revalidation
Иногда требуется обновить кэш только после определённого события, а не по фиксированному таймеру. Для этого служит функция revalidatePath:
import { revalidatePath } from 'next/cache';
export async function POST(request) {
// Обновление конкретного пути после изменения
await revalidatePath('/blog');
return new Response('Page revalidated');
}
revalidatePath принудительно пере‑генерирует указанный путь, используя актуальные запросы fetch. Это удобно в сценариях, где контент меняется нерегулярно, но необходимо гарантировать его свежесть на странице сразу после изменения.
Режим черновика (Draft Mode) для превью
Для редакторов и контент‑менеджеров важен механизм предварительного просмотра изменений без публикации. Next.js 16 вводит draft mode, который переключает приложение в режим, где все запросы fetch работают в динамическом режиме, игнорируя кэш:
import { draftMode } from 'next/headers';
export async function GET(request) {
const { isEnabled, enable, disable } = draftMode();
if (!isEnabled) {
// Включаем черновой режим для текущей сессии
enable();
}
// Дальнейшие запросы будут без кэша
const res = await fetch('https://api.example.com/draft-posts', {
cache: 'no-store'
});
const data = await res.json();
return new Response(JSON.stringify(data));
}
Черновой режим хранится в cookies, поэтому пользователь может перемещаться по сайту, получая актуальные, но ещё непубличные данные. После выхода из режима кэш снова начинает работать согласно заданным правилам.
Практические паттерны для продакшена
-
Статический контент с тегами – для публичных страниц (список статей, каталог товаров) используйте
fetchсrevalidateиtags. Теги позволяют быстро сбрасывать кэш после массовых обновлений. -
Динамический пользовательский контент – в личных кабинетах и аналитических дашбордах применяйте
cache: 'no-store'. При этом можно комбинировать сnext: { tags: [...] }для кэширования только общих частей (например, справочных данных). -
Инвалидация через веб‑хуки – настройте CMS так, чтобы при публикации/удалении записи вызывался эндпоинт, который использует
revalidateTag. Это устраняет задержку в несколько минут, характерную для таймерной пере‑валидации. -
Пакетная пере‑генерация – при крупном обновлении каталога товаров вызывайте
revalidatePathдля всех затронутых роутов. Это гарантирует, что страницы будут обновлены в момент, когда пользователь их откроет. -
Preview‑режим – включайте
draft modeтолько для авторизованных редакторов. При работе с черновиками отключайте кэш, чтобы любые изменения сразу отображались в интерфейсе без необходимости публикации.
Эти подходы позволяют построить надёжную систему кэширования, где каждый запрос контролируется явно, а инвалидация происходит предсказуемо и без «заплесневелых» страниц. Next.js 16 предоставляет гибкие инструменты, которые при правильном использовании устраняют неопределённость в работе с данными и делают процесс разработки более продуктивным.