TanStack Query

Фетч страницы статуса через TanStack Query — гайд useQuery

Получайте PulseAPI status-эндпоинт через useQuery. Кеш, refetch on focus, интервал-поллинг, SSE realtime — всё в типизированном React-хуке.

Три способа запустить страницу статуса для TanStack Query

Выберите нужный уровень контроля — zero-code, low-code или полный headless.

Хостед

Добавьте TanStack Query-эндпоинт, направьте CNAME на status.yourdomain.com — готово. 5 минут.

Headless

Через публичный API собрать свою UI прямо в TanStack Query-приложении. Полный контроль дизайна и брендинга.

Смотреть API

Встраиваемые бейджи

SVG-бейджи uptime и статуса в README или лендинг. Обновляются каждые 5 минут.

Вставьте этот health endpoint в своё TanStack Query-приложение

Скопируйте, вставьте, направьте PulseAPI на URL. 200 — здоров, 503 — деградация.

app/status/use-status-query.ts
import { useQuery } from '@tanstack/react-query'

interface StatusData {
  page: { title: string; customDomain: string | null }
  overallStatus: 'operational' | 'degraded' | 'down' | 'maintenance' | 'unknown'
  endpoints: Array<{
    id: string
    name: string
    status: string
    uptime24h: number
    avgResponseTime: number
  }>
}

export const useStatusQuery = (slug: string) =>
  useQuery<StatusData>({
    queryKey: ['status', slug],
    queryFn: async () => {
      const r = await fetch(`https://api.pulseapi.tech/status/${slug}`)
      if (!r.ok) throw new Error(`Status ${r.status}`)
      return r.json()
    },
    staleTime: 30_000,
    refetchInterval: 30_000,
    refetchOnWindowFocus: true,
  })

Установите staleTime и refetchInterval в 30 секунд в соответствии с нашим SSE heartbeat. Для realtime без polling сочетайте этот хук с /sse/status/:slug — на событиях патчите кеш через queryClient.setQueryData.

Что ломается в TanStack Query-приложениях и как это поймать

Устаревший статус на долгих вкладках

Дашборд, оставленный на ночь, показывает зелёный баннер — а прод лежит. refetchInterval + refetchOnWindowFocus держат кеш свежим.

Моргание неверного контента при ревалидации

placeholderData + keepPreviousData держит последний успешный статус на экране во время refetch — без моргания между "operational" и скелетоном.

Слишком много параллельных запросов из вложенных компонентов

Несколько компонентов с useStatusQuery запустили бы по запросу каждый — React Query дедуплицирует по queryKey, в воздухе на slug один fetch.

Headless-угол

Не нравится наша страница статуса? Соберите свою на TanStack Query.

Наш API отдаёт те же данные, что потребляет наша хостед-UI. Полная OpenAPI-спека на api.pulseapi.tech/docs.

components/StatusBanner.tsx — inline-баннер в приложении, когда PulseAPI сообщает о деградации или падении.
import { useStatusQuery } from './use-status-query'

export function StatusBanner({ slug }: { slug: string }) {
  const { data, isLoading, error } = useStatusQuery(slug)

  if (isLoading) return <div className="skeleton" />
  if (error) return null
  if (!data) return null
  if (data.overallStatus === 'operational') return null

  return (
    <a href={`https://${data.page.customDomain}`} className="banner">
      {data.overallStatus === 'down' ? 'Service disruption' : 'Degraded service'}
      {' — '}
      {data.endpoints.filter((e) => e.status !== 'operational').length} affected
    </a>
  )
}

Мониторинг TanStack Query — FAQ

Как совместить useQuery с SSE для realtime-обновлений?

В useEffect откройте EventSource на /sse/status/:slug и на каждое событие вызывайте queryClient.setQueryData(["status", slug], to merge event patches into the existing cache entry. Подписчики useQuery остаются в курсе без polling.

Работает с TanStack Query v4 и v5?

Оба. В v4 — cacheTime, в v5 переименовали в gcTime. isLoading в v5 — строго "первая загрузка"; для любого in-flight-индикатора используйте isPending + isFetching.

Можно префетчить статус на сервере через Next.js или Remix?

Да. Вызывайте queryClient.prefetchQuery в server component или loader, оберните дерево в HydrationBoundary (v5) или Hydrate (v4) с дегидратированным state. Хук useStatusQuery на первом рендере читает из гидратированного кеша — без моргания на клиенте.

Безопасно ли использовать org API-ключ в useQuery?

Нет — любой ключ в браузерном JS считается публичным. Публичному status-эндпоинту auth не нужен; org-API-ключи использовать только на сервере. Если auth нужен — проксируйте через backend-роут (/api/status) и обращайтесь к нему из useQuery.

Запустите мониторинг TanStack Query-приложения за 5 минут

Бесплатный тариф, без карты. Добавьте эндпоинт, получайте алерты о падениях.