Should I vibe code
Build a privacy-conscious desktop email client with local indexing and optional summaries
A mail client is a fortnight. A mail client with a padlock on it is a promise you have to keep in every branch.
?
Their verdict, the Growth price and the build-time estimate come from their entry, MIT-licensed. Checked 2026-08-04.
?
Our verdict, the regret score and everything below it. Editorial and unsponsored — nobody can pay to be moved.
The honest answer
why the verdict is what it is
Three mail clients on this site already argue about sync engines, credentialed daemons and inboxes wired to an LLM. Canary's entry is a different one, and it is the padlock. What this product sells is a claim — PGP on the way out, a SecureSend flow marketed as fit for patient information, an index that stays on your machine — and a claim is a thing you either keep in every branch or do not make at all. The encryption code is the easy part, because the libraries are excellent and nobody sensible writes their own. The hard parts are the ones a generated client gets wrong by default: what happens when the recipient has no key, whether the badge in the compose window reflects the toggle or the message that actually left, where the private key lives once you want it on your phone, and whether that lovely fast local search index is sitting in plaintext beside the mailbox it was supposed to protect. Every one of those failures is silent, and silence is the wrong failure mode for a product whose only feature is confidence.
What actually breaks
not "if". the specific failures.
- The plaintext fallback. Somewhere in every generated send path there is a branch for "recipient has no usable key", and the default written into it is send anyway, with a warning in a log nobody reads
- The badge. Bind the padlock to the compose toggle and it is decoration; bind it to what the SMTP transaction actually carried and it is a fact. Almost every first version binds it to the toggle
- Key trust, which is all of PGP and none of the tutorial. Anyone can upload a key for your address to a keyserver, so a green check beside a fingerprint you fetched thirty seconds ago is an assertion you invented
- Key lifecycle: generation, passphrase, backup, getting the same secret onto a second device without emailing it to yourself. Lose it and the archive is not locked, it is gone — there is no reset link for a private key
- The local index. Full-text search over decrypted bodies means a searchable plaintext copy of everything, usually in a SQLite file beside the encrypted store, which quietly undoes the product
- The AI features, which work by sending decrypted message bodies to a model provider — the one thing the person who chose an encrypted mail client was trying to avoid
- Revocation and expiry, handled as edge cases: encrypting to a key the owner retired last spring succeeds cleanly and produces a message they can no longer read
- Underneath all of it, the same multi-provider sync problem Mimestream and Spark are about: Exchange, iCloud, IMAP servers that lie about UIDVALIDITY, and Gmail's labels-are-not-folders
The fallback branch was written in the first week, when nothing worked and every send died with "no key for recipient". It logged a warning, sent in the clear, and was going to be removed before anyone else used the client. Eleven months later a reply-all pulled in an assistant's address that had never had a key, the branch fired, and a term sheet plus the four replies underneath it went out as plaintext to five people — while the composer still drew the padlock, because the padlock is bound to the toggle rather than to what left the machine. You find this in September, in your own Sent folder: thirty-one messages you believed were encrypted, sitting there readable. Each of them is also sitting in somebody else's mailbox, and the difference between those two facts is that you can only delete yours.
Is that you?
the verdict is a default, not a law
- It is a mail client with no encryption claim at all — read, search, compose, and the honest position that this is what your provider already gives you
- Encryption is opt-in per message, and a message that cannot be encrypted fails to send rather than degrading
- The private key was generated by a tool you did not write, lives in the OS keychain, and has an export you have actually tested restoring on a second machine
- The search index is encrypted with the same key material as the store, or there is no index
- There is any code path where an intended-encrypted message can be delivered in the clear without stopping to ask you
- You are sending patient information, or anything else where a compliance word appears in the requirements. A BAA is a contract somebody signs, not a feature you implement
- The archive holds one copy of the private key and no tested restore, so one wiped laptop turns years of mail into noise
- Anyone other than you reads the padlock before deciding what they are willing to put in writing
If you build it anyway
the checklist, then the prompt that enforces it
- Use OpenPGP.js, Sequoia or gopenpgp exactly as documented. Nobody on this project writes a primitive, pads a block or invents a key format.
- Build key backup, export and restore before you build compose. A lost private key is permanent data loss and deserves to be treated as such from the first commit.
- Delete the plaintext fallback. If the recipient has no usable key the send fails and says why. Never downgrade silently, and never per-recipient inside a single message.
- Derive the encrypted indicator from the sent artefact — read it back out of the Sent folder and verify — rather than from the state of a toggle in the composer.
- Show fingerprint, key source and verification state as three separate things. A key fetched from a keyserver is unverified until a human says otherwise, and the UI should say so in those words.
- Encrypt the search index with the same key material as the mail store, or accept slower search over bodies decrypted on demand. A plaintext index defeats encryption at rest completely.
- Any AI summarisation is off by default, per account, and names the provider that will receive the plaintext at the moment it happens — not in a settings page nobody opens.
- Handle expired and revoked keys explicitly and refuse them by default, because encrypting to a retired key is a failure that looks exactly like success.
I am building a desktop email client that advertises end-to-end encryption.
The risky part is not the inbox UI. It is that a padlock is a claim, and a
claim you break in one branch is worse than no claim at all. Work in this
order and argue with me if I try to skip ahead.
1. Never implement a cryptographic primitive. Use OpenPGP.js, Sequoia or
gopenpgp as documented, and refuse if I ask for anything custom.
2. Before the first encrypted message, write down the key lifecycle: where the
private key is generated, where it is stored, how it reaches a second
device, and what happens when the passphrase is lost. Show me that first.
3. Build key backup, export and a tested restore before the composer. Treat a
lost key as permanent data loss, because that is what it is.
4. There is no automatic fallback to plaintext. If a recipient has no usable
key the send fails with an explanation and I decide. Do not downgrade
silently, and do not downgrade for one recipient inside one message.
5. Derive the "encrypted" badge from the message that was actually sent — read
it back from Sent and verify — never from the compose-time toggle.
6. Display fingerprint, key source and verification state separately. A key
pulled from a keyserver is unverified. Do not draw a green check on it.
7. Reject expired and revoked keys by default and make me override explicitly.
8. If you build a local search index, encrypt it with the same key material as
the mail store. A plaintext index beside an encrypted mailbox is the whole
product undone, quietly.
9. AI summarisation is off by default and per account, and the UI names the
provider that will receive decrypted text at the moment it is sent.
10. Account credentials go in the OS keychain, OAuth wherever it exists. If a
provider needs a stored password, tell me what an attacker with my laptop
gets.
11. Out of scope until I ask: HIPAA claims, self-destructing links, and
anything the README wants to call compliance. That is a legal posture
somebody signs for, and $3 a month buys one that is not yours to defend.That one keeps you out of trouble. For the prompt that actually builds it, canivibecodeit.com has one.
their build prompt ↗Or don’t build it
the boring option, and the way back out
The moment the encryption is meant to protect somebody other than you. $3 a month is the difference between a padlock you drew and a padlock somebody is obliged to keep honest, and that difference only ever shows up in the branch you did not test. The client itself is a genuinely good project — the triage, the shortcuts, the unified inbox are all yours to enjoy. It is specifically the claim that is worth outsourcing.
$3/mo is cheaper than your weekend.
Two exits, and only one of them is cheap. The mail is fine: if the mailbox stayed the source of truth, leaving means uninstalling, revoking OAuth grants and rotating any password the client ever held. The encrypted archive is the expensive half. Export every private key and its passphrase somewhere that will outlive the project — a paper backup or a password manager, not the app's own database — before you stop maintaining it, and decrypt in place anything you want to still be able to read in five years. An encrypted mailbox whose only decryption tool is a binary you last compiled against a 2026 toolchain is not archived, it is buried.
The JavaScript OpenPGP implementation you should be calling instead of writing one.
Browser PGP extension whose key-management UI is a decade-long lesson in how hard trust decisions are to present.
Open-source desktop mail client, and a fair preview of the multi-provider sync work sitting underneath all of this.
Questions
There are already three mail-client entries. Why does this one score higher than Mimestream?
Because Mimestream's failure mode is a mailbox that will not sync, and this one's is a message you believed was private and was not. Mimestream is a sync engine wrapped in a nice window; Canary is a sync engine wrapped in a nice window plus a promise. The engineering is comparable, the way it fails is not, and irreversibility is the dimension that separates them.
I would use a real library. Isn't that the whole problem solved?
It solves the smallest part. Almost every serious PGP failure of the last twenty years lived in the layer above the primitives: which key was chosen, whether the signature verification result was rendered honestly, whether HTML rendering leaked plaintext back to a sender, whether the client fell back to unencrypted. EFAIL was a rendering bug, not a maths bug. Your agent will produce correct calls to a correct library and still get the surrounding decisions wrong, because the surrounding decisions are product design.
The AI summaries seem harmless. Are they?
Harmless in an ordinary mail client and self-defeating in this one. Summarising a thread means decrypting it and posting the plaintext to a model provider, which is exactly the trust boundary the encryption existed to draw. If you want both, make it explicit and per-message, run a local model, and never let a background job do it on receipt.
Canary markets SecureSend as HIPAA-friendly. Can I rebuild that?
You can rebuild the mechanism — an expiring link to content that only decrypts on the recipient's side. You cannot rebuild the compliance part, because that part is not code. It is a business associate agreement, a documented risk assessment, access logs, and a named person accountable for them. If protected health information is going near this, the entry to read is not this one; it is any of the ones where a regulator is listed as the person who pays.
Every week, someone ships something they shouldn’t have.
New verdicts, the worst thing that landed in the trap, and the occasional incident report. No other email, ever.
Your inbox is the reset link for everything else you own. It deserves better than your first sync engine.
Send later means a server that holds your mail password and presses send while you are asleep. Twice, sometimes.
An agent with inbox access takes instructions from anyone who knows your email address.
last reviewed 2026-08-04 · verdict is editorial and unsponsored · shared entry data from canivibecodeit under MIT · not legal advice