← All projects
Astro · Tailwind · Cloudflare Active

sandwichlabs.dev

The Sandwich Labs site itself — a static Astro build on Cloudflare Workers, hand-styled with Tailwind v4 tokens, and now tracking its own progress as the first entry in its own project collection.

The site you’re reading. It exists for a boring reason — we needed one place to point at when someone asks what Sandwich Labs is — and a less boring one: it’s the smallest possible testbed for the build-and-deploy stack we keep reaching for, so when something breaks here it breaks cheaply.

What it’s built on

A plain static Astro build. No UI framework, no client-side router, and no client-side JavaScript — the tag filters on the project index are real static pages, not a filter widget. Styling is Tailwind v4 with the design tokens declared in @theme rather than a tailwind.config.mjs, which keeps the whole palette in one CSS file next to the thing it styles.

  • Astro 6, static output, content collections for structured content.
  • Tailwind v4 via @tailwindcss/vite, tokens in src/styles/global.css.
  • Cloudflare Workers for hosting, configured in wrangler.jsonc.
  • pnpm, pinned through Corepack so every shell agrees on a version.

The visual language is deliberately hard-edged: two-pixel ink borders, offset drop shadows with no blur, a serif for headlines and a mono for labels. It reads like a workbench, which is the point.

The project tracker

This entry is the first record in the projects collection — a markdown file per project, with the interesting parts in frontmatter:

title: sandwichlabs.dev
description: The Sandwich Labs site itself…
tags: [astro, web, tailwind]
view_url: https://sandwichlabs.dev
links:
  - label: SandwichLabs/www
    url: https://github.com/SandwichLabs/www
    type: source

title, description, tags, view_url, and links are the core of it. Everything else the schema accepts — status, started, updated, last_change, eyebrow, featured, order, draft — is optional, and exists because a tracker that can’t say what state something is in isn’t tracking much.

Tags are slugified and de-duped at load, and each one gets a static page under /projects/tags/; each status in use gets one under /projects/status/, linked from the tally on the index. Links are typed, so the source repo, the write-up, and the docs each render with their own glyph instead of a wall of identical anchors.

What’s next

Nothing dramatic. An RSS feed over the collection, an OG image per project, and whatever the next project on the bench needs from the schema.