spb/countryatlas
Public
TypeScript 57%
Python 38.6%
JavaScript 3.6%
CSS 0.6%
1import type { Metadata } from 'next';2import { Suspense } from 'react';3import { t } from '@/i18n';4import { isNotBuilt } from '@/lib/api';5import { apiAnalytics } from '@/lib/api-analytics';6import { routes } from '@/lib/site';7import type { PeersResponse } from '@/lib/types-analytics';8import { NotBuiltState } from '@/components/data/empty-state';9import { PageHeader } from '@/components/explore/page-header';10import { PeersView } from '@/components/peers/peers-view';1112export const revalidate = 900;13type SP = Record<string, string | string[] | undefined>;1415function slug(v: string | string[] | undefined): string | undefined {16 const s = (Array.isArray(v) ? v[0] : v) ?? '';17 return /^[a-z0-9][a-z0-9-]*$/.test(s) ? s : undefined;18}1920export async function generateMetadata({ searchParams }: { searchParams: Promise<SP> }): Promise<Metadata> {21 const sp = await searchParams;22 const custom = !!(slug(sp.x) || slug(sp.y) || sp.year || sp.method);23 return { title: t('peers.metaTitle'), description: t('peers.description'), alternates: { canonical: routes.peers() }, robots: custom ? { index: false, follow: true } : undefined };24}2526export default async function PeersPage({ searchParams }: { searchParams: Promise<SP> }) {27 const sp = await searchParams;28 const year = Number(Array.isArray(sp.year) ? sp.year[0] : sp.year);29 const method = (Array.isArray(sp.method) ? sp.method[0] : sp.method) === 'ols' ? 'ols' : 'theil-sen';30 let data: PeersResponse | null = null;31 try {32 data = await apiAnalytics.peers({ x: slug(sp.x), y: slug(sp.y), year: Number.isInteger(year) && year > 1800 ? year : null, method });33 } catch (e) {34 if (isNotBuilt(e)) return <NotBuiltState />;35 data = null;36 }37 return (38 <>39 <PageHeader title={t('peers.title')} lede={t('peers.lede')} />40 {!data ? (41 <p className="py-8 text-sm text-ink-3">{t('peers.unavailable')}</p>42 ) : (43 <Suspense fallback={null}>44 <PeersView data={data} />45 </Suspense>46 )}47 </>48 );49}50