Skip to main content

Playing with Hugo (for poops and lols)

·908 words·5 mins
David Smith
Author
David Smith

How it started
#

Bored at the kitchen table on a Sunday afternoon, feeling the need to do something other than complete another Sudoku, and feeling inspired after ffconf on Friday….

A quick search “use github for website hosting” later and a scan of some of the links it turns up leads me quickly to the idea of using Hugo on GitHub (even though one of the articles suggested not using GitHub pages).

So ignoring the “don’t use GitHub pages” advice, I got started. Using the excellent WordPress to Markdown tool I quickly re-created my existing site as a series of Markdown files (most of the images appeared to have failed to download, but that was a “future Dave™” problem which I’d come back to). On to building the site — I’ve tinkered with Hugo before and mostly enjoyed the experience, so I went with it again. For anyone keeping score, this is the fourth time I’ve built or rebuilt my personal website: Tumblr → static site → WordPress → static site (Hugo). I picked the Blowfish theme and had something up and running pretty quickly.

And then… I got bored of trying to sort out all of the broken images and tidying up old posts. So it sat there, half finished, for a few months.

How it’s going
#

Fast forward to a weekend in March and a conversation with Claude — Anthropic’s AI assistant — which turned into a proper pair programming session, and then another one, and probably another one after that (I’ve lost count). What started as “let’s fix a few broken image paths” turned into something considerably more involved.

First though, we went back and tackled the thing that had stopped me in my tracks in November — the broken images. The WordPress export had left a trail of ../images/ paths that meant nothing to Hugo, WordPress shortcodes still sitting raw in post content, and a handful of posts with galleries that needed rebuilding entirely using Blowfish’s gallery shortcode. Not the most glamorous work, but satisfying in the way that tidying a drawer is satisfying. Sixteen years of posts, more or less intact.

First up was the fitness section. I’d wanted somewhere to surface my Strava data for a while, so we built a sync tool in TypeScript that pulls activity data from the Strava API and writes it out as JSON files that Hugo can read at build time. The result is a full fitness section on the site: annual and monthly breakdowns, year-on-year comparisons, and Chart.js graphs — all driven entirely from data files with no database in sight. There’s a sticky table header on the history page that required a slightly embarrassing amount of JavaScript because CSS position: sticky doesn’t play nicely when there’s an overflow-x: auto wrapper in the way. One of those things that should take five minutes and takes considerably longer. You know the ones.

The other thing that came out of the weekend was sorting out the photos section properly. I’d deleted my Instagram account a while back — Meta: ick — which meant the only way to recover those photos was from the data export. So we built a Docker-based import tool that takes that export, fixes the mojibake UTF-8 encoding that Instagram helpfully applies to everything, and creates proper Hugo page bundles from it — a few hundred posts imported in one go. That done, it felt wrong not to have a nice way to keep adding photos going forward, so we built a PWA — a web app you can pin to your iPhone home screen — for posting photos directly to the site without needing a laptop. Take a photo, write a caption, add some hashtags, and it commits everything straight to the GitHub repo via the API and triggers a build automatically. It’s probably overkill for a personal blog, but it does mean I can post from a pub garden which, let’s be honest, is the real use case. There were a few iterations along the way — hashtags appearing as individual characters, the Post button disappearing off the bottom of the screen, the app stubbornly refusing to update itself on my phone — all of which is just normal software development really, AI-assisted or otherwise.

Finally, with all of that in place, it felt like the right time to properly sort out the DNS. The domain has been sitting on old shared hosting for years, so we migrated everything over to Route53, updated the nameservers, pointed the apex and www records at GitHub Pages, and waited patiently for propagation to finish. It did.

The whole experience has been a genuinely interesting way to work. Having an AI that can hold the full context of a project, suggest approaches, write and iterate on code, and explain what it’s doing (and why it went wrong) makes for a very different kind of weekend tinkering than sitting alone with Stack Overflow. Could I have done all of this myself? Probably. Would it still be half-finished and sitting in a branch somewhere? Almost certainly. The site’s not quite finished — but then again this is the fourth version of this site, so “not quite finished” is basically a design feature at this point.

And yes, I’m writing this sat at the kitchen table. Some things don’t change.