HTML 77.2%
TypeScript 10.5%
Python 9.6%
JavaScript 2.5%
1import type { Metadata } from 'next';2import Link from 'next/link';3import { ActiveFilters, type FacetGroup, Facets, FilterBar, ListingLayout } from '@/components/listing/filters';4import { BreadcrumbLd } from '@/components/meta/breadcrumb-ld';5import { DataTable, EmptyRow, Td, Th } from '@/components/ui/data-table';6import { EntityBadge } from '@/components/ui/badges';7import { EntityLink, QualityMark } from '@/components/ui/entity';8import { Hint } from '@/components/ui/hint';9import { Pagination, withParams } from '@/components/ui/pagination';10import { Container, PageHeader } from '@/components/ui/section';11import { Unavailable } from '@/components/ui/unavailable';12import { api, safe } from '@/lib/api';13import { fmtInt, num, titleCase } from '@/lib/format';14import { routes, SITE_NAME } from '@/lib/site';1516export const metadata: Metadata = {17 title: 'Organizations — companies, labs and universities building AI',18 description: 'Every organization in the atlas — companies, research labs, universities — with country, kind, canonical model count and papers, each attribute backed by a source.',19 alternates: { canonical: '/companies' },20};21export const revalidate = 300;2223type SP = Record<string, string | undefined>;24const LIMIT = 50;25const KEYS = ['q', 'country', 'kind', 'sort', 'order', 'offset'] as const;26const SORTS = [27 { value: 'models', label: 'Most models' },28 { value: 'name', label: 'Name' },29 { value: 'updated', label: 'Recently updated' },30 { value: 'quality', label: 'Data quality' },31];3233export default async function CompaniesPage({ searchParams }: { searchParams: Promise<SP> }) {34 const sp = await searchParams;35 const current: Record<string, string | undefined> = {};36 for (const k of KEYS) if (sp[k]) current[k] = sp[k];37 const offset = Math.max(0, Number(current.offset) || 0);38 const sort = current.sort ?? 'models';39 const [page, stats] = await Promise.all([safe(api.companies({ ...current, sort, limit: LIMIT, offset, facets: 1 })), safe(api.stats())]);40 const href = (patch: Record<string, string | number | undefined | null>) => withParams('/companies', current, patch);41 const facetGroups: FacetGroup[] = [42 { key: 'country', label: 'Country', items: (page?.facets?.countries ?? []).map((x) => ({ value: x.value, count: x.count })) },43 { key: 'kind', label: 'Kind', items: (page?.facets?.kinds ?? []).map((x) => ({ value: x.value, label: titleCase(x.value), count: x.count })) },44 ];45 const sortHref = (s: string) => href({ sort: s, order: sort === s && current.order !== 'asc' ? 'asc' : undefined, offset: undefined });46 const definition = stats?.definitions?.organizations_total ?? 'Organizations = companies, labs and universities (entity types company, organization, lab, university); merged duplicates excluded.';47 const SortTh = ({ s, children, num: n }: { s: string; children: React.ReactNode; num?: boolean }) => (48 <Th num={n} aria-sort={sort === s ? (current.order === 'asc' ? 'ascending' : 'descending') : undefined}>49 <Link href={sortHref(s)} className={sort === s ? 'text-ink' : 'hover:text-ink'}>50 {children}51 {sort === s && <span aria-hidden> {current.order === 'asc' ? '↑' : '↓'}</span>}52 </Link>53 </Th>54 );5556 return (57 <Container wide>58 <BreadcrumbLd items={[{ name: SITE_NAME, href: '/' }, { name: 'Organizations', href: '/companies' }]} />59 <PageHeader60 eyebrow="Organizations"61 title="Companies, labs & universities"62 lede="Who builds, serves and studies AI. Model counts are canonical releases; paper counts are stated publisher relations. Every organization page separates corporate news from model events."63 aside={64 page ? (65 <p className="tnum flex items-center gap-1 text-sm text-ink-3">66 {fmtInt(page.total)} organizations <span className="text-ink-3">(companies, labs, universities)</span>67 <Hint text={definition} align="right" />68 </p>69 ) : undefined70 }71 >72 <FilterBar73 action="/companies"74 className="mt-6"75 resetHref={routes.companies()}76 fields={[77 { kind: 'text', name: 'q', label: 'Name', value: current.q, placeholder: 'e.g. Anthropic' },78 { kind: 'text', name: 'country', label: 'Country (ISO-2)', value: current.country, placeholder: 'US, FR, CN…' },79 ...(current.kind ? [{ kind: 'hidden' as const, name: 'kind', value: current.kind }] : []),80 ]}81 sort={{ value: sort, options: SORTS }}82 />83 <ActiveFilters current={current} labels={{ q: 'query', country: 'country', kind: 'kind' }} makeHref={(p) => href(p)} className="mt-3" />84 </PageHeader>85 <div className="pb-16">86 <ListingLayout facets={<Facets groups={facetGroups} current={current} makeHref={(p) => href(p)} />}>87 {!page ? (88 <Unavailable what="Organizations" />89 ) : (90 <>91 <DataTable caption="Organizations">92 <thead>93 <tr>94 <SortTh s="name">Organization</SortTh>95 <Th>Type</Th>96 <Th>Country</Th>97 <Th>Kind</Th>98 <Th>Founded</Th>99 <SortTh s="models" num>100 Models101 </SortTh>102 <Th num>Papers</Th>103 <SortTh s="quality" num>104 Quality105 </SortTh>106 </tr>107 </thead>108 <tbody>109 {page.items.length === 0 && <EmptyRow cols={8}>No organizations match these filters.</EmptyRow>}110 {page.items.map((c) => {111 const a = c.attributes ?? {};112 return (113 <tr key={c.id}>114 <Td primary>115 <EntityLink e={c} />116 {c.description && <span className="block max-w-md truncate text-xs text-ink-3">{c.description}</span>}117 </Td>118 <Td label="Type">119 <EntityBadge type={c.entity_type} small />120 </Td>121 <Td label="Country" className="mono text-ink-2">{typeof a.country === 'string' ? a.country : <span className="text-ink-3">—</span>}</Td>122 <Td label="Kind" className="text-ink-2">{typeof a.org_kind === 'string' ? titleCase(a.org_kind) : <span className="text-ink-3">—</span>}</Td>123 <Td label="Founded" className="tnum text-ink-2">{a.founded ? String(a.founded).slice(0, 4) : <span className="text-ink-3">—</span>}</Td>124 <Td num label="Models" className="tnum">125 {num(c.model_count) ? (126 <Link href={`/models?org=${encodeURIComponent(c.slug)}`} className="hover:text-accent">127 {fmtInt(c.model_count)}128 </Link>129 ) : (130 <span className="text-ink-3">0</span>131 )}132 </Td>133 <Td num label="Papers" className="tnum">{num(c.paper_count) ? fmtInt(c.paper_count) : <span className="text-ink-3">0</span>}</Td>134 <Td num label="Quality">135 <QualityMark q={c.quality?.score} />136 </Td>137 </tr>138 );139 })}140 </tbody>141 </DataTable>142 <Pagination total={page.total} limit={LIMIT} offset={offset} makeHref={(o) => href({ offset: o || undefined })} className="mt-4" />143 </>144 )}145 </ListingLayout>146 </div>147 </Container>148 );149}150