About this site
A minimal, fast, fully static site focused on readability, performance, and maintainability.
Goals
- Ship static HTML for instant loads and reliable hosting
- Keep JS to zero for robustness and accessibility
- Use components for reuse, consistency, and easy iteration
The journey
I started with handwritten HTML and a lightweight CSS framework. As content grew, copy‑pasting layouts and keeping design consistent became a tax on iteration.
Moving to a component model solved that: I could compose pages from small, reusable pieces and keep typography and spacing consistent without fighting the markup.
I work daily with .NET across apps, services, and websites, so building with a familiar stack made sense—as long as it could stay static.
Static generation
The site is pre-rendered to static HTML at build time. That delivers:
- Fast first paint and predictable SEO
- Simple, cache‑friendly hosting on a CDN
- No client bootstrapping or runtime dependencies
Build pipeline
Every commit triggers a build that generates the static site and publishes it to the host. The process is fast, reproducible, and easy to roll back.
name: Deploy to Cloudflare Pages
on:
push:
branches:
- master
pull_request:
branches:
- master
jobs:
build-and-deploy:
runs-on: ubuntu-latest
steps:
- name: Checkout repository
uses: actions/checkout@v4
- name: Setup Bun
uses: oven-sh/setup-bun@v1
with:
bun-version: latest
- name: Install dependencies
run: bun install
- name: Build Tailwind CSS
run: bun run tailwindcss -i ./wwwroot/css/~input.css -o ./wwwroot/css/tailwind.css
- name: Setup .NET
uses: actions/setup-dotnet@v4
with:
dotnet-version: '9.0.x'
- name: Restore dependencies
run: dotnet restore
- name: Build and generate static site
run: dotnet run --configuration Release
- name: Deploy to Cloudflare Pages
uses: cloudflare/wrangler-action@v3
with:
apiToken: ${{ secrets.CLOUDFLARE_API_TOKEN }}
accountId: ${{ secrets.CLOUDFLARE_ACCOUNT_ID }}
command: pages deploy build/site --project-name=personal-siteCode presentation
Code snippets are rendered at build time for zero‑JS syntax highlighting and consistent theming. A small component runs a CLI highlighter during the build and inlines the result into the page.
@attribute [Route(PageRoute.Thoughts.ThisSite)]
<HeadContent>
<meta name="description"
content="How I built this site: a minimal, fast, static Blazor site pre-rendered to HTML with no JavaScript, designed for readability and performance."/>
</HeadContent>
<PageTitle>About this site - Thoughts</PageTitle>
<article class="flex flex-col gap-10">
<header class="flex flex-col gap-3">
<h1>About this site</h1>
<p class="text-neutral-500 dark:text-neutral-400 text-lg leading-relaxed">
A minimal, fast, fully static site focused on readability, performance, and maintainability.
</p>
</header>
<section class="flex flex-col gap-4">
<h2>Goals</h2>
<ul class="text-neutral-700 dark:text-neutral-300">
<li class="blue">
Ship static HTML for instant loads and reliable hosting
</li>
<li class="blue">
Keep JS to zero for robustness and accessibility
</li>
<li class="blue">
Use components for reuse, consistency, and easy iteration
</li>
</ul>
</section>
<section class="flex flex-col gap-4">
<h2>The journey</h2>
<div class="flex flex-col gap-3">
<p>
I started with handwritten HTML and a lightweight CSS framework. As content grew, copy‑pasting layouts
and keeping design consistent became a tax on iteration.
</p>
<p>
Moving to a component model solved that: I could compose pages from small, reusable pieces and keep
typography and spacing consistent without fighting the markup.
</p>
<p>
I work daily with .NET across apps, services, and websites, so building with a familiar stack made
sense—as long as it could stay static.
</p>
</div>
</section>
<section class="flex flex-col gap-4">
<h2>Static generation</h2>
<p>
The site is pre-rendered to static HTML at build time. That delivers:
</p>
<ul class="text-neutral-700 dark:text-neutral-300">
<li class="green">
Fast first paint and predictable SEO
</li>
<li class="green">
Simple, cache‑friendly hosting on a CDN
</li>
<li class="green">
No client bootstrapping or runtime dependencies
</li>
</ul>
</section>
<section class="flex flex-col gap-4">
<h2>Build pipeline</h2>
<p>
Every commit triggers a build that generates the static site and publishes it to the host. The process is
fast, reproducible, and easy to roll back.
</p>
<CodeView FilePath=".github/workflows/deploy.yml" Lang="yaml"
CollapsingIcon="@Icon.Regular("arrows-out-simple").ToString()"/>
</section>
<section class="flex flex-col gap-4">
<h2>Code presentation</h2>
<p>
Code snippets are rendered at build time for zero‑JS syntax highlighting and consistent theming. A small
component runs a CLI highlighter during the build and inlines the result into the page.
</p>
<CodeView FilePath="Components/Pages/Thoughts/ThisSite.razor" Lang="razor"
CollapsingIcon="@Icon.Regular("arrows-out-simple").ToString()"/>
</section>
<section class="flex flex-col gap-4">
<h2>What this enables</h2>
<div class="grid grid-cols-1 md:grid-cols-2 gap-4">
<div class="p-4 rounded-lg bg-blue-500/10 border border-blue-500/20">
<h3 class="text-neutral-900 dark:text-neutral-50">
Performance
</h3>
<p class="text-neutral-700 dark:text-neutral-300">
Minimal payloads, static HTML, and aggressive caching keep pages snappy on any connection.
</p>
</div>
<div class="p-4 rounded-lg bg-purple-500/10 border border-purple-500/20">
<h3 class="text-neutral-900 dark:text-neutral-50">
Maintainability
</h3>
<p class="text-neutral-700 dark:text-neutral-300">
Components centralize layout and styling so content stays the focus.
</p>
</div>
</div>
</section>
</article>What this enables
Performance
Minimal payloads, static HTML, and aggressive caching keep pages snappy on any connection.
Maintainability
Components centralize layout and styling so content stays the focus.