I had a Fujifilm X100V for ~1.5 years, until my bag was stolen, with it inside it. Fortunately, insurance was worth it! Instead of immediately getting a replacement, I looked at what was out there. I wanted something in a similar form factor, a built-in flash, and a low aperture on a ~50mm lens, that has relatively quick autofocus. For ~£1,000 less, I have an interchangeable lens body, and I’m…
After adding diagrams 1 , I wished I had nicer charts 2 . Interactive charts are rendered from vl fenced code blocks. The spec is validated at compile time, so any local data URLs are checked for existence too. The data lives in priv/static/data/ . Examples Here’s some examples. Loss curves A multi-series line chart using Vega-Lite’s fold transform to pivot train_loss and val_loss from wide to…
Blog posts now support inline diagrams authored in D2 1 . Why D2 Like most people, I reached for Mermaid first. I didn’t want to add a JavaScript dependency though. D2 is a modern approach to diagrams, and has some nice things like supporting light and dark mode. How it works A custom MDEx 2 pipeline plugin walks the document AST at compile time, finds every fenced code block tagged d2 , and…
Idea There are several daily activities you do as an X engineer in your terminal. For example, I err on the side of regularly keeping my Git repositories in sync, with regular rebasing—and restacking, with stacked changes. These are minor things, but they add up as some niceties of computing. To take agents to a proactive, instead of reactive, stance, why not have something do things for me…
Previously I had hacked together a Magit plugin 1 for git-spice 2 . In the meantime, Abhinav Gupta has released official JSON support 3 ! Following this, I’ve released an alpha version of git-spice.el 4 . Feel free to give it a go. There’s a good chunk of AI generated code inthere, as a warning. It’s now listed on git-spice’s website 5 . Magit plugin for git-spice (for stacked pull requests) ↩…
There was a pattern at work with some fellow engineers, in data engineer roles, where there would be a lot of glue functions in Python. They were all effectively a mapping over a list and doing a transform. People would add unit tests for them too. This doesn’t sound like a bad problem, and in a way, it’s not. How it’s a problem is that it creates multiple levels of indirection, when understanding…
I use Railway 1 , and recently upgraded to LiveView 1.1 2 in my Rom-to-the-Com 3 side-project. This caused deploying my app via Railpack 4 to fail. Fortunately, it was a simple fix of changing the order of the build steps. I submitted a PR 5 . It was merged in, and my app has been deployed. Another benefit of source-available software. Railway ↩…
git-spice 1 is a CLI tool for stacked pull requests. It has forge support for GitHub, so far. Since Emacs is my primary editor, with Magit in it, I wanted to see how quickly I could add initial support for git-spice. There’s an open issue 2 , but for now I wanted to test it out. I patched in the most basic JSON output. Here’s what it looks like in Magit so far: git-spice ↩ log: –json output…
There’s the agentic web phrase being bandied around now. It may be little more than what Web 3.0 was suggested, and asked for, to be. As part of discovering that, you can now connect to my website as it hosts a remote MCP server, at https://j-e-s-s-e.com/mcp . For example, you can use npx @modelcontextprotocol/inspector , and then put that in as the address, and connect. There’s currently 2 tools:…
Release announcement On 2025-06-08 I wrote about documentation decay 1 and gave a snippet of a program that I began using a little bit. I’m happy to release the alpha version of the evolution of that, called Clevis 2 . It’s a CLI tool, written in Rust, and there’s also a GitHub Action 3 available. Example Here’s a real-world example from my day job: From b0611ce5c8031ecc54379630e1143f4f09ef68ee…
You can make the same mistakes with deciding to use microservices, but with data/ML pipelines, instead of the traditionally understood meaning of service. This is where 1 pipeline = 1 microservice. Similarly with deciding between monoliths and microservices, you can too quickly go for separate micro-pipelines , instead of 1, monolith pipeline. An example of a shared problem is, why introduce…
Following on from my previous contributions 1 , I’ve now put the menu in a separate package 2 . NB: This is my first Emacs package too. First contributions to Himalaya Emacs package ↩ jesse-c/himalaya-menu-emacs ↩
Justfiles, as an alternative to Makefiles, have grown a lot in popularity. I use them for projects and at work. A common pattern for things like this (e.g. Cargo, Mix, etc) is to have a transient menu to run commands quickly. With a little AI assistance, I now have one 1 that I use daily at work. It ( just-transient--make-transient ) looks for a Justfile, and if it finds one, it creates a simple…
Good practices generally need minimal barriers to implement and barriers to overcome. One of those is conventional commits. I’ve used them to narrow down changes in Git logs, to add clarity to a commit’s intent, to encourage splitting up changes into distinct changes (i.e. don’t fix something and add a new feature together, break them up), and so on. Even if you really like them, you still want to…
DAP is to debugging that LSP is to coding. For Emacs, Dape 1 is to dap-mode that Eglot is to lsp-mode . It took me longer than it should’ve, but, I’ve now confiused Dape for both Python code execution debugging and test debugging 2 . There’s not a huge amount of examples of this configuration around, so I’m sharing it here to help others. I’ve based my configs on the default ones for Python, and…
I’ve been using Himalaya on-and-off since 2023, and have made a Raycast package for it 1 . I switched to Emacs a few years ago too, from Neovim—and have probably tried every other editor at some point too. With the v1 release of Himalaya, and updating my Raycast package for it 2 , I was curious to see what other developments had happened. That took me to himalaya-emacs to which I fixed a tiny bug…
The Raycast extension I made for Himalaya was released in 2023 1 , and I’ve now released a new version 2 that updates it for Himalya v1! 3 I have several contributions open for Himalaya Emacs too 4 . Raycast extension for Himalaya released ↩ feat(himalaya): Update for Himalaya v1.0.0 extensions#18388 ↩ Release v1.0.0 ↩ Evil and Transient mode maps, HTML viewing, etc. ↩
Recently 1 I put out another headless-first program. I’ve improved it a bunch since then, and just before I was working on the private mode feature. For at least 8 years 2 , I’ve occasionally had the thought of agents. Today I noticed the similarity about being agent-first and headless-first. Being those, means that you need the data, context, and most importantly, actions available to be called…
This is the latest, in my ongoing experiments of daemon-first or headless-first 1 2 3 software. This time, it’s for my clipboard history, that’s turned out to be an invaluable thing to have access oo—much like my shell history. I’ve created a daemon 4 and Raycast extension 5 . Someone has put together a comparison list 6 of clipboard managers for macOS, that currently has 29 listed! I had been…
In Explicitly showing, and checking, documentation decay 1 , I gave a Python snippet for checking some “links” between data in documentation. After doing some recent changes to keep that project easily usable, I had that snippet sitting locally in my workspace. Recently I used this concept for another real-world project 2 . The original snippet wasn’t far off! The changeset, including the CI…
Again on a previous blog post 1 , I’ve come across some writings by the inimitable Ink & Switch group on a similar concept 2 3 . Here’s a use case they describe: Every time a chart changes, he needs to manually drag files from his computer into the browser. This aligns almost exactly with my original post! It’s fascinating to see the same, otherwise common problem, pointed out and described—with…
In a previous blog post 1 , I wrote about an idea to avoid documentation decay, like links or installation instructions falling out-of-date. I just had a chance to try it out, on a new project 2 3 . The README is generated from a Jinja2 template. So far, it’s the tools that are pulled from the actual model context server. Here’s the template for that: ## Tools {% for tool in tools %}…
With the launch of the Model Context Protocol initiative by Anthropic 1 , I thought I’d try my hand at making one—as did many others, also think to do! As I use Linear daily, I thought that would be a good target 2 . Next would be Reminders.app for Linear⟷Reminders.app agentic (?) flows. I’ve just tagged a v0.2.0 release, so check it out at https://github.com/jesse-c/linear-context-server-ts .…
I’ve added audio as another interface for regular and useful writing—across daily notes, Git comments, etc. I thought I’d quickly package it up and make it available 1 . I shared the snippets originally with my colleagues. It uses an MLX version of a Whisper model. It’s helpful because at the moment it takes 3 sources: Record from a microphone Download a YouTube video Provide a path to a local…
This is an implementation 1 as a follow-up to a previous post 2 about preventing posting dupes on Instagram, through a simple ML model. For now, you can upload an image, and it’ll give the top k (5, at the moment), images that your image is similar to. This approach makes it so that I can use it, which is the main priority, and also lets others have fun with it. Usually if I’m editing photos, I…
Someone mentioned to me that some of their girl friends had thoughts about some of the rankings. With that, and wanting to add a feature where people can edit rankings, I’ve thrown that together. Have fun at https://www.rom-to-the-com.com .
Welcome to ResNet-50 Embeddings Only This came out of Preventing posting dupes on Instagram . There’s truly nothing new here, except that I’ve uploaded it as a stand-alone model 1 . I appreciate the work of the many others, that this is based on. https://huggingface.co/jxtc/resnet-50-embeddings ↩
What’s now simple One of the things I’ve done continuously for a while is photography. Recently, I did my first paid shoot, at an art gallery opening, for one of the artists. Otherwise, it’s simply things from my life, like anyone. I’ve almost posted a photo twice before, if it’s from a previous month or year. As with others, I was recently reminded of XKCD 1425 (Tasks) 1 by Simon Willison 2 .…
The problem with manual links Have you ever seen perfectly up-to-date documentation? What about a SaaS product’s API documentation? For the latter, there’s well known approaches, and tools, for documentation generation. I’ve seen a kind of new tools that will monitor your requests/responses, to catch drift. I’ll focus on the former for now. On 2023-08-22, I was looking at Elastic’s Helm charts,…
To reduce use of embeddings outside of Vespa itself, I’ve removed it from the data transformation pipeline 1 and the querying CLI 2 . jesse-c/notes-app-hybrid-search#2 ↩ jesse-c/notes-app-hybrid-search#1 ↩
Introduction One of the ways I use Notes.app is for having a Shortcut that creates a daily note, titled as the current day (e.g. “2024-09-08”), where I use it for journal-esque writings, dropping links to products or articles, project ideas, and anything . Unfortunately, the keyword search in Notes.app isn’t always sufficient. I’m sure Apple will add something like this eventually, and for now,…
Around 3 years ago, a friend of mine told me about something they’ve been doing, called The Teddy Talks . I loved the idea, and have run it annually where I live, for the last 4 years! Whenever I’ve spoken about it with new friends or colleagues, almost everyone universally loves the idea. To help spread the initiative, I’ve launched a simple website this week: https://www.theteddytalks.com .
Part of the reason this project was made, was because of indecision/conflicts of what should be watched. To help with that, I’ve added a feature request of a “I’m feeling lucky!” button that will choose a random set of percentages for “rom” to “com”. Have fun at https://www.rom-to-the-com.com .
A lot of questions people had was about where I got the data from, and would then often check for films being included, and they weren’t always! You’re now able to add your own suggestions: Have fun at https://www.rom-to-the-com.com .
A few years ago, some friends and I went on a road-trip to Wales. How we came up with the idea has long been forgotten, but the idea lived on. I bough the domains immediately after that trip, and held onto them until now! What’s different from now is that LLMs have hit it off, and solved the data problem for this side-project. Before reading on, check it out: Rom-to-the-Com . Here’s a screenshot:…
This will be a brief overview of how I attempted to fine-tune an LLM on my personal messages. The goal was to 1) go through the data preparation, experimentation, and evaluation loop end-to-end, and 2) be able to side-by-side evaluate my responses to responses from the LLM. This was out of curiosity and also to practice some data and ML engineering! I’m in the process of transitioning…
For this website, I currently use NimblePublisher 1 for the content management. By default, it uses Earmark for Markdown and different Makeup packages for syntax highlighting. Having tried to write a Makeup parser 2 , and being a big fan of Tree-sitter, I was happy to hear about Autumn 3 and MDex 4 . Autumn uses a Rust crate under-the-hood, through Rustler, for Tree-sitter-based syntax…
Recently I reminded myself of TF-IDF and the relatively simplicity of it, in and of itself. Having considered a Python implementation, and wanting to write something in Flix 1 2 , I thought this could be a good opportunity. Why is it partially wrong? Well, because I wrote it, wasn’t 100% happy with the results, but the intent was to quickly try something in Flix! Here it is: type alias ID = String…
If you’re getting the following error when going through a AWS SageMaker Studio tutorial 1 , here’s a quick solution I’m writing down, to save someone else searching. It’s as obvious as you’d expect! The error: ModuleNotFoundError: No module named 's3fs' Earlier in the notebook, install the package: %pip install s3fs Then, import it: import s3fs Deploy a Machine Learning Model to a Real-Time…
How I started programming This is about my journey with programming languages from imperative to functional to (potentially) logic. Similar to most people, I got into programming with imperative languages. They were the programming languages (PLs) that I used at my first few jobs—specifically, ColdFusion, PHP, Java, Python, JavaScript, and some others. Back in high school, I remember our IT…
Having switched to using Elixir and NimblePublisher for the backend of my personal website, I’ve needed to improve the availability of Makeup parsers. Firstly, starting with Swift, with makeup_swift . It’s incredibly bare bones, so far. The approach so far is to be fairly true to the Swift Language Reference 1 . The prioritisation is hopefully on the more common parts of the language.…
Previously 1 2 , I wrote about a paradigm where you had daemon which had multi-UIs that interacted with it. For some time I had wanted to quickly be able to act on emails as they come in. Someone is working on a Raycast extension that uses AppleScript to interact with Mail.app 3 . Whilst it’s tractable, it was taking some time—and then I remembered Himalaya 4 ! After testing it out, I was happy…
I came across a blog post 1 about using hidutil on macOS. As much as I’m thankful for those who worked on Karabiner Elements, I’m happy to remove a dependency! This was a simple change to my dotfiles 2 . I had already used the builtin macOS ability to remap a modifier, which I had done from caps lock to ESC, which I had to remove. Mac keyboard with hidutil ↩…
This is one of those, “I don’t know why it broke but here’s what fixed it”. Safari started opening without any windows—private or otherwise. Using AppCleaner 1 , search for “Safari”. I removed everything except what’s remaining in this screenshot. If there’s permission issues, use a terminal or Finder. NB: Be wise in what you delete. AppCleaner ↩
Between Rust and Serde and Swift and Codable , it’s relatively easy to serialise and deserialise between the 2, using JSON. Whilst there aren’t shared definitions through a common format, such as Protobuf or MessagePack, for simple data it looks to be maintainable. serde_derive and Codable ideally save you writing encoders/serialisers and decoders/deserialisers. For Rust → Swift, I’ve so far had…
Recently I tried Emacs 29 1 and began slimming down my config 2 . Following the Tree-sitter starter guide 3 , I couldn’t figure out why I wasn’t able to start the appropriate mode. I would get errors along the lines of, Cannot activate tree-sitter, because language definition for ... . After double-checking file paths and names, I compared my local build output of the recommend build script 4 to…
I’ve relaunched this app! 1 The short version is that it’s the gitignore.io equivalent for Homebrew Brewfiles. There’s work to do, but, it’s in a reliable and reproducible state. Previously, it was on a VPS running FreeBSD and was using jails with Nginx and Puma. Now, it’s still on a VPS, but it’s running Debian and is using containers with Caddy and Puma. I do not regret using FreeBSD and jails.…
v0.0.1 was released on 2021-06-09 1 . Since then, I’ve been using it daily both at home and at work. After a lazy approach to auto-starting it 2 , I added a daemon definition for macOS with launchd . Recently as well, I added Emacs support. With these changes, I remembered to do a release, giving us v1! 3 Initial release ↩ dotfiles#7d46082baecb3e1440dd17c0c26fc3d2fd4e3cb6 ↩ v1 release ↩
I currently use Zola for this website and use Emacs as my editor with Projectile . Here’s a snippet from my dotfiles to add support for Zola projects to Projectile 1 . diff --git a/home/private_dot_config/emacs/init.el b/home/private_dot_config/emacs/init.el index c8d15dc .. a3f9260 100644 --- a/home/private_dot_config/emacs/init.el +++ b/home/private_dot_config/emacs/init.el @@ -797,7 +797,19 @@…