Production-ready, zero-knowledge, end-to-end encrypted messaging. Built with Next.js 15, React 19, TypeScript, Web Crypto API, and PWA.
- Double Ratchet Protocol: Signal-style encryption offering Forward Secrecy (compromised keys can't read past messages) and Post-Compromise Security (healing).
- Crypto Isolation: All sensitive key operations run in a dedicated Web Worker (
public/worker.js), ensuring main thread vulnerabilities (XSS) cannot easily extract keys. - Trust On First Use (TOFU): Identity Keys are generated once and pinned in IndexedDB.
- JIT Handshake: Just-In-Time Key Exchange allows you to chat immediately by pasting a Peer ID.
- Installable: Full "Add to Home Screen" support as a native-like app.
- Security-First Caching: Custom Service Worker (
sw.js) explicitly excludes crypto logic and keys from cache to ensure freshness, while speeding up UI assets. - Offline Shell: Application loads instantly even offline (though messaging requires network).
- Remote Edit & Recall: Securely Edit or Delete sent messages. These actions are encrypted and propagated to peers automatically.
- Self-Destruct: "Read Once" (Burn-on-read) and Timer-based expiration support.
- Traffic Analysis Resistance: Messages padded to fixed 256-byte buckets.
- Metadata Protection: Random "Jitter" (0-300ms) obscures typing patterns.
- Client-Side Encryption: All files are encrypted in the browser using AES-256-GCM with unique per-file keys before upload.
- Zero-Knowledge Storage: Server stores only encrypted binary blobs. No filenames, MIME types, or metadata are persisted.
- Secure Key Exchange: Media decryption keys are transmitted only via the existing E2E encrypted channel (Double Ratchet).
- On-Demand Decryption: Receiver downloads encrypted blob and decrypts locallyβserver never sees plaintext.
- Supported Formats: Images, videos, and any file type (rendered as downloadable attachment).
- Size Limit: 25MB per file.
- Strict Transport: Enforced HSTS, CSP, and Anti-CSWSH (Origin Verification).
- Audit Logs: Built-in local security event logging at
/security/events. - No Login: Anonymity by default. No email, phone, or serverside database.
git clone <your-repo-url>
cd securechat
npm installThis starts Next.js (Port 3000) and WebSocket Relay (Port 3001) concurrently.
npm run devOpen http://localhost:3000.
Note: You will see a dedicated WebSocket server running on port 3001. This is the Zero-Knowledge Relay. It blindly passes encrypted packets.
If the server fails to start because port 3000/3001 is busy:
# Kill stuck processes (Linux/Mac)
fuser -k 3000/tcp 3001/tcp
# Then restart
npm run devThis means the Peer ID you are trying to message is offline or invalid (peers are ephemeral).
- Fix: Ask the peer to refresh and share their new ID.
Ensure the WebSocket server is running npm run ws:dev (included in npm run dev).
securechat/
βββ app/
β βββ page.tsx # Client Logic (UI)
β βββ api/
β β βββ media/ # Encrypted Media API
β β βββ upload/ # POST: Accept encrypted blob, return download URL
β β βββ download/ # GET: Stream encrypted blob to client
β βββ security/ # Threat Model & Events Log
β βββ layout.tsx # Security Headers & PWA Register
βββ components/ # UI Components (Bubble, Sidebar, MediaContent)
βββ hooks/
β βββ useSecureChat.ts # Crypto Logic, Protocol Orchestration, Media Handling
βββ lib/
β βββ storage/
β β βββ db.ts # IndexedDB Wrapper (Identity, Sessions)
β β βββ mediaStorage.ts # Filesystem Storage for Encrypted Blobs
β βββ crypto/ # Crypto Utils
βββ public/
β βββ worker.js # ISOLATED Crypto Worker (Keys, File Encryption)
β βββ sw.js # Security-First Service Worker
β βββ manifest.json # PWA Manifest
βββ media/ # Encrypted blob storage (gitignored)
βββ ws-server.ts # Relay Server (Port 3001)
βββ next.config.js # Strict CSP
Create .env.local for production overrides:
NEXT_PUBLIC_WS_URL=wss://your-domain.com
WS_PORT=3001
MEDIA_STORAGE_PATH=/path/to/persistent/media # Optional: defaults to ./medianpm run build
npm start- Reverse Proxy: You MUST use Nginx/Caddy to terminate TLS (HTTPS) and forward WebSocket
Upgradeheaders. - HTTPS: Web Crypto API requires HTTPS (or localhost).
- Media Storage: Ensure
MEDIA_STORAGE_PATHpoints to a persistent, writable directory.
| Layer | Protection |
|---|---|
| Encryption | AES-256-GCM with unique key per file |
| Key Exchange | Keys sent via Double Ratchet E2E channel |
| Storage | Server stores only encrypted blobs |
| Metadata | No filenames, MIME types, or sizes logged |
| Decryption | Client-side only, on-demand |
- Protocol: Based on the Double Ratchet Algorithm by Signal.
- Crypto: Native Web Crypto API (SubtleCrypto).
- License: MIT.