SPB Git forge
28commits 1branches 0releases
7.7 MBsize
maindefault branch
10 days agolast push
Python 66.3% TypeScript 22.7% JavaScript 8.6% HTML 1.4% CSS 0.7%
4.0 KB · 72 lines tsx
Raw Blame History
1import type { Metadata } from 'next';2import { Columns } from '@/components/charts/bars';3import { Dot, LiveAgo } from '@/components/ui/live';4import { Container, Note, PageHeader, Stat, StatGrid, Unavailable } from '@/components/ui/section';5import { api, safe } from '@/lib/api';6import { fmtBytes, fmtDate, fmtDays, fmtInt, fmtPct } from '@/lib/format';78export const metadata: Metadata = { title: 'System status', description: 'Public aggregate health of the Company Atlas sensor network: sensors online, observations and events today, success rate and scheduler lag.' };9export const revalidate = 30;1011export default async function SystemPage() {12  const [sys, stats, hist] = await Promise.all([safe(api.system()), safe(api.stats()), safe(api.statsHistory(30))]);13  const ok = sys && (sys.success_rate_24h ?? 100) >= 90 && (sys.queue_lag_s ?? 0) < 600;14  return (15    <Container>16      <PageHeader17        eyebrow={18          <>19            <Dot pulse={!!sys} tone={sys ? (ok ? 'live' : 'warning') : 'danger'} /> System20          </>21        }22        title={sys ? (ok ? 'All systems observing' : 'Degraded — observing with reduced throughput') : 'Status unavailable'}23        lede="Aggregate health only (spec §130): no per-sensor or per-domain detail is published here. Individual sensor freshness is shown on each company’s Sources tab."24      />25      {!sys ? (26        <Unavailable what="System health" />27      ) : (28        <StatGrid cols={4}>29          <Stat label="Sensors online" value={fmtInt(sys.sensors_online)} hint={`${fmtInt(sys.sensors_failing)} failing`} />30          <Stat label="Observations today" value={fmtInt(sys.observations_today)} hint={sys.fetch_per_min !== null ? `${fmtInt(sys.fetch_per_min)} fetches / min` : undefined} />31          <Stat label="Events today" value={fmtInt(sys.events_today)} hint={`${fmtInt(sys.countries_covered)} countries covered`} />32          <Stat label="Success rate 24 h" value={fmtPct(sys.success_rate_24h, 1)} hint={sys.queue_lag_s !== null ? `queue lag ${fmtInt(sys.queue_lag_s)} s` : undefined} />33        </StatGrid>34      )}35      {sys && (36        <p className="mt-3 text-xs text-ink-3">37          Scheduler last tick <LiveAgo at={sys.scheduler_last_tick_at} tick={5000} /> · this page refreshes every 30 s on the server.38        </p>39      )}40      {stats && (41        <div className="mt-10">42          <p className="eyebrow mb-3">Dataset</p>43          <StatGrid cols={4}>44            <Stat label="Dataset age" value={fmtDays(stats.dataset_age_days)} hint={stats.dataset_started_at ? `since ${fmtDate(stats.dataset_started_at)}` : undefined} size="sm" />45            <Stat label="Companies · sensors" value={`${fmtInt(stats.companies)} · ${fmtInt(stats.sensors)}`} size="sm" />46            <Stat label="Observations · changes · events" value={`${fmtInt(stats.observations)} · ${fmtInt(stats.changes)} · ${fmtInt(stats.events)}`} size="sm" />47            <Stat label="Archive" value={fmtBytes(stats.archive?.bytes)} hint={`${fmtInt(stats.archive?.objects)} objects`} size="sm" />48          </StatGrid>49        </div>50      )}51      {hist && hist.items.length > 1 && (52        <div className="mt-10 grid gap-6 md:grid-cols-3">53          {(54            [55              ['observations', 'Observations / day'],56              ['changes', 'Changes / day'],57              ['events', 'Events / day'],58            ] as const59          ).map(([k, label]) => (60            <div key={k}>61              <p className="eyebrow">{label} · 30 d</p>62              <Columns values={hist.items.map((h) => h[k])} width={300} height={48} className="mt-2 h-auto w-full" ariaLabel={label} />63              <p className="tnum mt-1 text-xs text-ink-3">latest {fmtInt(hist.items[hist.items.length - 1]?.[k])}</p>64            </div>65          ))}66        </div>67      )}68      <Note className="mt-10">Each service exposes /health, /ready and /metrics internally; this page summarises them. “Last successfully checked” timestamps on company pages are the honest freshness signal for any single fact.</Note>69    </Container>70  );71}72