From 541251f3954d8d5ccb361f76c8c3658181eea40b Mon Sep 17 00:00:00 2001 From: Kjell Kind Date: Tue, 20 Oct 2026 19:28:35 +0200 Subject: [PATCH] feat: link about page contributors to their /dev/null profile Contributors who are on /dev/null now link to their profile and show their profile card on hover. They are found by their GitHub account, so a rename on either side keeps the right link. Everyone else still links to GitHub. Co-Authored-By: Claude Opus 5.5 --- app/Http/Controllers/AboutController.php | 7 +- app/Queries/ContributorsQuery.php | 88 +++++++++++++++++ resources/js/lib/about.ts | 54 +---------- resources/js/pages/about/show.tsx | 95 +++++++++++++------ .../Controllers/AboutControllerTest.php | 10 ++ 5 files changed, 171 insertions(+), 83 deletions(-) create mode 100644 app/Queries/ContributorsQuery.php diff --git a/app/Http/Controllers/AboutController.php b/app/Http/Controllers/AboutController.php index 98b461175..c12d0628c 100644 --- a/app/Http/Controllers/AboutController.php +++ b/app/Http/Controllers/AboutController.php @@ -4,15 +4,18 @@ namespace App\Http\Controllers; +use App\Queries\ContributorsQuery; use App\Services\PageMetadata; use Inertia\Inertia; use Inertia\Response; final readonly class AboutController { - public function show(PageMetadata $metadata): Response + public function show(PageMetadata $metadata, ContributorsQuery $contributors): Response { - return Inertia::render('about/show')->withViewData(['preview' => $metadata->page( + return Inertia::render('about/show', [ + 'contributors' => $contributors->get(...), + ])->withViewData(['preview' => $metadata->page( 'About - /dev/null', 'How /dev/null was built in the open: from the first commit on stream to the developers who joined and the people who shipped it.', route('about.show'), diff --git a/app/Queries/ContributorsQuery.php b/app/Queries/ContributorsQuery.php new file mode 100644 index 000000000..99ac35dee --- /dev/null +++ b/app/Queries/ContributorsQuery.php @@ -0,0 +1,88 @@ + + */ + public function get(): array + { + $contributors = $this->contributors(); + + $usernames = User::query() + ->whereIn('github_id', array_column($contributors, 'github_id')) + ->get() + ->mapWithKeys(fn (User $user): array => [$user->github_id => $user->username]); + + return array_map(fn (array $contributor): array => [ + 'login' => $contributor['login'], + 'commits' => $contributor['commits'], + 'username' => $usernames->get($contributor['github_id']), + ], $contributors); + } + + /** + * Everyone with a commit on production, most commits first, by GitHub login and account. Bots and agents are left + * out. + * + * @return list + */ + private function contributors(): array + { + return [ + ['login' => 'xHeaven', 'github_id' => '14284867', 'commits' => 199], + ['login' => 'nunomaduro', 'github_id' => '5457236', 'commits' => 176], + ['login' => 'mnapoli', 'github_id' => '720328', 'commits' => 61], + ['login' => 'brendt', 'github_id' => '6905297', 'commits' => 42], + ['login' => 'simonhamp', 'github_id' => '31628', 'commits' => 18], + ['login' => 'paulinevos', 'github_id' => '5345273', 'commits' => 16], + ['login' => 'jubianchi', 'github_id' => '327237', 'commits' => 16], + ['login' => 'MrPunyapal', 'github_id' => '53343069', 'commits' => 15], + ['login' => 'sadiqk2', 'github_id' => '88760696', 'commits' => 8], + ['login' => 'camilleislasse', 'github_id' => '34024380', 'commits' => 6], + ['login' => 'hbenabdallah', 'github_id' => '63171491', 'commits' => 5], + ['login' => 'vtlxx', 'github_id' => '112337985', 'commits' => 5], + ['login' => 'robelsust', 'github_id' => '12664097', 'commits' => 4], + ['login' => 'HelgeSverre', 'github_id' => '1089652', 'commits' => 4], + ['login' => 'SanderMuller', 'github_id' => '9074391', 'commits' => 3], + ['login' => 'MaximeGoncalves', 'github_id' => '35679360', 'commits' => 3], + ['login' => 'mathiasonea', 'github_id' => '9391581', 'commits' => 3], + ['login' => 'fernandofreamunde', 'github_id' => '3598030', 'commits' => 3], + ['login' => 'mon4ssi', 'github_id' => '4429864', 'commits' => 2], + ['login' => 'hbenjacquet', 'github_id' => '244774096', 'commits' => 2], + ['login' => 'Akiyo974', 'github_id' => '123602948', 'commits' => 2], + ['login' => 'Chemaclass', 'github_id' => '5256287', 'commits' => 2], + ['login' => 'eznix86', 'github_id' => '26553194', 'commits' => 2], + ['login' => 'BENNIEV-ZA', 'github_id' => '33395137', 'commits' => 2], + ['login' => 'ahosker', 'github_id' => '346166', 'commits' => 2], + ['login' => 'eramitgupta', 'github_id' => '72160684', 'commits' => 1], + ['login' => 'utsavsomaiya', 'github_id' => '96036522', 'commits' => 1], + ['login' => 'tooinfinity', 'github_id' => '51855906', 'commits' => 1], + ['login' => 'murrant', 'github_id' => '39462', 'commits' => 1], + ['login' => 'RobinMalfait', 'github_id' => '1834413', 'commits' => 1], + ['login' => 'prateekbhujel', 'github_id' => '13213140', 'commits' => 1], + ['login' => 'ondrejmirtes', 'github_id' => '104888', 'commits' => 1], + ['login' => 'lazarospsa', 'github_id' => '37215838', 'commits' => 1], + ['login' => 'kachelle', 'github_id' => '33377566', 'commits' => 1], + ['login' => 'kadirtikil', 'github_id' => '92791650', 'commits' => 1], + ['login' => 'jjaybrown', 'github_id' => '477626', 'commits' => 1], + ['login' => 'GTS-MEGHNI', 'github_id' => '47923380', 'commits' => 1], + ['login' => 'faissaloux', 'github_id' => '60013703', 'commits' => 1], + ['login' => 'fabpl', 'github_id' => '6574025', 'commits' => 1], + ['login' => 'danielh-official', 'github_id' => '49914607', 'commits' => 1], + ['login' => 'chrisgocode', 'github_id' => '96142828', 'commits' => 1], + ['login' => 'AmanuelLegese', 'github_id' => '24702768', 'commits' => 1], + ['login' => 'alaminfirdows', 'github_id' => '30468274', 'commits' => 1], + ['login' => 'aaqidmasoodi', 'github_id' => '60925897', 'commits' => 1], + ]; + } +} diff --git a/resources/js/lib/about.ts b/resources/js/lib/about.ts index c6bbc3621..1c2336457 100644 --- a/resources/js/lib/about.ts +++ b/resources/js/lib/about.ts @@ -35,9 +35,13 @@ export type StoryPerson = { name: string; }; +/** + * Someone with a commit on production. The username is theirs on /dev/null, or null when they aren't on it. + */ export type StoryContributor = { login: string; commits: number; + username: string | null; }; export const storyBefore: StoryEvent[] = [ @@ -181,53 +185,3 @@ export const storyAfter: StoryEvent[] = [ }, }, ]; - -/** - * Everyone with a commit on production, most commits first. Bots and agents are left out. - */ -export const storyContributors: StoryContributor[] = [ - { login: 'xHeaven', commits: 199 }, - { login: 'nunomaduro', commits: 176 }, - { login: 'mnapoli', commits: 61 }, - { login: 'brendt', commits: 42 }, - { login: 'simonhamp', commits: 18 }, - { login: 'paulinevos', commits: 16 }, - { login: 'jubianchi', commits: 16 }, - { login: 'MrPunyapal', commits: 15 }, - { login: 'sadiqk2', commits: 8 }, - { login: 'camilleislasse', commits: 6 }, - { login: 'hbenabdallah', commits: 5 }, - { login: 'vtlxx', commits: 5 }, - { login: 'robelsust', commits: 4 }, - { login: 'HelgeSverre', commits: 4 }, - { login: 'SanderMuller', commits: 3 }, - { login: 'MaximeGoncalves', commits: 3 }, - { login: 'mathiasonea', commits: 3 }, - { login: 'fernandofreamunde', commits: 3 }, - { login: 'mon4ssi', commits: 2 }, - { login: 'hbenjacquet', commits: 2 }, - { login: 'Akiyo974', commits: 2 }, - { login: 'Chemaclass', commits: 2 }, - { login: 'eznix86', commits: 2 }, - { login: 'BENNIEV-ZA', commits: 2 }, - { login: 'ahosker', commits: 2 }, - { login: 'eramitgupta', commits: 1 }, - { login: 'utsavsomaiya', commits: 1 }, - { login: 'tooinfinity', commits: 1 }, - { login: 'murrant', commits: 1 }, - { login: 'RobinMalfait', commits: 1 }, - { login: 'prateekbhujel', commits: 1 }, - { login: 'ondrejmirtes', commits: 1 }, - { login: 'lazarospsa', commits: 1 }, - { login: 'kachelle', commits: 1 }, - { login: 'kadirtikil', commits: 1 }, - { login: 'jjaybrown', commits: 1 }, - { login: 'GTS-MEGHNI', commits: 1 }, - { login: 'faissaloux', commits: 1 }, - { login: 'fabpl', commits: 1 }, - { login: 'danielh-official', commits: 1 }, - { login: 'chrisgocode', commits: 1 }, - { login: 'AmanuelLegese', commits: 1 }, - { login: 'alaminfirdows', commits: 1 }, - { login: 'aaqidmasoodi', commits: 1 }, -]; diff --git a/resources/js/pages/about/show.tsx b/resources/js/pages/about/show.tsx index 409804079..9b0cb416b 100644 --- a/resources/js/pages/about/show.tsx +++ b/resources/js/pages/about/show.tsx @@ -13,9 +13,11 @@ import { DocumentPage, DocumentSection, } from '@/components/document-page'; +import { UserPreview } from '@/components/user-preview'; import AppLayout from '@/layouts/app-layout'; import type { StoryCommit, + StoryContributor, StoryEvent, StoryEventKind, StoryStream, @@ -24,11 +26,11 @@ import { storyAfter, storyAfterLane, storyBefore, - storyContributors, storyFounders, storyStreams, } from '@/lib/about'; import { cn, laneColor } from '@/lib/utils'; +import { show } from '@/routes/user'; import type { Lane } from '@/types'; const kindIcons: Record = { @@ -264,44 +266,75 @@ function Stream({ stream }: { stream: StoryStream }) { ); } -function Contributors() { +function ContributorCard({ contributor }: { contributor: StoryContributor }) { + return ( + <> + + + + @{contributor.login} + + + {contributor.commits}{' '} + {contributor.commits === 1 ? 'commit' : 'commits'} + + + + ); +} + +/** + * Contributors on /dev/null link to their profile, with their profile card on hover. Everyone else links to GitHub. + */ +function Contributors({ contributors }: { contributors: StoryContributor[] }) { + const className = + 'flex items-center gap-2.5 rounded-md border px-2.5 py-2 no-underline! transition-colors hover:bg-muted'; + return ( ); } -export default function Show() { +export default function Show({ + contributors, +}: { + contributors: StoryContributor[]; +}) { const { repository } = usePage().props; return ( <> @@ -392,7 +425,7 @@ export default function Show() {

Everyone who has a commit on production. Thank you.

- +

Want to be on this list?{' '} assertSee('', false) ->assertSee('"@type":"WebPage"', false); }); + +it('links each contributor who is on /dev/null to their profile, found by their GitHub account', function (): void { + User::factory()->create(['github_id' => '14284867', 'username' => 'renamed-on-devnull']); + + $this->get(route('about.show')) + ->assertOk() + ->assertInertia(fn ($page) => $page + ->where('contributors.0', ['login' => 'xHeaven', 'commits' => 199, 'username' => 'renamed-on-devnull']) + ->where('contributors.1', ['login' => 'nunomaduro', 'commits' => 176, 'username' => null])); +});