Загрузка данных: функция load
Функция load в +page.js/+page.server.js загружает данные для страницы до её отрисовки и отдаёт их как проп data.
«Сначала данные, потом разметка.» Загрузчик гарантирует, что страница рендерится уже с готовыми данными — без мерцания пустого экрана.
Страницам почти всегда нужны данные: список статей, профиль пользователя, товары. SvelteKit предлагает аккуратный механизм — функцию load. Вы создаёте рядом с +page.svelte файл +page.js (или +page.server.js) и экспортируете из него load. То, что она вернёт, попадёт в страницу как проп data — уже к моменту рендера.
Есть два варианта загрузчика. +page.js — универсальный: код выполняется и на сервере (при первой загрузке), и на клиенте (при навигации). +page.server.js — только серверный: здесь безопасно обращаться к базе данных, использовать секретные ключи, читать файлы. Выбор зависит от того, нужен ли доступ к серверным ресурсам.
// src/routes/blog/[slug]/+page.server.js
export async function load({ params }) {
const post = await db.getPost(params.slug); // безопасно: только на сервере
if (!post) throw error(404, 'Статья не найдена');
return { post };
}<!-- src/routes/blog/[slug]/+page.svelte -->
<script>
let { data } = $props(); // то, что вернул load
</script>
<h1>{data.post.title}</h1>
<article>{data.post.body}</article>Загрузчик получает полезный контекст: params (динамические сегменты URL), fetch (умная обёртка, которая на сервере не делает лишних запросов), url и другое. Разделяйте данные грамотно: глобальные вещи (текущий пользователь) грузите в +layout.server.js, а специфичные для страницы — в её собственном загрузчике. Важно: возвращаемые данные должны быть сериализуемыми — при навигации они передаются с сервера на клиент.
Как это работает под капотом
При запросе SvelteKit сначала вызывает load, ждёт данные, затем рендерит страницу с этими данными. При клиентской навигации он вызывает load снова, но рендерит уже без перезагрузки страницы. Смоделируем этот порядок «загрузить, потом отрисовать».
// Порядок: load -> затем render с данными
async function load(params) {
// имитируем запрос к 'базе'
await new Promise(r => setTimeout(r, 0));
return { post: { title: 'Привет, SvelteKit', slug: params.slug } };
}
function render(data) {
console.log('рендер страницы с заголовком:', data.post.title);
}
(async () => {
const data = await load({ slug: 'hello' }); // СНАЧАЛА данные
render(data); // ПОТОМ разметка
})();Попробуй сам ▶ — вставь код в консоль браузера (F12 → Console) и нажми Enter, чтобы увидеть вывод.
запрос /blog/hello
|
v
load({ params }) -> данные { post }
|
v
+page.svelte получает data
|
v
HTML с готовыми данными -> браузерЧастые ошибки
- Обращаться к базе или секретам в
+page.js. Это попадёт в браузер; используйте+page.server.js. - Возвращать несериализуемое из
load. Функции и классы не переживут передачу на клиент. - Грузить всё в одном загрузчике. Глобальное — в лейаут, специфичное — в страницу.
Best practices
- Серверные ресурсы и секреты — только в
+page.server.js. - Используйте переданный
fetchвнутриload— он оптимизирован для SSR. - Бросайте
error(404, ...)для отсутствующих сущностей — SvelteKit покажет страницу ошибки.
Где брать данные: слои загрузки
На реальных проектах быстро становится ясно, что данные удобно загружать на разных уровнях. Глобальные вещи, нужные каждой странице, — кто сейчас залогинен, какие у него настройки, в какой теме показывать сайт — логично грузить один раз в лейаутном загрузчике +layout.server.js, и они станут доступны всем вложенным страницам. Специфичные для конкретной страницы данные — текст статьи, карточку товара, список комментариев — грузит её собственный load. Такое разделение избавляет от дублирующих запросов и держит код опрятным. Важно и правильно выбирать между универсальным и серверным загрузчиком: всё, что касается базы данных, секретных ключей или файловой системы, должно жить только в +page.server.js, иначе чувствительный код утечёт в браузер. Помните и про сериализуемость: данные из загрузчика при клиентской навигации передаются с сервера на клиент, поэтому возвращать оттуда функции или экземпляры классов нельзя. Освоив эти правила, вы будете загружать данные эффективно и безопасно.
Итог: load загружает данные до рендера и отдаёт их как проп data. +page.js работает на сервере и клиенте, +page.server.js — только на сервере, для безопасного доступа к ресурсам.