rhseung.me
A personal site built on Astro islands. This page is the result.
- Astro
- React
- Tailwind CSS
- TypeScript
Why
A dozen repositories had piled up, and a list of GitHub repos showed none of what mattered: what each thing is, and why it was built that way. READMEs explain features, not judgment.
How
How much React belongs in a static site. All-React hides the content behind JavaScript; all-Astro means hand-writing every interaction again. Astro islands split the difference — content freezes into HTML at build time, and exactly one island hydrates per route. With JavaScript off, the project list still reads.
Language moved into the URL. It started as a client-side i18n.changeLanguage() toggle,
which on a static site is effectively monolingual: crawlers see one copy of the HTML, so
there is no way to emit hreflang or per-language canonicals. A single [...lang] rest
parameter now emits / and /en/ from one file.
The content schema is owned by the feature, not the config. Putting the zod schema in
content.config.ts would tie the Model layer to astro:content, which Storybook and vitest
cannot resolve. Inverting the direction lets four consumers share one schema.
Result
No theme flash on first paint, per-language URLs indexed separately, and a story for every component so accessibility violations fail CI. The résumé renders to screen and PDF from the same YAML.
Limits
Project write-ups are still thin, and filtering has one axis — domain — so you cannot narrow by stack. That waits until there are more than a dozen entries.