Personal Website

This is my fourth attempt at a personal website. Every couple years I get the itch to redo it.

Previous Attempts

The first attempt was entirely in React, which made writing content painful. It was hosted on AWS S3 and CloudFront, which meant more maintenance than I wanted out of a weekend project.

The second attempt used Jekyll. Being a static site generator, writing content was easy. But Ruby dependencies were a nightmare to set up across machines.

The third attempt used Docusaurus and was hosted on Cloudflare Pages. Docusaurus was solid, but I wanted something with more flexibility and a better component story.

Current Stack

Next.js + Fumadocs

The site is built on Next.js with Fumadocs, an MDX-based documentation framework. All the content lives as MDX files in content/docs/, and Fumadocs handles the sidebar, search, and page rendering. It gives me the structure of a docs site with the flexibility of a full React app when I need it.

Hosting on Vercel

Hosted on Vercel, which is about as zero-maintenance as it gets for a Next.js app. Every push to main triggers a deploy, and PRs get preview deployments automatically.

Testing with Playwright

The site has E2E tests written in Playwright that run on every push and PR via a GitHub Actions workflow. Playwright auto-starts a dev server and runs the tests against it. Nothing fancy, but it catches broken pages before they ship.

Code Quality

Prettier runs automatically on commit through Husky and lint-staged, so I don't have to think about formatting.

Dev Environment

Mise manages the Bun version, so anyone who clones the repo gets the right runtime automatically. The repo also has a Dev Container config for VS Code and GitHub Codespaces, which gives a fully reproducible environment without any local setup.

On this page