Загрузка данных

Экспортируйте функцию data(), и её результат появится как ctx.data в вашей функции рендеринга. Она выполняется во время сборки и на каждый запрос в сервере разработки.

import { html, body, h1 } from 'javascript-to-html'

export async function data({ params, dev }) {
  const res = await fetch(`https://api.example.com/posts/${params.slug}`)
  return await res.json()
}

export default ({ data }) =>
  html(
    body(
      h1(data.title),
      data.body,
    ),
  )

fetchWithCache

Собираете много страниц с одного API? Импортируйте fetchWithCache из sitelo:

import { fetchWithCache } from 'sitelo'

export async function data({ params }) {
  const res = await fetchWithCache(
    `https://api.example.com/posts/${params.slug}`,
    { /* обычные параметры fetch */ },
    { maxAge: 3600 }
  )
  return { post: await res.json() }
}

Параметры

Режимы кэша

По умолчанию кэшируются только GET-запросы (передайте cacheKey, чтобы кэшировать другие методы). Ответы с ошибками не кэшируются никогда.

Локальные JSON-файлы

Нет API? Держите контент в репозитории в виде JSON и читайте его через sitelo/data.

data/
├─ site.json
└─ posts/
   ├─ hello-world.json
   └─ why-static.json
import { readJsonCollection } from 'sitelo/data'

const posts = () => readJsonCollection('data/posts', { sort: '-date' })

export async function generateStaticParams() {
  return (await posts()).map((post) => ({ slug: post.slug }))
}

export async function data({ params }) {
  return (await posts()).find((post) => post.slug === params.slug)
}

export default ({ data }) => `
  <html><body>
    <h1>${data.title}</h1>
    <time datetime="${data.date}">${data.date}</time>
    ${data.body}
  </body></html>
`

Относительные пути разрешаются от корня проекта, поэтому data/posts означает одно и то же, откуда бы вы ни запускали CLI. readJson возвращает один разобранный файл; readJsonCollection возвращает массив записей, у каждой есть slug — из каталога .json-файлов (по файлу на запись, slug из имени файла) или из одного файла с массивом записей либо объектом, ключи которого — слаги.

// data/posts/hello-world.json  ->  { slug: 'hello-world', ... }
await readJsonCollection('data/posts')

// data/posts.json: [{ "slug": "hello-world", ... }]
// data/posts.json: { "hello-world": { ... } }
await readJsonCollection('data/posts.json')

// data/site.json
await readJson('data/site.json')

Параметры коллекции

Чтение запоминается по файлу, поэтому сборка из 500 страниц разбирает каждый файл один раз. Dev-сервер вместо этого сверяет mtime и перезагружает страницу, когда меняется прочитанный JSON-файл. Повторяющиеся слаги, отсутствующие файлы и некорректный JSON останавливают сборку — с указанием пути.