[idea:26w33]2026-08-16

Week 33

Contents

It was a productive week back at the office (my apartment living room). I’m writing on a Monday again, which is becoming the more reasonable day on which to publish my weeknote, so I’ll stop apologizing for it. The sections are in reverse order this week, as some hacking I did over the weekend has resulted in the new skin you see here for these weeknotes, and it’s very much top of mind. The tooling that enables this structure is something I’ve been wanting to build since I started writing weeknotes, and a lot of the work I’m planning to do in the coming months will build on it as a basis.

This website now runs on a new Rheo/Typst package called rookery. I spent the weekend developing this package and doing my best to explain its concepts and how it works in that documentation site, and so I direct the reader there for a proper explanation. Here I’ll just talk a little about its motivation and the research that I hope it will jumpstart.

When I was an undergraduate freshman, my parents bought me a Macbook Pro to use for my studies. I remember opening it in California when I arrived in the US on August 10th, 2013. My high school hadn’t offered any classes in computing except a summer course on touch typing, taught by the headmaster’s wife, but I had taught myself Python using Coursera and EdX, the MOOC platforms of the moment.

For reasons I don’t remember, I used the indy software Growly Notes for all my work. In a particularly memorable course as a freshman (taught by Daniel Heller-Roazen), I remember deciding to take notes in a different way each lecture, ranging from structured bullets on Growly to writing a single stream-of-thought line that spiralled from the outer edges of an A4 piece of paper to its center.1

Growly stuck with me for four years. In my junior or senior year, a PhD student in German whom I had become friends with, William Stewart, clued me in to another indy Mac software, DEVONThink. Over several years as a recent graduate working at Forensic Architecture in London, I came to a way of using DEVONthink as what I called an associative archive. This wasn’t a note-taking philosophy so much as it was a kind of nascent theory of how to bring the best of Unix to digital archiving in general, and personal research databases in particular.

As I moved through the early years of my dissertation, I eventually managed to cleanse myself of any strong dependency on Apple software. Though I haven’t yet managed to recreate a richly featured associative archiving system on Linux, much of my recent software work with the FCL is essentially in search of this vision.

In 2023 or so, I adopted Org-mode more seriously at Zac Ioannidis’ suggestion. Org-mode completely transformed my way of thinking about note-taking, partly because I hacked together a way (with LaTeX and Pandoc) to export documents to both HTML and PDF, and partly because of its inbuilt TODO system.

At the end of 2025, I started looking into Typst after conversations with Will Crichton. This led me to develop Rheo and to publish a paper with Will about its possible use in augmented reading research alongside bene, an EPUB reading system. As I started doing all my writing in Typst, I came to realise that I wanted to use it as the basis of not only an associative archive, but also both a proper academic authoring toolchain and my (increasingly constant) communication with LLMs.

Rookery lets you create intellectual junkyards in Typst, and it is the next step in this line of my research thinking about better foundations for documents and knowledge systems. It draws most of its concepts from Jon Sterling’s forester, which I wrote about as inspiration for why I started writing weeknotes, and again in the rookery FAQ.

I recognise, however, that often tools in this ‘deep note taking’ space can come across as unapproachable and opaque—at least, this is my experience of how tools like Roam Research and even Obsidian tend to signify. Notion is the most mainstream tool that draws aspects of its architecture from this research space, but it very much follows Apple’s example in cultivating walled gardens and prioritizing enterprise use cases.

Rookery is my first real contribution to this space (other than Rheo, which arguably doesn’t play in quite the same sandpit), and I can’t wait to rebuild and extend several of the sites I maintain with it this coming week. This site is the first that I’ve ported—it took all of five minutes with the help of Claude Code—so watch this space for many more rookery examples.

The development of rookery and its documentation took only one weekend (15-16 August), though with full 10+ hour days hacking, and it stands on the shoulders of much prior work in Rheo. It is almost entirely vibe-engineered, and only currently tested anecdotally in my own examples. Rookery is personal software for the time being, and like Rheo it is likely to undergo relatively dramatic changes in the next few months as I work out how I best work with it. That said, if this kind of tooling excites you, you’re brave enough to want to use rookery for something, or you just have some feedback, please do reach out.

Footnotes

  1. ^ Appropriately, I believe that these were my notes for the lecture on Dante’s Inferno.

Earlier in the week, I posted a new blog post, Birdkeeping. I wrote this post two weeks ago, actually, as I started hacking on a tool in the same family as rookery, and it represents my latest thinking about how to use LLMs effectively in software maintenance and research. I decided that I want to develop this tool in Lean, an exciting new programming language that is getting a lot of play in software news at the moment in relation to the waves AI is making in mathematical research.

Grant Sanderson has some good thoughts about how to use LLMs to learn, and I’m doing something similar in order to learn Lean. I have a prototype for this tool in Rust—which is the programming language I’m most comfortable thinking with right now—and so I asked Opus 5 to devise a tutorial covering core concepts and features in Lean that reconstruct the same tool. This has so far been a productive exercise, as I know exactly what I’m building and why I’d want to build it: I just get a contextualized tour of Lean along the way. After an hour or two building the prototype back up in Lean, I realised that I still needed to refine some of the concepts in the tool themselves, so I went back to Rust for a bit where I can iterate faster. But this is the general workflow that I intend to continue. More on this tool when it’s more mature in my own thinking!

In order to enable parts of rookery, I cut a 0.5.2 release of Rheo this week. It only adds one feature, which is to enable both end users and Rheo packages to specify marrow. I haven’t fully thought through the consequences of this feature in Rheo yet, so I’m leaving it undocumented for now.

A bigger rewrite also got underway factoring out parts of Rheo’s engine to custom Typst packages. Rheo is intended as a kind of wrapping compiler around Typst, and so it only wants features that are impossible to achieve or otherwise not performant in pure Typst. The way that Rheo creates rheo-context, for example, is currently hacky given that it could be implemented as a Typst package. In Rheo 0.6.0, I hope to strip away some of the unnecessary features in Rheo’s core and compartmentalize them instead as packages.

I also shipped a blogfeed 0.1.1, which enables the nice colours you can now see in the filters on my main blog.

I spent a day at the very beginning of the week—which feels like a long time ago now—setting up a local instance of listmonk so that I can send out emails easily every time I have a new post here or on my main blog. This was a bit more finicky than I had hoped, as listmonk doesn’t provide a built-in way to treat Atom feeds like the one for this site as a source of truth for email campaigns, which is what I want. It was so frustrating, in fact, that I went searching for a different framework halfway through. Buttondown looks usable, but I wanted to self-host it, and it’s not open source. So I resisted the urge to develop my own emailing software from scratch, and stuck through configuring listmonk.

I ended up developing a custom Python CLI / NixOS module that both provisions a fresh instance of listmonk in the way that I want, and also runs a daemon that polls Atom feeds and creates new campaigns when there is new content. After a forgettable afternoon fighting with listmonk’s misshapen API, I got it working reasonably enough. When my Framework Desktop is turned on, it polls my sites’ Atom feeds, and prompts me if there are new campaigns (emails for new posts) to send out. I can adapt the template for the email, i.e. how much of the content it previews in the email itself, and send emails etc. in the listmonk frontend interface, which is… fine.

The other major hitch is that, in order to provide an endpoint through which users can automatically subscribe and unsubscribe, the service running on my machine would need an external IP address. The deeper problem is that I intentionally don’t leave my desktop on at all times, and so the service isn’t always available. I have plans to solve this deeper part with (yet another) system I’m building; but given it doesn’t exist yet, there’s no point right now in taking the trouble to expose my listmonk server to the broader Internet. My workaround at the moment is just to manually maintain the list, which means that ‘subscribing’ and ‘unsubscribing’ just amount to sending me an email. Thankfully, the readership for both this site and my blog is minuscule, and given its technical consistency many if not most of my readers know how Atom feeds work. For those who don’t, you can get on the email list by sending an email with subscribe weeknotes.ohrg.org in the header to hi [the symbol in emails] ohrg [dot] org.