nazim@os: ~
AVAILABLE FOR COLLABS✦CAPE TOWN, SOUTH AFRICA✦BUILDING SOFTWARE✦PRODUCING MUSIC AS VETKAT✦MAKING VISUAL ART✦AVAILABLE FOR COLLABS✦CAPE TOWN, SOUTH AFRICA✦BUILDING SOFTWARE✦PRODUCING MUSIC AS VETKAT✦MAKING VISUAL ART✦AVAILABLE FOR COLLABS✦CAPE TOWN, SOUTH AFRICA✦BUILDING SOFTWARE✦PRODUCING MUSIC AS VETKAT✦MAKING VISUAL ART✦AVAILABLE FOR COLLABS✦CAPE TOWN, SOUTH AFRICA✦BUILDING SOFTWARE✦PRODUCING MUSIC AS VETKAT✦MAKING VISUAL ART✦

Desclution Link

Log in to the link.

A small members-only chatroom. Sign up with your email, pick a username and a spellword, and you're in.

desclution@link: ~
Signup: email a 6-digit code, always answer 202, store a PBKDF2-hashed spellword, hand back a 7-day JWT, then join the members-only room over a WebSocket
What happens when you sign up. Signup never says whether an email already has an account.

Served from my desk

Checking…

This runs on my desktop.

Not a cloud region, not a managed platform. Every message in Desclution Link goes through a machine sitting in my room. When it’s off, the link is off, and /status will tell you so.

  1. 01Youbrowser, over HTTPS
  2. 02Tailscale Funnelpublic HTTPS → my machine
  3. 03Home serverloopback-only port
  4. 04Docker networkprivate bridge
  5. 05ASP.NET Core + SignalRthe chat service
  6. 06PostgreSQLnever exposed
Pages come from Vercel; chat goes through a Tailscale Funnel to the homelab chat service, PostgreSQL and monitoring
Where a request goes. The homelab never opens a port; the Funnel carries chat to it.
Desclution as building blocks: Link, Lab and the portfolio, with room for the next service
Desclution is built as blocks: Link is the chat, Lab is the machine it runs on.

Why self-host it?

Partly an engineering exercise, partly an experiment in running real software on hardware I control.

Deploying to a managed platform hides the hard parts. Running it myself brings them all back: networking, storage, container lifecycles, monitoring, security boundaries, and what happens when the machine reboots.

The point isn’t to pretend a home server is production. It’s to understand what managed infrastructure actually does for you, by doing it by hand first.

What I learned

  • Networking

    Tunnels, reverse proxies and why the service only listens on loopback. The public way in is Funnel, never an open port.

  • Persistent storage

    Named Docker volumes, migrations that run on boot, and not losing the database when a container is rebuilt.

  • Container lifecycle

    Health checks, restart policies and start-up ordering, so the chat service waits for Postgres instead of crashing.

  • Monitoring

    A private Grafana, Prometheus and Alloy stack, reachable only over the tailnet, for logs and metrics from the box itself.

  • Security boundaries

    Explicit CORS origins, rate limits, hashed spellwords, email-verified signups, and a database with no route in from outside.

  • Deploying by hand

    git pull, docker compose up, check /health. Small enough to understand end to end, which is the whole point.