Rust
12 posts
-
Generated illustrations, without the blog looking generated
Every post here now has a hand-drawn-looking picture and a share card with its title in it, drawn by an image model for about three cents each. How the house style is held steady across posts, what the model gets wrong, why the title is drawn by the model but normalised by Typst, and what the research on AI-made pictures says about doing this at all.
-
Citations by DOI, and the warning I read past for a month
A reference manager moved its database, a build script swallowed the error, and every build for a month reported success. Rebuilding the pipeline around DOIs and crossref, and why Zotero stays as the other half.
-
Audio on a static site: build-time TTS and the script it reads from
This post has an audio version in a clone of my own voice, generated at build time with Fish Audio S2.1 Pro and committed next to the PDFs. What the dyslexia research says, why the pipeline emits a readable script before it makes any sound, the four things the script got wrong, and why the whole thing is shelved for now.
-
A subscribe button does not need a Worker
The newsletter moved off Cloudflare Workers and onto the mail server in a day: one Rust service, a Postgres with four tables, addresses sealed at rest, and a record of which issue went to whom. Why a mail store as a database was the right workaround in February and the wrong one now, what the move cut from the attack surface, and what the research on LLM-written code says about doing this with a coding agent without the complexity creeping back.
-
Reader analytics, kept to myself
This blog now has real user monitoring: page views, web vitals, errors and which links get clicked, sent to an OpenObserve I run on my own server, only after the reader says yes, and sampled before a byte of the SDK is downloaded. Why a writer wants feedback at all, what the responsible-innovation framework says to leave out, the alternatives I looked at, and the day it produced six measurements of the same files for every one of a reader.
-
Forking Codex to talk to any endpoint
How we restored the Chat Completions wire API in a Codex fork, so one coding agent drives local Ollama models, OpenRouter, Azure OpenAI with Entra auth, or any EU-hosted provider. The three patches that made it usable, the branch model that keeps the rebases to an hour, and why Baldwin & Clark's design rules say the interface was the thing to fight for.
-
One-click unsubscribe needs a URL per reader and a DKIM tag
Three months of running a self-hosted newsletter: double opt-in with no database, why one-click unsubscribe forced me to stop using my mail server's fan-out, and an RFC 8058 DKIM requirement that ends in an anticlimax.
-
Images on a static site: tradeoffs, limits, and a 150-line Rust optimizer
Why images on this blog live in git next to the post instead of in object storage, how many that can hold, the small Rust tool that turns anything into a WebP, and what six months of using it changed.
-
Proper citations on a static site: Zotero, Rust, and Typst
How I built a citation pipeline for my Zola blog that reads from Zotero, renders references in HTML, and generates PDFs with Typst. No LaTeX required.
-
Self-hosting email is not that hard anymore
This blog's newsletter ran on a Rust Cloudflare Worker and my own Stalwart mail server, with no database and nothing paid for, until September 2026, when it moved onto the mail server itself. What the system looked like after a year of fixes, the DNS records that keep it out of the junk folder, what Hacker News gets wrong about running your own mail, and why a newsletter is a pipeline in the knowledge-diffusion sense.
-
I use Typst to generate PDFs of my blog posts and my CV
How I replaced LaTeX with Typst to auto-generate downloadable PDFs for every blog post and keep my CV version-controlled. Markdown in, beautiful PDFs out.
-
Zola has no plugins, so this blog grew a Rust CLI
Why the blog runs on Zola, what Zola refuses to do, and how that one refusal decided the shape of everything else: a Rust CLI that owns citations, PDFs, audio and the newsletter, every generated file committed to git, and a build that is one script. Read through organisational path dependence, with four things I would do differently.