Skip to content

Repository files navigation

InboxSweeper

Clean years of junk out of your inbox — for free, without handing your email to anyone.

InboxSweeper deletes old promotions and newsletters in bulk and unsubscribes you from the noise. Built for Gmail today, with experimental support for Yahoo and other IMAP inboxes (see the note below). It runs entirely on your own computer; your email is never uploaded anywhere. Deleted mail goes to Trash, so you can always get it back.

  • 🆓 Free and open source — no account, no subscription, no catch.
  • 🔒 Private — everything happens on your machine; nothing is sent to a company.
  • 🧹 Cleans by who sent it — clears the junk without touching your receipts, orders, or bookings.
  • ✉️ Actually unsubscribes — it uses the real one-click unsubscribe, not just delete-and-hope.
  • ♻️ Safe — deletions go to Trash (recoverable), and bank, security, and government email is protected automatically.
  • 🖱️ Four ways to use it — a double-click web app, a one-file Windows .exe, your AI assistant (Claude / Codex), or the terminal.

⬇️ Get it: Download the app (ZIP) then double-click the launcher inside · or the one-file Windows .exe · or pipx install inboxsweeper if you live in a terminal — full options: Claude & Codex · terminal.

How this is different from other "inbox" cleaners

There are a lot of inbox tools — browser extensions, Gmail-only add-ons, cloud services. Most ask you to "Sign in with Google" and hand a company ongoing access to your mailbox. InboxSweeper is built the opposite way:

  • No OAuth / no "Sign in with Google". You paste a scoped app password once (stored in your OS keychain), never grant a third party access to your account. Revoke it anytime and the tool stops instantly.
  • Not a browser extension. Nothing installs into your browser; it's open-source code you run yourself and can read line by line. No extension that can change hands or silently update what it does.
  • Nothing is uploaded — not even a token. Your mail, credentials and tokens never leave your machine. No cloud copy of your inbox, no server holding your access. (The only thing sent is an anonymous, opt-out sweep counter — counts + version, never addresses or content.)
  • Works beyond Gmail. Gmail fully supported, plus experimental Yahoo and any IMAP inbox — not locked to one provider.
  • Focused, not bloated. Clean by sender, real one-click unsubscribe, deliberate report-spam — and nothing gimmicky bolted on.
  • Free and open source, no strings. MIT, no signup, no OTP, no phone number, no subscription.

⚠️ Read the built-in safety rules before you run a sweep. The one rule that matters most: recognize a sender → unsubscribe; don't recognize it → report spam, never unsubscribe. Clicking unsubscribe on real spam confirms your address is live and gets you more spam.


⚡ Three cleaning modes — you pick the aggression

The heart of InboxSweeper: one dial from cautious to ruthless. The wizard asks which mode you want before it touches anything. Banks, security, payments, receipts and government mail stay protected in every mode — the dial only changes how far back it reaches and how many senders it clears per run.

Mode 🦥 Sloth 🧹 Normal 🔥 MadMax
safest recommended aggressive
Reaches mail older than 2 years mail older than 1 year all promo mail, incl. recent
Senders / run 25 50 100
python3 inboxsweeper.py wizard              # asks you to pick a mode
python3 inboxsweeper.py sweep --mode madmax # or set it directly on any command

Every sweep goes to Trash (recoverable ~30 days) and previews the count before anything moves. Hit the per-run cap? It tells you exactly how many senders remain — just run it again to clear the next batch.


🎯 Three actions — and when to use each

The mode above decides how far back to reach. Once you've scanned, you choose what to do with a sender. There are three, and picking the right one matters:

Action Use it when… What it does
✉️ Unsubscribe you recognize the sender Real one-click / mailto unsubscribe — stops it at the source
🗑️ Move to Trash you're just done with it Clears the backlog to Trash (recoverable ~30 days)
🚩 Report spam you don't recognize it Trains your provider's filter so future mail auto-junks

The one rule that matters most: recognize a sender → unsubscribe; don't recognize it → report spam, never unsubscribe. Clicking unsubscribe on real spam confirms your address is live and gets you more spam. That's why Report spam is a separate, deliberate action — in the app it's its own tab that starts with nothing selected, and in the terminal it's the spam command (or option 2 in the wizard). It never runs in bulk by accident, and it can never touch a financial/security/government sender.


Four ways to use it

Pick the one that fits you:

You are… Path In short
Anyone — no tech needed (recommended) 🖱️ Web app Download the ZIP, double-click the launcher. Opens in your browser. → Web app
On Windows, want zero setup 📦 One-file .exe Download InboxSweeper.exe, double-click. → Windows .exe
A Claude Code / Codex user 🤖 Claude skill Install the skill and just ask. → AI agent
A coder ⌨️ Terminal pipx install inboxsweeper, then one command. → Terminal

🖱️ The web app (for everyone)

The same point-and-click interface on every platform. How you start it differs by computer — and on a Mac the honest answer isn't the one you'd expect, so it's spelled out below.

🪟 Windows — double-click, nothing else

  1. Download the app: on the GitHub page, click the green Code button → Download ZIP (or the direct link).
  2. Unzip it — right-click → Extract All.
  3. Double-click InboxSweeper.bat. Windows may warn once (what to click).
  4. A small window opens and InboxSweeper appears in your browser. Keep it open while you use it.

Or skip Python entirely with the one-file .exe.

🍎 Mac — copy two lines, once

Why there's a step at all: Macs refuse to open apps unless the maker pays Apple $99 a year. This one is free and doesn't. So instead of fighting that, you install it a different way — it takes about a minute, and you never see a warning.

You'll use an app called Terminal. Don't worry about what it is; you're pasting two lines.

Step 1 — Open Terminal. Hold ⌘ (Command) and press Space. A search box appears in the middle of your screen. Type Terminal and press Return. A plain window opens with some text and a blinking cursor.

Step 2 — Install it. Copy this line, paste it into that window, press Return:

pip3 install inboxsweeper

Text will scroll past for 20–30 seconds. That's normal. Wait until the blinking cursor comes back.

Says command not found? Your Mac needs Python first — it's free and takes 2 minutes: download it from python.org/downloads, open the file, click Continue → Install, then come back and repeat Step 2.

Step 3 — Start it. Copy this line, paste it, press Return:

inboxsweeper serve

Your web browser opens with InboxSweeper in it. That's the whole thing — from here it's all clicking. Leave the Terminal window open while you use it; closing it stops the app.

Every time after this, you only do Steps 1 and 3. It's already installed.

I already downloaded the ZIP and want to use that instead

Double-clicking InboxSweeper.command will show "Apple could not verify…" — that's the wall described above. To clear it, open Terminal (Step 1) and paste this, then press Return:

xattr -d com.apple.quarantine ~/Downloads/inboxsweeper-main/InboxSweeper.command

Now double-click InboxSweeper.command in Finder and it opens normally, every time.

If you get No such file or directory, your folder is somewhere else: type xattr -d com.apple.quarantine (with a space at the end), then drag the InboxSweeper.command file from Finder into the Terminal window — it fills in the correct path for you — then press Return.

You may also see advice to right-click → Open, or to use System Settings → Privacy & Security → Open Anyway. Apple removed the first in macOS 15, and the second is built for .app bundles and often shows no button for files like this one. If it doesn't work for you, nothing is broken — use the command above.

🐧 Linux

pip install inboxsweeper && inboxsweeper serve, or double-click InboxSweeper.command from the ZIP.

It installs its one dependency automatically. Don't have Python? The launcher opens the download page and walks you through the free, one-time install — then just double-click again. From there it's all clicking: paste an app password once (it shows you exactly how to get one), Scan, tick the junk senders, and hit Move to Trash or Unsubscribe. Nothing is uploaded; deletions go to Trash.

📦 Windows .exe (nothing else to install)

Prefer a true one-file download with no Python step at all? On Windows:

  1. Download InboxSweeper.exe. Chrome/Edge may block the download itself ("isn't commonly downloaded") → open the Downloads bar, click the next to the file → KeepKeep anyway.
  2. Double-click it. Windows SmartScreen may warn (free/unsigned) → click More info → Run anyway.
  3. It opens in your web browser — pick Gmail or Yahoo and follow the on-screen steps.

Want proof it's really from this repo? Every release is built by a public GitHub Actions workflow that records signed build provenance. With the GitHub CLI:

gh attestation verify InboxSweeper.exe --repo elixir-bash/inboxsweeper

That confirms the exact file you downloaded was built from this source, by that workflow — which is most of what a code-signing certificate would tell you, without the $99/year.


🚧 First run: what your computer will say

InboxSweeper isn't code-signed — a certificate costs $99/year and this is free — so your browser and OS treat it as an unknown app. Nothing is wrong. Each wall and the one button past it:

What you see Where What to click
"isn't commonly downloaded" / "can't be downloaded securely" Chrome/Edge, during download Downloads bar → KeepKeep anyway
"Windows protected your PC" Windows, first launch More infoRun anyway
"Apple could not verify…" / "unidentified developer" Mac, first launch Click Done, then System Settings → Privacy & Security → Open Anyway

Mac — read this first. If you're willing to paste one line, skip all of it:

pip3 install inboxsweeper && inboxsweeper serve

A pip install carries no "downloaded from the internet" flag, so Gatekeeper never gets involved — no warnings, no Settings, no approval. Everything below is only for people who'd rather not.

The click-through route, and its catch. The old advice (right-click → Open) was removed by Apple in macOS 15. The replacement is Apple's documented flow — but be warned it's designed for .app bundles and is unreliable for launcher files like ours; the approval button often doesn't appear at all. If that happens to you, nothing is wrong with your Mac — use the one-liner above:

  1. Double-click InboxSweeper.command. macOS blocks it. Click Donenot Move to Trash, which deletes the launcher.
  2. Apple menu → System Settings → Privacy & Security. Scroll down to the Security section.
  3. You'll see a line about InboxSweeper.command being blocked → click Open Anyway.
  4. Enter your login password (or Touch ID), then click OK.
  5. Double-click the launcher again → Open.

⏱️ Do steps 1–4 in one sitting. Apple only shows the Open Anyway button for about an hour after the blocked attempt. If you come back tomorrow the button is gone and it looks broken — just double-click the launcher again to restart the clock.

After this, macOS remembers it: future double-clicks open normally, like any other app.

On macOS 14 Sonoma and older, the old route still works: right-click (or Control-click) InboxSweeper.commandOpenOpen.

Fastest route if you're comfortable in Terminal (any macOS version) — this removes the "downloaded from the internet" flag, so the launcher just opens:

xattr -d com.apple.quarantine ~/Downloads/inboxsweeper-main/InboxSweeper.command

Hit something not listed here? Open an issue with your OS, browser and the exact wording — that's the fastest way to get it fixed.


AI coding agents (Claude Code, Codex, Jules, Cursor…)

This repo ships ready-made instructions so an AI coding agent can drive the tool for you. See integrations/ for the full map — in short:

  • Claude Code — install as a skill (bundles the script so it's self-contained):
    mkdir -p ~/.claude/skills/inboxsweeper
    cp integrations/claude-code/SKILL.md inboxsweeper.py ~/.claude/skills/inboxsweeper/
    Then just ask Claude: "declutter my gmail" / "unsubscribe from these senders" / "report these as spam".
  • Codex, Jules, Cursor, Gemini CLI & other agents — they all read AGENTS.md automatically. Drop inboxsweeper.py + AGENTS.md in your project (or run the agent from this repo) and just ask. It documents the commands, the safety rules, and the recommended flow.

The terminal (for coders)

If you just want a clean inbox and don't care how it works:

pipx install inboxsweeper      # or: pip install inboxsweeper

inboxsweeper wizard                    # Gmail
inboxsweeper wizard --provider yahoo   # Yahoo

On a Mac this is also the path of least resistance — a pip install carries no "downloaded from the internet" flag, so there's no Gatekeeper unlock to do.

Prefer to run it from source?
git clone https://github.com/elixir-bash/inboxsweeper && cd inboxsweeper
pip install -r requirements.txt
python3 inboxsweeper.py wizard

The wizard walks you through everything, in plain language:

  1. First it asks what you want to do: Clean up (unsubscribe + move to Trash) or Report spam.
  2. If it's your first run, it prints the exact steps to create an app password and asks you to paste it once (hidden). It's stored securely (macOS Keychain, or a locked file).
  3. It scans your mailbox and shows your noisiest bulk senders.
  4. Clean up asks — in y/N prompts — whether to unsubscribe (first) then move that mail to Trash. Report spam starts with nothing selected and asks which senders to flag. Nothing happens without your yes, and it always previews counts before moving anything.

That's the whole journey. Everything below is for people who want the individual commands.


1. Prerequisites

  • Python 3.9+
  • pip install -r requirements.txt (only requests, and only for unsub-run)
  • A Gmail or Yahoo account with 2-Step Verification ON (required for app passwords)

⚠️ Yahoo / other IMAP is experimental. It works, but with a big caveat: Yahoo's IMAP only exposes your ~10,000 most-recent messages per folder — older mail simply isn't reachable, and Yahoo's server-side search is limited. For a large Yahoo backlog, use Yahoo's own web unsubscribe (Yahoo Mail → Settings → More Settings → Subscriptions), which isn't capped. Gmail has no such limits — that's the primary, fully-supported target.

Setup (if you still want it): create an app password at login.yahoo.com/account/securityCreate app password under "External connections", confirm IMAP is on (Settings → More Settings → Mailboxes), then add --provider yahoo to any command.

2. Create a Gmail app password (step by step)

You never give this tool your real Google password. You create a scoped app password. (Or skip this section entirely and let python3 inboxsweeper.py setup walk you through it.)

  1. Turn on 2-Step Verification: myaccount.google.com/security2-Step Verification → follow the steps. (App passwords don't exist without it.)
  2. Go to myaccount.google.com/apppasswords.
  3. App name: inboxsweeperCreate.
  4. Google shows a 16-character password like abcd efgh ijkl mnop. Copy it. (You can always revoke it later from that same page — the tool stops working instantly.)
  5. IMAP is already enabled on modern Gmail (no toggle). If you have an old account: Gmail → ⚙️ See all settingsForwarding and POP/IMAPEnable IMAP → Save.

3. Store the credentials

Option A — macOS Keychain (recommended on Mac). The value is prompted and never echoed:

security add-generic-password -U -s gmail_cleanup      -a you@gmail.com -w   # paste app pw, hidden
security add-generic-password -U -s gmail_cleanup_addr -a account       -w you@gmail.com

Option B — environment variables (any OS). Put spaces-removed password here:

export GMAIL_ADDR="you@gmail.com"
export GMAIL_APP_PASSWORD="abcdefghijklmnop"

The tool checks env vars first, then Keychain.

4. Use it

# 1. See where the noise is
python3 inboxsweeper.py counts

# 2. Rank the noisiest bulk senders (default query = the safe bulk set)
python3 inboxsweeper.py profile --top 40

# 3. Preview a deletion (DRY RUN — nothing moves)
python3 inboxsweeper.py sweep --senders linkedin.com

# 4. Actually move them to Trash (30-day recovery)
python3 inboxsweeper.py sweep --senders linkedin.com --yes

# 5. See each sender's unsubscribe method, then unsubscribe from specific ones
python3 inboxsweeper.py unsub-list --top 40
python3 inboxsweeper.py unsub-run --domains "email-marriott.com,mail.zillow.com,uber.com"

Commands

Command Purpose
wizard Start here. Guided: first pick Clean up (unsubscribe + Trash) or Report spam
setup Store credentials for a provider (prints the app-password steps)
counts Landscape of your mailbox (sizes by category / bulk)
profile --top N Tally the noisiest bulk senders
unsub-list --top N Senders + unsubscribe method (1click/mailto/weblink/none)
sweep [--senders a.com,b.com] [--days 365] [--yes] Move a sender's old mail to Trash. Dry-run unless --yes.
unsub-run --domains a.com,b.com Execute unsubscribe (one-click POST or mailto/SMTP)
spam --senders a.com,b.com [--yes] Report specific senders as spam (trains your filter). Deliberate & opt-in — never bulk. Dry-run unless --yes.

Add --provider gmail (default) or --provider yahoo to any command. sweep targets by sender (the safe way — see the built-in safety rules); omit --senders to target every non-protected bulk sender. Protected senders (financial/security/gov/transactional) are always skipped.

5. Recommended flow

  1. counts → find the mass (often it's category:updates, which hides receipts).
  2. profile → rank bulk senders.
  3. Classify each into PROTECT / DELETE / KEEP-BY-DEFAULT using the built-in safety rules.
  4. sweep (dry-run → --yes) the DELETE set. Verify a sample in Gmail → Bin.
  5. unsub-listunsub-run the recognized DELETE senders.
  6. Unrecognized/spammy senders: report spam in Gmail — don't unsubscribe.
  7. Add Gmail filters for the worst repeat offenders so the backlog can't rebuild.

The story behind it

I have a habit of pointing a bit of code at the everyday annoyances in my life. For the better part of 15 years, my inbox was the one that never stayed solved. It started the way these things always do: a small IMAP script to nuke the obvious promotions. Then another for newsletters. Then a cron job, once a month, to hold the pile back while I wasn't looking.

The trouble is email never sits still. Every so often something underneath would shift — Google killed off "less secure app" access and I had to move everything onto 2-factor and app passwords; the special folders never behaved the same across providers ([Gmail]/Trash here, "Bin" there); IMAP search would quietly change what it returned; Yahoo would only hand back your ten thousand most-recent messages; a provider would tighten rate limits or rotate a port. The cron would break, usually silently, and I'd only notice weeks later when the clutter had crept back in. So I patched. Year after year, one more fix stacked on the last.

But the part I could never fully automate away was the careful bit — the plumbing and cleaning. Bulk-deleting email is easy; bulk-deleting only the junk and never once touching what matters is hard. A bank statement, a flight confirmation, a receipt I'd need at tax time — those can't land in Trash by accident. So most of my years of tinkering weren't about deleting faster; they were about drawing the line ever more carefully: expanding the list of protected senders, teaching it to recognize a financial or government domain, making sure even the most aggressive sweep still stepped around anything critical.

This year, working with AI, I finally stopped patching the symptoms and fixed the core. The fragile scripts became a real app — the cleaning modes, the safe-by-default sweeps that always go to Trash, the automatic shield around bank, security and government mail, real one-click unsubscribe, a browser UI. The whole construct I'd carried in my head for a decade, done properly. And then the step I'd never gotten around to alone: making it open source, so anyone can clean their inbox the same careful way — for free, and without ever handing their mail to a company.

That's what InboxSweeper is: years of doing this the hard way, finally turned into something anyone can use.

How it works

  • Connects over IMAP and searches with Gmail's X-GM-RAW extension, so any Gmail search query works server-side.
  • "Delete" = IMAP MOVE to the Trash/Bin folder (auto-detected via the \Trash special-use flag), which is Gmail's 30-day-recoverable trash — not a permanent delete.
  • Unsubscribe reads the message's List-Unsubscribe / List-Unsubscribe-Post headers:
    • one-click → HTTP POST with body List-Unsubscribe=One-Click (RFC 8058).
    • mailto → sends an unsubscribe email via SMTP using your app password.
    • weblink-only → reported for manual handling (never auto-clicked; could be a tracker).

FAQ

Will I still get receipts/order confirmations after unsubscribing? Yes. Unsubscribing only cancels a marketing list; transactional mail is a separate, CAN-SPAM-exempt stream.

Is it safe? Deletions go to Bin (recoverable). Unsubscribes use one-click/mailto only. The tool never permanently deletes and never clicks arbitrary web links.

Does it work with non-Gmail IMAP? It's built for Gmail (uses X-GM-RAW and Gmail categories). Other providers need query changes.

Is this the Chrome extension / Gmail add-on that asks to sign in with Google? No — different project. This one has no OAuth and no browser extension. You use an app password over IMAP, entirely on your own machine, and it's open source so you can read exactly what it does before you run it.

Do I have to grant Google account access? No. You paste a scoped app password once; you never click through a "Sign in with Google" consent screen handing anyone access to your account.

Why isn't this just a website I can open? Because a browser can't talk to a mailbox. IMAP is a raw socket connection on port 993, and JavaScript in a page is only allowed to make HTTP requests — there's no API that lets a downloaded HTML file reach imap.gmail.com. A pure web version would need one of two things: a server that holds your app password and reads your mail for you, or "Sign in with Google" (OAuth over HTTPS, which a browser can do). Those are precisely the two things this tool exists to avoid. So instead it runs a small program on your own machine that speaks IMAP, and serves the interface to your browser at 127.0.0.1 — the page you see is local, and nothing it touches leaves your computer.

Anonymous usage stats

To show how many people we've helped — and to catch problems — the tool sends anonymous counters: a random install ID, your OS, the tool version, and totals (emails cleaned, MB freed, unsubscribes). It never sends your email address, senders, subjects, or any message content — your mail still never leaves your machine. Turn it off completely with INBOXSWEEPER_NO_TELEMETRY=1. The live totals appear on the website.

Security

  • Uses an app password, never your Google password. Revoke it anytime at apppasswords and the tool dies instantly.
  • Nothing is hardcoded; credentials come from Keychain or env vars.
  • .gitignore keeps local credential files out of the repo.

License

MIT — see LICENSE. Personal tool; use at your own risk. Always dry-run first.

Author

Built by Mukundan GovindarajLinkedIn · GitHub. If InboxSweeper helps you, a ⭐ on the repo or a hello on LinkedIn is genuinely appreciated.

About

Free, open-source inbox cleaner that runs 100% on your machine. Bulk-delete promotions and one-click unsubscribe in Gmail. No cloud, no account, no cost.

Topics

Resources

Code of conduct

Contributing

Security policy

Stars

0 stars

Watchers

1 watching

Forks

Releases

Packages

Used by

Contributors

Languages