Base64 Is Fast Now, Actually This is a short post. I was wondering recently, if I had to send a binary file across a text stream to a browser - i.e., embedded in JSON - what would be the fastest way to do that. Clearly, base64'ing the content is a valid approach and always has a 4/3 overhead. However, one thought I had is that JS strings are fundamentally just arrays of unsigned 16-bit integers…
Major Node Changes This document is a short list of changes in Node.js' major releases. It does not cover point releases, just e.g., v13, v14 and so on. v25 (2025) v8 14.1 Supports Uint8Array base64/hex helpers Type stripping for TS support enabld by default This does not transform types, you may still need --experimental-transform-types v24 (2025) v8 13.6 Adds Float16Array , RegExp.escape Adds…
Why Will Wikipedia Wither? aka: in the age of AI, what is the role of summarizers Wikipedia is the world's free encyclopedia. Some definitions: an encyclopedia summarizes knowledge—let's call this primary sources—in a useful, digestable format. And primary sources are, well, primary! Research papers, quotes, police reports, press releases, survey data, photos, stats on Pokémon, medical records,…
All Browsers Get This Wrong We found a bug in Shadow DOM that's strangely consistent across Firefox, Safari and Chrome. And this bug is strange: it's not actually a user-facing issue, but rather, something the developer tools across each browser just gets wrong . 🤯 Background I'm a huge fan of Web Components, despite their various downsides. Part of this was my time at Google: I was paid to…
Collaboration, Now! Update: If you're in Sydney in July 2025, join our hackathon ! I've a bold claim to make. I think the web is stuck, stagnant, immovable, … more synonyms. 🛑 We're stuck in, fundamentally, a React-pinned era. Around ~2018 or so, React had the complete suite: functional components and hooks. And modern app development, whether you like it or not, is largely inspired by that kind…
Post-Request/Response Apps Serverless or monolithic/'serverful' architectures are often presented as sides of the same coin: they're both just alternative ways to serve synchronous requests, for example, a HTTP server serving content, or handling API requests publicly or internally. But this is a naïve viewpoint, and we as developers now almost see 'serverless-like' development as the silver…
Node.js can run TypeScript This is a fairly quick post, but it's impactful if you use Node.js. Node.js can now just run TypeScript locally, without needing tsx or a build step. How Node v22 has added an experimental flag, --experimental-transform-types . This supercedes a previous strip flag, because it supports code-based TypeScript features like enum . (Maybe there's some features still missing,…
Kuto, a reverse JS bundler Kuto is a novel approach to shipping code on the web. It lets you re-use code a client already has for shipping updates. For a 'real-world' site with ~3mb of JS, updating the React dependency resulted in: 71% smaller download 28% faster start time (on a ~5yo old phone, a Pixel 3 ). …vs a single bundle, or any case where all the code is invalidated. Note that Kuto works…
CJS Equivalency I've been working on bundler-like things and I've thought again about the classic CJS vs ESM interop issue. It occurs to me that one way to transform CJS to ESM is to treat each CJS file as a 'builder'. This isn't bundling , but perhaps a step on the way, or for a serving library which purely provides a transform. Example Here's a reductive example. We have a CJS file which has…
December Tech Vibe Check It's the end of 2023. This isn't a "year in review", just some musings about what's been going on recently. Read on to find out more about: What I'm doing in the Cloud What open-source code I'm publishing Some business plans and musings. Cloud Tech Stack There's been some cool updates in the way I build projects. Cloud Run I bit the bullet and moved this blog over to Cloud…
Baldur's Gate 3 Character Choice My partner and I have been playing co-op Baldur's Gate 3 on PS5. It's good, although a bit clunky on controller, and while the split-screen mode is amazing that it works at all, it's also the source of pretty hefty FPS drops. When cross-play is added, one of us will probably swap to a Mac to keep playing. How Your Character Choice Works We found character creation…
Opinions On Sydney Rail Transport This is a post containing my niche opinions on Sydney's public transport system. If you're from Sydney and a transport nerd, this is probably interesting. Otherwise, maybe read something else. I'm not going to give background, suffice to say that Sydney is Australia's biggest city and has the highest number of commuters who use public transport. Without further…
AWS Amplify Is A Grift Yes, this is a punchy headline, but if you'll join me on this journey, you'll see how. 👀 So, here's the context. For the past year or so, I was at a renewable energy startup. It was a great experience, but I recently resigned: I'm having another child, and I just don't need to work full-time—so I'm not going to. To be clear, this post is entirely my opinion: as of writing,…
AbortController for expiry My last post on AbortController continues to be my most read blog post, ever. This one probably won't do quite as well, but that's fine—it's a bit more niche, but it's definitely also an extension of that one. Today, the problem I'll solve is: you have a token, key, or some object (e.g., some key to access a system) it's valid only for some time (e.g., an hour) - it has…
Practical Python Modules I grew up writing a lot of Python, which I guess speaks to how old and unorganized it is. And since then, I've been primarily a JS developer—that ecosystem has its failings, but the rules around how things are imported inside "node_modules" are mostly well established, even despite its quirks. For modules, though—Python is a mess. But I think there's some simple knowledge…
Focus Management in 2022 📺 I recently gave a talk! It's on <dialog> and the inert attribute, with a mention of <fieldset disabled> , too. You can find the talk on JSNation , who graciously hosted me and motivated me to get this done. 🎉 But also, it's just on YouTube here (albeit without my face and a snazzy intro/outro): This talk combines one of my quite popular blogposts— In Defence Of Dialog…
Event-Driven JavaScript Development Every JS developer has written code to handle "click" listeners—press a button, tap a link—and you'll do something interesting. Events are core to the way we write for the web and use the DOM. 👆 But what if I were to tell you that you should and could be using event-driven development for yourself —not even in the DOM? 🤔 To do that, we can now subclass…
Cross-Tab Title Hints Let's say you've built a website that shows items—maybe things you can buy online, or a catalogue of TV episodes. Your users are opening lots of tabs at once 📈 to compare and contrast, or decide what to buy, or whatever. Turns out, we can use just the hidden tabs as a surface to help the user out. But note that this is really a desktop-only feature, because tabs aren't…
AbortController is your friend Also available in: [ 한국어 번역 ] One of my favorite new features of JS is the humble AbortController , and its AbortSignal . It enables some new development patterns, which I'll cover below, but first: the canonical demo. It's to use AbortController to provide a fetch() you can abort early: Sorry, your browser doesn't support an inline demo. And here's a simplified…
Unit Testing React without Jest Jest is clearly a polished testing tool, but with the advent of Node.js 18 , we really don't need it any more. Jest also has a huge surface area, is perhaps inexorably linked to Webpack, and needs its own binary—you can't just "run the tests" as a script. So it has some modern challenges. This blog post will teach you how to set up your code, rather than provide an…