Blake Smith

create. code. learn.

»

You Should Host Your Own Code Forge

Back in April, GitHub shared a staggering graph of their scaling challenges:

GitHub Repository and Commit Expansion

LLMs are producing code at an almost frightening rate, and if you use GitHub on a semi-frequent basis, you’ll know that it’s down quite regularly these days as a result of the onslaught.

For my own personal work, rather than tolerate the GitHub instability, I’ve instead opted to self-host my own Forgejo instance in my basement server rack.

Smith Cottage Internal Forgejo instance

This is yet another important step in reclaiming my own computing sovereignty. While the world is busy spraying gigatons of slop all over GitHub, I’m taking back ownership of the code that’s always been mine. Growing in my craft means not just owning the work, but also building the tools and the environment that the work gets produced in. I aspire to build the Hans Zimmer music studio of computing.

Hans Zimmer Music Studio

Running my own private code forge has been a joy, especially with “push to create repository” Forgejo feature turned on. This enables any whimsical hairbrained idea to quickly become a git repository stashed for my own private creation. If I want to live a creative life, full of Big Magic, I have to start with the basics: doing a huge volume of work. A private code forge is a great scratch-pad to sink ideas into.

If you’re looking for a sign to bring your code “back home”, either personally, or at your company, the graph above might be the right signal that it’s time to take a look at self-hosted options. Forgejo is definitely worth a look!


»

The Server Rack Expands

The server rack continues to expand! In an effort to buy hardware before the AI bubble continues to drive up computer hardware prices, I’ve added three more Minisforum UM690L mini PCs to the basement rack (this time in black!).

Expanded Server Rack

I’ll be using this new batch of machines to separate a testing cluster from “production” infrastructure that runs the stuff in the house (Home Assistant, Jellyfin, etc.)

I haven’t yet isolated the network switching / routing, but that’ll come at some point.

In the meantime, I’ll keep on cheering for the AI bubble to crash in hopes of computer hardware returning back to earth.


»

More Functionality, Less Dependency

One thing that’s still underrated in programming: Skipping a library dependency and coding something small that you need directly. No over-generalized library, no unecessary abstractions, no library dependency hell – just straight forward code that solves your specific problem in the most direct way possible.

To put a longer story on it: I’ve been working on provisioning VMs with cloud-init NoCloud for the cloud orchestration platform I’m building. To bootstrap VM state from a fresh image, I need to expose a VFAT disk from the host hypervisor to the guest with the VM’s metadata (Network setup, hostname, users, etc.). The disk image needs to be dynamically built during VM provisioning time, and injected with the correct instance information inside the VFAT volume for the guest to read.

VM provisioning happens in Rust code, so there are so a few different ways I considered implementing this:

  • Build up a directory on a local scratch temp dir with the instance metadata files, and shell out to mkfs.vfat with something like std::process to turn the directory into a vfat volume.
  • Use an existing Rust library like fatfs to write the instance metadata files into a new FAT filesystem

Both of these require taking on external program or library dependencies.

I went a different way instead. I made a single zero-dependency Rust function that builds up the FAT filesystem in memory, and writes out the bytes directly to a file on the host.

It’s a few hundred lines of code, most of which are comments and tests. I read an old Microsoft FAT specification, wrestled with the hackish oddities of Long Filename support, and got something working in a few hours time.

What’s missing from this implementation? So much!

  • Only supports a fixed number of FAT filesystem clusters
  • Only supports fixed filesystem sector sizes
  • Only supports a hard-coded root directory size
  • Hardcoded filesystem label only (It has to be the string cidata to work with cloud-init anyways!)
  • No read support
  • Basic FAT12 only (No larger files with FAT32)
  • No general file write interface: Just supports writing the 4 metadata files we need and that’s it
  • Immutable writes only, no updates / mutations.

But this is all I need (and will probably ever need!). If I ever start doing anything fancier and dynamic with FAT filesystems, I can re-evaluate.

Instead, I get no breaking API changes from upstream libraries, no CVEs to patch, no license changes or rug-pulls, and code that’s straight forward and easy to fix and debug directly. Why carry around the extra weight of more dependencies for such a tightly scoped problem? We’re only writing 4 small metadata files to the vfat disk image after all.

Was this the quickest way to solve the problem? Probably not! Slapping in another dependency via cargo add and gluing some more APIs together would have probably gotten the problem “out of the way” faster from the start. But the initial expediency shouldn’t overshadow the benefits of building something tidy, compact, and definitionally simple like this.

I want less duct tape and glue in my programs. I want less moving pieces and maintenance. I want code that’s mine. I want systems that are load bearing and ready for production. I want more functionality, with less dependency.


» all posts