SPB Git forge
15commits 1branches 0releases
29.7 MBsize
maindefault branch
10 days agolast push
TypeScript 36.3% Python 31.8% Go 18% JavaScript 9.8% Shell 1.9% SQL 1.4% CSS 0.5%
3.4 KB · 73 lines tsx
Raw Blame History
1import type { Metadata } from 'next';2import Link from 'next/link';3import { LevelBadge, PNum, Section } from '@/components/ui/primitives';4import { apiGet } from '@/lib/api';5import { fmtInt, fmtPct } from '@/lib/format';6import { VendorIndicator } from '@/components/service/VendorIndicator';7import type { ServiceRow } from '@/lib/types';89export const dynamic = 'force-dynamic';10export const metadata: Metadata = { title: 'Services', description: 'Independent observation of major Internet services versus what their status pages declare.' };1112export default async function ServicesPage() {13  const { services } = await apiGet<{ services: ServiceRow[] }>('/api/v1/services');14  const sorted = [...services].sort((a, b) => b.pressure - a.pressure);15  return (16    <div className="pb-8">17      <header className="pt-6 pb-4">18        <p className="label">Index</p>19        <h1 className="mt-1 text-[26px] font-medium tracking-tight sm:text-[32px]">Services</h1>20        <p className="mt-1 text-[13px] text-ink-2">{fmtInt(services.length)} providers · what we observe from our probes next to what the vendor declares. The discrepancy is the valuable part.</p>21      </header>22      <Section>23        <div className="scroll-x -mx-3 px-3">24          <table className="tbl">25            <thead>26              <tr>27                <th>Service</th>28                <th className="hidden sm:table-cell">Category</th>29                <th className="r">Pressure</th>30                <th className="hidden md:table-cell">Level</th>31                <th className="r">Observed avail. 24h</th>32                <th className="r hidden sm:table-cell">Targets</th>33                <th className="hidden md:table-cell">Affected regions</th>34                <th>Vendor status</th>35              </tr>36            </thead>37            <tbody>38              {sorted.map((s) => {39                const discrepancy = s.affected_regions.length > 0 && s.vendor_status?.indicator === 'none';40                return (41                  <tr key={s.slug}>42                    <td>43                      <Link href={`/service/${s.slug}`} className="text-ink hover:text-accent">44                        {s.name}45                      </Link>46                      {discrepancy && <span className="ml-2 text-[10px] uppercase tracking-[0.1em] text-warn">discrepancy</span>}47                    </td>48                    <td className="hidden text-ink-2 sm:table-cell">{s.category}</td>49                    <td className="r">50                      <PNum value={s.pressure} className="text-[14px]" />51                    </td>52                    <td className="hidden md:table-cell">53                      <LevelBadge level={s.level} size="xs" />54                    </td>55                    <td className="num r" style={{ color: s.observed_availability_24h < 0.999 ? 'var(--p-elevated)' : 'var(--ink)' }}>56                      {fmtPct(s.observed_availability_24h, 2)}57                    </td>58                    <td className="num r hidden text-ink-2 sm:table-cell">{fmtInt(s.targets)}</td>59                    <td className="hidden text-ink-2 md:table-cell">{s.affected_regions.length ? s.affected_regions.join(', ') : '—'}</td>60                    <td>61                      <VendorIndicator v={s.vendor_status} />62                    </td>63                  </tr>64                );65              })}66            </tbody>67          </table>68        </div>69      </Section>70    </div>71  );72}73