← All Writing
September 14, 20267 min read

How to Build Your Own Gmail Client (So Your Email Isn’t Tied to a Google Storage Plan)

Google’s answer to a full mailbox is a bigger storage plan, but you can keep a synced copy of your mail on a computer you already own and let Gmail keep doing the delivering.

YieldA Gmail-style web inbox that reads from a copy on your own computer, syncs your changes back to Gmail, and sends with a real undo button
DifficultyAdvanced (Gmail API, two-way sync, a search index, and a lot of “does it match Gmail?” checking)
Total Cook TimeA few focused sessions to build, then several rounds of testing before it was trustworthy as an everyday inbox

Ingredients

The Problem: Paying Rent on Your Own Email

Gmail’s free 15 GB is shared with Google Drive and Google Photos. When it fills up, the only path Google offers is a paid plan, and then a bigger one. Past 200 GB, the plans also bundle AI features you may not want.

Yearly cost of each planstorage onlybundled with AI$0$60$120$180$240Free 15 GB$0/mo · shared with Drive + Photos$0Basic 100 GB$1.99/mo$23.88Standard 200 GB$2.99/mo$35.88Google AI Plus 400 GB$4.99/mo · 2× Gemini$59.88Google AI Pro 5 TB$19.99/mo · 4× Gemini$239.88Google AI Ultra 20–30 TBfrom $99.99/mo · up to 20× Gemini$1,199.88Ultra’s bar is cut off: at $1,199.88 a year it runs about five times past the edge.
Google One personal plans, as of September 2026. Every tier is a yearly bill for keeping mail you could store on a disk you already own.

The alternative is to delete old mail and big attachments. People don’t, because deleting from Gmail feels final. Receipts, leases, warranties, the thread where someone agreed to something in writing: you can’t guess which ones you’ll need later.

Google Takeout gives you a one-time export, which is a snapshot, not a habit. What you want is a copy that stays current on its own and that you can read and search like email. Once you have that, cleaning up Gmail stops being risky, and staying on the free tier becomes realistic. Gmail goes back to being the post office instead of the storage unit.

Where Mine Landed

My version, Mailroom, behaves like Gmail closely enough that I stopped noticing the difference. It doesn’t clean up Gmail for me, and I didn’t want it to. What it changes is the risk: clearing out old mail and big attachments stopped being scary, because a searchable copy already exists outside Google.

One warning for your own build: before you delete anything from Gmail, make sure your copy is backed up somewhere else too. Leaving Google’s storage only works if your own is at least as durable.

Here’s how to build one.

Rule #1: Let Gmail Stay in Charge

The tempting version of this project is “replace Gmail”: run your own mail server, move your domain, never look back. Don’t. That means taking on spam filtering, deliverability, and a mail server that has to be up every minute of every day.

Gmail stays the post office. Your client is just a better window into it. Mail still arrives at Gmail and still leaves through Gmail. Your client downloads a copy, gives you your own inbox on top, and pushes your changes back. That one rule settles a lot:

How the Setup Works

The whole thing is four pieces, with one rule between them: only one piece is allowed to change your real mailbox.

YOUR COMPUTER AT HOMEGmaildelivers and sends mailsource of truthSync processruns in the backgroundthe only writer to GmailLocal storeraw email files (.eml)+ rebuildable search indexWeb appyour inbox, search, composeholds no Gmail keysYour browserlaptop or phone, anywhereGmail appon your phone, unchangedmailchangesreads mail,queues changesprivatenetwork
Gmail still does the delivering. Everything inside the dashed box runs on a computer you own, and only the sync process can touch your real mailbox.

Step 1: Keep the Copy in Sync (Twice)

Gmail offers a change feed: ask what changed since last time and it tells you. Build on it, but don’t trust it alone. It occasionally skips events, and a missed event is never sent again. You’ll see it as messages you read in Gmail still showing as unread in your client.

The fix is a second, slower loop that re-asks Gmail directly (“which messages are unread right now?”) and corrects anything that drifted. The fast feed keeps you current; the slow check keeps you honest.

🔧 Developer section: sync gotchas

Step 2: Make Search Match Gmail, Not Just Look Like It

You’ll want Gmail’s search syntax to work: from:, has:attachment, is:unread, - for “not.” To test it, run the same query in both and compare which threads come back, not how many.

Watch for word stemming: many search engines treat “order,” “orders,” and “ordered” as one word. Gmail doesn’t. A query can return the exact same count as Gmail, which looks like a pass, while the threads don’t overlap at all. Also make sure a search your code can’t understand says so, instead of showing zero results. An empty list looks exactly like “nothing matched.”

Step 3: Add Sending, With an Undo That Works

Replicate the parts of Gmail you actually use: replies that stay in the right thread, drafts that are real Gmail drafts (start on your laptop, finish on your phone), forwards that keep their attachments. Sent mail shows up in Gmail’s Sent folder and syncs back down like anything else.

Undo send works the way Gmail’s does: hold the message for 30 seconds before it really goes out. A common trap: undo can look like it worked while the email still goes out, if you hit it in the split second the sync process is picking the message up. The screen says cancelled, the database says cancelled, and the email sends anyway. The fix is small:

🔧 Developer section: check that your claim actually won

Step 4: Keep It Off the Internet

A page with all your email behind it shouldn’t be on the public internet, even behind a password. Run it on a private network, such as Tailscale, instead, which connects only your own devices. Your phone and laptop can reach it from anywhere; to everyone else, there’s nothing there. Keep your Gmail token outside the code, and keep mail data out of git entirely.

Step 5: Test It Like a User, Not a Checklist

Before switching over, have Claude agents use your client next to real Gmail and report every difference. Tell them to check that things work, not just that they show up. A few tests worth adding to the list:

“It loads” is not “it works”

Do the thing a person would actually do: click the link, download the file, run the search, and read what comes back.

Build Notes

What went fast

What needed patience

Try Building One

If your Gmail is creeping toward the storage limit, this is a very buildable project with Claude Code, as long as you start with the rule: Gmail delivers, you keep the copy. If you build one, or get stuck partway, tell me about it. I’d like to hear what you ran into.

← Back to all writing