Zero-Knowledge PGP Chat for People Who Don't Trust "Trust Us"
Concealment is a zero-knowledge, end-to-end encrypted chat platform that uses modern PGP cryptography and client-side key management to keep messages unreadable to servers, infrastructure, or anyone else.
🚀 Launch App | 📋 Privacy Policy | 📖 User Manual
Most "secure" messengers still trust someone:
- Servers see way more metadata than they should.
- Admins can flip a flag and start logging "for debugging".
- A database leak becomes a treasure chest of chat history.
Concealment takes the opposite approach:
"Assume compromise. Design so that compromise doesn't matter."
- The backend only sees ciphertext and minimal routing metadata.
- Private keys never leave your device in plaintext.
- If Firestore, Storage, or the WebSocket backend are all breached, the attacker still sees only encrypted blobs.
┌──────────────────────────┐
│ Concealment │
│ Zero-Knowledge PGP Chat │
└────────────┬─────────────┘
│
┌──────────────────┼──────────────────┐
│ │ │
┌─────▼─────┐ ┌─────▼─────┐ ┌─────▼─────┐
│ Web App │ │ Backend │ │ Firebase │
│ React/TS │ │ (Optional│ │ Firestore │
│ OpenPGP.js│ │ WebSocket│ │ & Storage │
└───────────┘ └───────────┘ └───────────┘
All encryption happens on the left (client).
The middle and right only ever see encrypted blobs and metadata.
When users click Launch App, Concealment guides them through secure account creation, PGP key generation in their browser, and passphrase-protected key storage before they ever send a message. Every chat they start from the live app is end-to-end encrypted and stored only as ciphertext in Firebase.
[ 1 ] Open Launch App
https://www.concealment.live
│
▼
[ 2 ] Create Account
• Email + password (Firebase Auth)
│
▼
[ 3 ] Generate Keys
• RSA-4096 / RSA-2048 / Curve25519
• Keys generated in-browser via Web Crypto API
│
▼
[ 4 ] Protect with Passphrase
• PBKDF2-HMAC-SHA256
• Private key stored only encrypted (IndexedDB / secure storage)
│
▼
[ 5 ] Start Chatting
• Messages signed + encrypted with PGP
• Stored as ciphertext in Firestore
Concealment uses PGP-style public-key cryptography with a modern stack:
| Algorithm | Use Case | Security | Performance |
|---|---|---|---|
| RSA-4096 | Maximum paranoia & long-term confidentiality | Proven, 20+ years | Slower (~2-3 sec/msg) |
| RSA-2048 | Balanced security & performance | NIST-recommended, ~15 years | Fast (~0.5 sec/msg) |
| Curve25519 | Modern & efficient (Signal, WireGuard use it) | ~RSA-3072 equivalent | Fastest (~0.3 sec/msg) |
┌─────────────────────────────────────────────────────────────┐
│ SENDER'S DEVICE │
├─────────────────────────────────────────────────────────────┤
│ 1. User types plaintext message: "Hello" │
│ 2. Client SIGNS message with sender's PRIVATE KEY │
│ 3. Client ENCRYPTS signed message with RECIPIENT'S PUBLIC │
│ KEY (PGP envelope) │
│ 4. Result: PGP ciphertext block (unreadable) │
└─────────────────────────────────────────────────────────────┘
│
▼
┌────────────────────────────┐
│ Firebase Firestore │
│ (Only ciphertext stored) │
└────────────────────────────┘
│
▼
┌─────────────────────────────────────────────────────────────┐
│ RECIPIENT'S DEVICE │
├─────────────────────────────────────────────────────────────┤
│ 1. Client DECRYPTS message using recipient's PRIVATE KEY │
│ 2. Client VERIFIES signature using SENDER'S PUBLIC KEY │
│ 3. If tampered: signature fails, message flagged ❌ │
│ 4. If valid: plaintext displayed in chat ✅ │
└─────────────────────────────────────────────────────────────┘
At no point does a server see plaintext or hold a decryption-capable key.
Your keys are your identity. Concealment treats them like radioactive material:
-
On first setup, the client generates a new PGP keypair:
- Algorithm: user-selected (RSA-2048, RSA-4096, or Curve25519)
- Generated entirely on the client with Web Crypto API + OpenPGP.js
-
Private key is encrypted at rest:
- Protected with a user passphrase (minimum 12 characters)
- Passphrase transformed into encryption key using PBKDF2-HMAC-SHA256
- Iteration count: 100,000+ (brute-force resistant)
-
Storage strategy:
- Browser: encrypted private key stored in IndexedDB
- Mobile (Flutter): encrypted in OS KeyStore / Keychain
- Decrypted key: only lives in memory during active session
- Cleanup: wiped immediately on logout/lock
Security Chain:
┌──────────────────────────────────────────────────────┐
│ User Passphrase (never stored, never sent) │
│ "Tr0pic@lStorm#2024!" │
│ │ │
│ ▼ (PBKDF2-HMAC-SHA256, 100k iterations) │
│ Derived Encryption Key (temporary, memory-only) │
│ │ │
│ ▼ (AES-256) │
│ Encrypted Private Key (stored in IndexedDB) │
│ "-----BEGIN PGP PRIVATE KEY BLOCK (encrypted)-----" │
│ │ │
│ If device stolen + IndexedDB dumped: still secure! │
└──────────────────────────────────────────────────────┘
- Minimum 12 characters enforced
- Entropy validation against common patterns
- Real-time strength feedback: "Weak" → "Very Strong"
- Example:
Tr0pic@lStorm#2024!→ ✅ "Very Strong" - Critical: Server NEVER stores passphrase (only PBKDF2 hash for verification)
Concealment doesn't want to know who you "are". It only cares that your keys work.
-
On login, you get a fresh cyberpunk alias, like:
Phantom-Echo-7Ghost-Vector-19Cipher-Storm-42
-
Aliases are:
- Ephemeral – tied to sessions, not a permanent profile
- Generated by controlled random formula:
[Adjective]-[Noun]-[Number] - Can be regenerated if you don't like it
-
Real identity is the PGP fingerprint:
- Example:
ABCD 1234 5678 90EF GHIJ - You can verify someone's identity by comparing fingerprints out-of-band
- Fingerprints are unchangeable and mathematically tied to the key
- Example:
Result: low-friction UX for humans, high-assurance identity for cryptography.
Concealment stands on Firebase, but treats it as an untrusted storage and signaling layer:
/users/{uid}
├── email: "user@example.com"
├── alias: "Phantom-Echo-7"
├── publicKey: "-----BEGIN PGP PUBLIC KEY BLOCK-----\n..."
├── fingerprint: "ABCD123456789EFGHIJ"
├── keyType: "RSA_4096" | "RSA_2048" | "ECC_CURVE25519"
├── createdAt: 2024-01-15T10:30:00Z
└── lastLogin: 2024-01-20T14:45:00Z
/conversations/{conversationId}
├── participants: ["uid1", "uid2"]
├── participantAliases: { "uid1": "Phantom-Echo-7", "uid2": "Ghost-X" }
├── createdAt: 2024-01-15T10:30:00Z
└── lastMessageAt: 2024-01-20T14:45:00Z
/conversations/{conversationId}/messages/{messageId}
├── senderId: "uid1"
├── senderAlias: "Phantom-Echo-7"
├── ciphertext: "-----BEGIN PGP MESSAGE-----\nHQEMA..." [ENCRYPTED]
├── signature: "-----BEGIN PGP SIGNATURE-----\nIHcD..." [PROOF OF AUTHENTICITY]
├── attachmentUrl: "https://storage.firebase.../image.jpg" (optional)
├── timestamp: 2024-01-20T14:45:00Z
├── ttl: 30 [seconds until auto-delete, null = never]
├── isDeleted: false [soft delete for recovery]
└── reactions: { "👍": ["uid2"], "😂": ["uid1", "uid2"] }
Key principle: Only ciphertext and metadata land in Firestore. No plaintext fields exist by design.
- Encrypted attachments (images/files) stored in Firebase Storage
- Files encrypted before upload; Storage only sees opaque blobs
- Downloaded blobs decrypted locally by the client
Concealment has an optional FastAPI WebSocket backend used only for real-time UX:
┌─────────────────────────────────────────┐
│ FastAPI WebSocket Backend │
│ (Python, Optional, Stateless) │
├─────────────────────────────────────────┤
│ Responsibilities: │
│ ✓ Handle WebSocket sessions │
│ ✓ Broadcast "new message" pings │
│ ✓ Send typing indicators │
│ ✓ Update online/offline presence │
│ │
│ NEVER does: │
│ ✗ Store messages │
│ ✗ See plaintext │
│ ✗ Hold private keys │
│ ✗ Bypass end-to-end encryption │
└─────────────────────────────────────────┘
If the backend dies, the app gracefully falls back to Firestore polling:
┌──────────────────────────────────────┐
│ Backend Available │
├──────────────────────────────────────┤
│ • Real-time messaging (fast) │
│ • Live typing indicators │
│ • Instant online status │
└──────────────────────────────────────┘
│
▼ (Backend down)
┌──────────────────────────────────────┐
│ Fallback Mode (Firestore Polling) │
├──────────────────────────────────────┤
│ • Messages fetch every 3 sec │
│ • No real-time signaling │
│ • Typing indicators delayed │
│ • All encryption still works! ✅ │
└──────────────────────────────────────┘
UX slows down slightly, but encryption and functionality remain intact.
- React 18 + TypeScript + Vite for fast, typed SPA
- OpenPGP.js layered over Web Crypto API for:
- Key generation
- Encryption/decryption
- Signing/verification
- Fingerprint calculation
- TailwindCSS + custom styles for dark, neon, cyberpunk interface:
- Glitchy headings
- Matrix-like typography
- Glowing borders and scanline effects
The Flutter app (under development) mirrors web's security model:
- Crypto: implemented with
pointycastle, compatible with PGP - Storage: OS KeyStore/Keychain + encrypted local SQLCipher DB for offline drafts
- Enhanced Features:
- Biometric unlock (Face ID / fingerprint) for encrypted key vault
- Voice & video calling via WebRTC
- Push notifications (Firebase Cloud Messaging)
- Same zero-knowledge stance for message content
For a detailed breakdown of what data is stored, how long it is retained, and what never leaves your device, see the full Privacy Policy.
┌─────────────────────────┐
│ Your Device │
│ (Browser / Mobile App) │
└───────────┬────────────┘
│
Plaintext │ Encrypted
┌───────────────────▼───────────────────┐
│ 1. You type a message (plaintext) │
│ 2. Message is signed with your │
│ private key │
│ 3. Message is encrypted with the │
│ recipient's public key (PGP) │
└───────────────────┬───────────────────┘
│
▼
┌─────────────────────────┐
│ Firestore / Storage │
│ • Only ciphertext │
│ • No private keys │
│ • Minimal metadata │
│ • NO plaintext EVER │
└─────────────────────────┘
This document explains how Concealment's zero-knowledge design, PGP encryption, and client-side key management minimize personally identifiable and message content exposure.
The full User Manual walks through every feature in detail:
┌────────────────────────────────────────────────────────────┐
│ Concealment Manual │
├──────────────┬─────────────────────────────────────────────┤
│ Topic │ What You Learn │
├──────────────┼─────────────────────────────────────────────┤
│ Setup │ Create an account, generate PGP keys, │
│ │ choose RSA-4096 vs RSA-2048 vs Curve25519 │
├──────────────┼─────────────────────────────────────────────┤
│ Chat Usage │ Start conversations, verify fingerprints, │
│ │ send encrypted messages & attachments │
├──────────────┼─────────────────────────────────────────────┤
│ Security │ How passphrases work, what happens if you │
│ │ forget them, self-destruct timers │
├──────────────┼─────────────────────────────────────────────┤
│ Advanced │ Ephemeral aliases, WebSocket signaling, │
│ │ mobile roadmap, threat model │
└──────────────┴─────────────────────────────────────────────┘
Concealment assumes:
- Servers can be compromised
- Firestore and Storage content can leak
- Admins might turn malicious in the future
- Network traffic can be captured
Concealment defends by:
- Keeping all encryption and decryption on the client
- Never sending private keys or passphrases to any backend
- Storing only ciphertext and public information in Firebase
- Making metadata small and boring (conversation IDs, timestamps, basic routing)
Result: If an attacker gains read access to every database and server log, they still do not gain the ability to decrypt messages.
Concealment is:
- A PGP-style secure messenger with:
- RSA-4096 / RSA-2048 / Curve25519 keys
- Client-side key generation via Web Crypto API + OpenPGP.js
- Encrypted storage in Firebase
- Zero-knowledge by architecture
Concealment is not:
- A metadata-free system (timestamps and participant IDs still exist)
- A password manager or general secret vault
- A "just trust the server" chat app with encryption bolted on later
- A post-quantum algorithm (yet – Phase 3 roadmap includes this)
| Feature | Status | Details |
|---|---|---|
| User Authentication | ✅ Live | Email/password via Firebase |
| PGP Key Generation | ✅ Live | RSA 2048 + 4096 + ECC Curve25519 |
| Key Storage | ✅ Live | Encrypted with passphrase (PBKDF2) |
| 1:1 Encrypted Chat | ✅ Live | Real-time Firestore listeners |
| Message Signing | ✅ Live | PGP digital signatures |
| Message Encryption | ✅ Live | RSA or ECC encryption |
| Self-Destruct Messages | ✅ Live | TTL-based auto-delete (30s to 1h) |
| Screenshot Detection | ✅ Live | Desktop + mobile browser support |
| Blur on Focus Loss | ✅ Live | BlurGuard component |
| File Attachments | ✅ Live | Images + PDFs encrypted before upload |
| Fingerprint Verification | ✅ Live | Visual + hex fingerprint display |
| Ephemeral Aliases | ✅ Live | Random cyberpunk names per session |
| WebSocket Signaling | ✅ Live | Optional FastAPI backend on Railway |
| Firestore Fallback | ✅ Live | Auto-switches if backend down |
| Typing Indicators | ✅ Live | Via WebSocket or Firestore |
| Online Status | ✅ Live | Green dot when connected |
| Cyberpunk UI | ✅ Live | Neon glows, glitch effects, matrix font |
| Theme Customization | ✅ Live | Light/Dark/Cyberpunk modes |
- Google Sign-In integration
- Voice calling (WebRTC)
- Video calling (WebRTC)
- Group chats (N-party encryption)
- Message reactions & threading
- Rich text editor with markdown
- Post-quantum cryptography (Kyber, Dilithium)
- Desktop app (Electron)
- Message search (encrypted metadata indexing)
- Decentralized backend option
- Portable identity (export encrypted identity package)
- Launch App – Start chatting now
- Privacy Policy – How your data is handled
- User Manual – Step-by-step usage guide
- GitHub Repo: concealment-docs – This documentation
Here's the sentence you're looking for:
"Concealment uses PGP-compatible RSA-4096, RSA-2048, and Curve25519 keys generated client-side via the Web Crypto API and OpenPGP.js, with all messages end-to-end encrypted using digital signatures for authenticity and stored only as ciphertext in Firebase Firestore, ensuring zero-knowledge encryption architecture where servers never see plaintext or private keys."
Concealment follows a paranoid-by-design approach:
- Zero Trust: Assume every layer (network, storage, backend) is compromised
- Client-First: All sensitive operations happen on your device
- Minimal Server Knowledge: Servers only see encrypted blobs and routing metadata
- Cryptographic Guarantees: Messages are mathematically proven authentic and confidential
- Transparency: Full open-source documentation of architecture and threat model
Concealment is built with security and privacy as first-class concerns. For security disclosures, please contact security@concealment.live instead of opening public issues.
Concealment stands on the shoulders of giants:
- OpenPGP.js – Pure JavaScript PGP implementation
- Web Crypto API – Modern cryptographic primitives
- Firebase – Infrastructure for auth, storage, and real-time databases
- React + TypeScript – Type-safe web frontend
- Flutter + PointyCastle – Mobile cryptography
This is your complete source of truth. Ready to encrypt? 🔐