Philosophy

Hackable software is an approach to write, maintain and distribute minimal programs for personal use.

Software is:

  • doing not more and not less than what the user needs
  • made for users capable of reading and customizing its source code
  • distributed as source code, compiled by the user
  • not meant to be developed forever and its final state should be described by its feature set from the beginning
  • extended either by the user directly, or by applying source code patches distributed as diff files

Now… let’s start from the beginning.

What is hacking

hacker: n.

[originally, someone who makes furniture with an axe]

But today we will not be talking about carpenters, MIT hackers, or security researchers. But rather:

hacker: n.

1. A person who enjoys exploring the details of programmable systems and how to stretch their capabilities, as opposed to most users, who prefer to learn only the minimum necessary. RFC1392, the Internet Users’ Glossary, usefully amplifies this as: A person who delights in having an intimate understanding of the internal workings of a system, computers and computer networks in particular.

2. One who programs enthusiastically (even obsessively) or who enjoys programming rather than just theorizing about programming.

UNIX vs Enterprise

One can seemingly categorize all software in the world into programs that can do everything and programs that do only one thing.

Every program attempts to expand until it can read mail. Those programs which cannot so expand are replaced by ones which can.

Zawinski’s Law

This is a natural process in a commercial setting where more features mean more customers and more money. But this is not the only way.

There are programs that were designed to do one thing and do it well. You might know some of them, and most likely because they were originally a part of a UNIX operating system in the ’70s. I’m talking about command line utilities such as ls, cat, sudo, etc.

XKCD-149

The idea behind these minimal, modular programs is now known as Unix philosophy:

Software cafeteria

In context of hackable software, it’s important to notice that likely all software you use can do more than you need from it. Commercial software is designed as food in a college cafeteria - nobody particularly likes it, but it’s the best common denominator.

And minimalist Unix software won’t help there much, because on their own such tools are not very powerful - power emerges when they are combined together (output of one is input of another) to solve non-standard task. In this analogy simple programs are ingredients and in hands of a great cook they become a tasty meal.

Russian school kitchen, pots (likely) with black tea

How would a software from a fine dining restaurant look like? Building software for personal use of a single wealthy client is not a real thing, so it seems like we have to rely on big companies with lots of money and smart engineers to make good programs that would fit every user at once.

Wait, home cooking! It’s a big thing, but making custom programs from scratch is hard. The amount of foundational knowledge needed to write and understand the first ever line of code is monumental. More approachable way would be to rely on simple programs to do the heavy lifting and combine them to produce something meaningful. Brian Kernighan mentioned it in a recent talk about the history of UNIX, how powerful combination of a simple programs can be in the right hands. As an example, this command can be used to forcefully stop application conky:

ps aux | grep conky | grep -v grep | awk '{print $2}' | xargs kill

This is a great starting point to gradually explore the world of programming, along with visual scripting and problem solving games.

“I’m ready to write some code!” - you said. Good, the rest of this post is for amateur cooks and professional chefs who would like to make meals for themselves.

Suckless

The idea of tailoring programs to your own needs is not new. Most notable examples include programs released in 2006 by Suckless community: X11 window manager dwm, terminal emulator st, menu utility dmenu and others.

What distinguishes suckless software from other personal use programs developed today is that configuration is done directly in the source code. This also means that traditional way of distributing software in binaries doesn’t work - full source code and build instructions are needed.

So what is hackable software

Hackable software is the idea of writing programs for hackers. Let’s expand on the principles a bit.

Software is doing not more and not less than what the user needs

Every feature is implemented in the most simple and straightforward form: keep it simple, fast, and clear. It’s easier to protect simplicity when additional functionality is out of scope.

Software is made for users capable of reading and customizing its source code

It’s great when source code can be read and understood by the user in one evening. User manual documentation is not necessary, since concise code is better than plain text documentation. But hacking documentation is encouraged (via HACKING.md), providing help on building the program, high-level design overview, and other notes that would help grasping the code.

Software is not meant to be developed forever and its final state should be described by its feature set from the beginning

In many cases, code quality is compromised because of a wrong assumptions and dynamically changing requirements. Think about designing a bicycle not knowing it would be needed to make it a motorcycle along the way.

Software is distributed as source code, compiled by the user

Because users need to configure programs by modifying the source code, they need to have it in full. Also, please provide build instructions in case it’s not obvious from the build system config (npm run build or cargo build or zig build or make)

Software is extended either by the user directly, or by applying source code patches distributed as diff files

Extending functionality is often hard and requires architecture changes, so it might be a good idea to not break it for all user, even those who don’t need it. So it makes sense to keep additional functionality optional by providing patches. It is also encouraged to share your extensions with others who can find it useful.

Evaluation

Why would anyone use it, who is it for, and what are drawbacks.

The good

For developer:

For user:

The bad

Like any approach, hackable software has its limits and drawbacks:

Plug

This post is a formulation of design ideas and principles I followed developing hat - modal text editor for modern terminals.

Screenshot select Screenshot select
Screenshot completion Screenshot diagnostics

I’m an active neovim user, and I found that developing plugins is harder than it needs to be. 100 LOC nvim plugin could be two-line patch in hat. And after reading a bunch of neovim’s source code I can confidently say that it is not as simple at it looks (depending on how you read it, it might be a compliment to its UI).

Rant on abstraction

And developing neovim plugins or tweaking the config is problematic because it’s abstract. You don’t need fundamental knowledge to do that, but specific neovim knowledge. And more abstract technology becomes, the harder it gets to gain such knowledge.

We can go a level higher and talk about beginner neovim users who decide to start their journey with neovim distributions or even distribution managers. By choosing a distribution, user has to learn how to solve problems in context of that specific distribution. So much that core neovim knowledge might not suffice. Not sure if there is a term for this effect, but it’s often overlooked that abstraction does not make things simpler, rather hides complexity under the rug.

My advice to picking the right abstraction level is to go as low as it is reasonable for your problem/knowledge and be cautious of being too abstract. Abstraction is good until you need specifics of what it is hiding, then it falls apart.

Further reading