iex> Ken</>

Local-first is an argument, not a feature: no server, no account, no sync

iex> Blog.post!("20260916-local-first-is-an-argument")
%Post{
title: "Local-first is an argument, not a feature: no server, no account, no sync",
date: ~D[],
author: ,
reading_time: 9, # minutes
body: """

Most of the software I build is missing the same three things. There is no account. There is no sync. There is no cloud anything.

People read that list as a roadmap. Things I have not got round to, features that arrive once the project is serious. It is not a roadmap. Those three absences are the product, and I have been building instances of an argument I have never actually written down.

There is one exception, and I will come to it at the end, because it is the case that tests whether the argument is worth anything.

Here it is first, in the order the benefits arrive: one you feel today, one that holds always, and one that matters in twenty years.

It is simply better software

Start with the unglamorous part, because it is the part you notice first.

Fardel opens instantly. There is no sign-in, no session check, no spinner while something three thousand kilometres away decides whether I am still me. It works on the train, in a basement, on a plane, during an outage at a company I have never heard of. Every interaction is a function call against a file on the same disk as the code, so the latency is not low, it is absent.

None of that is clever engineering. It is what you get for free when you delete the network. Local apps feel fast because they are doing dramatically less, and most of what they have stopped doing was never for you in the first place.

The honest framing is not "I built something fast." It is "I removed the slow part, and the slow part turned out to be optional."

Privacy that isn't a promise

Every privacy policy is a statement of intent. It describes what a company currently plans to do with data it currently holds, and it can be revised, reinterpreted, or inherited by an acquirer with different plans. I have written about how little that sentence is worth once the business model needs it to mean something else.

A missing server is not a statement of intent. It is a statement of fact.

There is nothing to leak because there is no store to breach. Nothing to subpoena, because I hold none of it. Nothing to sell if I run out of money, nothing to quietly start analysing when a metrics dashboard looks flat, nothing that changes when I change my mind. The strongest guarantee software can offer you is not a promise to behave. It is an architecture in which misbehaving is not available.

A caveat, or I would be talking out of both sides of my mouth. I pay Proton for my email, and email is emphatically not local-first. It is a network protocol. My messages sit on a server I do not own, and what I get there is encryption and a Swiss jurisdiction rather than absence.

That is only not a contradiction if the principle is stated properly, and the version I gave above is too strong. The principle is not "never use a server." It is: concede exactly as much as the problem requires, and not one step further.

Email cannot exist without a server, so the strongest guarantee available is that the server cannot read what it holds, and I take that deal gladly. Household finances can work perfectly well without one. Accepting a server there would mean giving up the stronger guarantee in exchange for nothing at all.

Ranked honestly: no server beats a server that cannot read your data, which beats a server that merely promises not to. Nearly all software sits in that third tier, for problems that never required a server in the first place. The argument is not that tier one is the only acceptable place to be. It is that you should not be further down the list than your problem forces you.

No server means no business model

This is the one that connects to everything else I have been writing about.

A local app has no hosting cost, no per-user marginal cost, nothing that scales with usage. That sounds like a description of a weak business, and it is. There is no rent to charge because I am not providing an ongoing service. There is no metered resource to meter.

Which means there is also no pressure. I argued recently that advertising is what a company reaches for when subscriber growth flattens, and that the pattern is structural rather than a failure of character. The most reliable way not to be subject to that pressure is to build something that never generates it: no recurring revenue to protect, no growth curve to defend, no board expecting a number that the honest version of the product cannot produce.

The cost is real and I am not going to pretend otherwise. Software with no business model has no business model. That is why I ask for support rather than sell subscriptions, and why the answer to "how does this make money" is "it does not, particularly."

But the trade is legible, which is more than most software offers. You get a tool that has no structural reason to ever turn on you. I get no revenue. Nobody is being quietly charged in a currency they did not agree to.

Your data outlives me

This is the argument I actually find decisive, and it is the one nobody asks about.

Fardel stores everything in a single SQLite file. Not a proprietary format, not a database that needs a server process, not an export you have to remember to run. One file, in a format with a published specification, that the project intends to support into the 2050s, and that essentially every programming language can already read.

So consider the worst case, which is not a breach or a lawsuit but simple abandonment. Suppose I lose interest. Suppose I get bored, or ill, or hit by the proverbial bus. What happens to your data?

Nothing happens to it. It is a file on your disk. It opens in anything that speaks SQL, twenty years from now, with no involvement from me whatsoever, because there is nothing to involve me in. My continued participation was never load-bearing.

Compare that to the normal case. When a cloud product shuts down you get an email, a wind-down date, and an export in whatever shape the company felt like producing. Your data was always a rendering of rows you had no direct access to, and the rendering stops when the company does. The thing you thought you owned turns out to have been a view.

What it costs you

Everything above is the case for the design. Here is the bill, and I am not going to dress any of it up as a secret feature.

Your data is on one machine. Fardel is on my laptop. It is not on my phone, so I cannot check a balance while standing in a shop deciding whether to buy the thing. If I am away for a week and left the laptop at home, I am simply not doing any bookkeeping that week. For a category of app that benefits enormously from being reachable at the moment of the purchase, that is not a small loss.

"Household" is doing suspicious work in the description. Fardel tracks household finances and possessions, and a household contains more than one person. Right now it serves exactly one of them. Shared access is the thing multi-user cloud software does effortlessly and the thing a single local file does not do at all, and I have no good answer beyond the one that is coming in the next section.

Backup is your problem again. Cloud services solved backup so completely that most people have forgotten it was ever a problem, and that is a real service rather than a trick. A single SQLite file on a single disk is one drive failure, one spilled drink or one stolen bag away from nothing. Cloud products do this invisibly and correctly. I hand it back to you, and most people, including me on a bad week, will not do it reliably.

Recovery is manual. Lose the machine and the recovery story is not "sign in on the new one." It is "restore the backup you hopefully made," which is the same sentence as above wearing a different hat.

Some of these have answers. A file is easy to sync with tools you already trust, and encrypted backups are a solved problem if you bother. But "if you bother" is carrying real weight in that sentence, and pretending otherwise would make this an advertisement rather than an argument. The honest summary is that local-first trades convenience you would definitely have used for guarantees you will probably never notice, and that trade is not obviously correct for everyone.

Where my own argument breaks

Here is the exception I promised. I do not apply this universally, because one use case defeats it.

Notes need to be on your phone and your laptop and to agree with each other. That is a genuine requirement, not a preference, and it cannot be satisfied by a file on one machine. So NoirNotes, the one app of mine that needs sync, has a server and a real database. The compromise there is to encrypt everything in the browser before it leaves, so the server stores ciphertext it holds no key for. That is a weaker guarantee than "there is no server", and I would rather name it as weaker than blur the two.

A note on the term while I am being pedantic about my own claims. "Local-first" was coined by the Ink and Switch essay, and their version includes seamless sync and collaboration among its ideals: the network is optional, not absent. Mine are stricter than that, and strictly speaking mine are local-only. I use the word anyway because it is the word people have, but the distinction matters, and sync is exactly where most local-first claims quietly put the server back.

The three missing features

So: no account, because there is nobody to be an account with. No sync, because sync needs a server and a server needs a reason to exist beyond your convenience. No cloud, because the cloud is someone else's computer and the terms are theirs.

Those are not gaps in the roadmap. They are the roadmap, read correctly.

"""
}
iex> Blog.Post.tip()
"If this post saved you time or taught you something, please consider buying me a coffee on Ko-fi ☕. It keeps me writing in the open."
iex> Blog.Post.adjacent()
%{
next: :nil
}
iex> Blog.archive()
iex> Blog.subscribe(:atom)
"/blog/atom.xml" # paste into any RSS reader
iex> Ken.tip()