# SeedPGP v1.1.0 **Secure BIP39 mnemonic backup using PGP encryption and QR codes** A TypeScript/Bun tool for encrypting cryptocurrency seed phrases with OpenPGP and encoding them as QR-friendly Base45 frames with CRC16 integrity checking. ## Features - ๐Ÿ” **PGP Encryption**: Uses cv25519 (Curve25519) for modern elliptic curve cryptography - ๐Ÿ“ฑ **QR Code Ready**: Base45 encoding optimized for QR code generation - โœ… **Integrity Checking**: CRC16-CCITT-FALSE checksums prevent corruption - ๐Ÿ”‘ **BIP39 Support**: Full support for 12/18/24-word mnemonics with passphrase indicator - ๐Ÿงช **Battle-Tested**: Validated against official Trezor BIP39 test vectors - โšก **Fast**: Built with Bun runtime for optimal performance ## Installation ```bash # Clone repository git clone https://github.com/kccleoc/seedpgp-web.git cd seedpgp-web # Install dependencies bun install # Run tests bun test # Start development server bun run dev ``` ## Usage ### Encrypt a Mnemonic ```typescript import { encryptToSeedPgp, buildPlaintext } from "./lib/seedpgp"; const mnemonic = "legal winner thank year wave sausage worth useful legal winner thank yellow"; const plaintext = buildPlaintext(mnemonic, false); // false = no BIP39 passphrase used const result = await encryptToSeedPgp({ plaintext, publicKeyArmored: yourPgpPublicKey, }); console.log(result.framed); // SEEDPGP1:0:ABCD:BASE45DATA... console.log(result.recipientFingerprint); // Key fingerprint for verification ``` ### Decrypt a SeedPGP Frame ```typescript import { decryptSeedPgp } from "./lib/seedpgp"; const decrypted = await decryptSeedPgp({ frameText: "SEEDPGP1:0:ABCD:BASE45DATA...", privateKeyArmored: yourPrivateKey, privateKeyPassphrase: "your-key-password", }); console.log(decrypted.w); // Recovered mnemonic console.log(decrypted.pp); // BIP39 passphrase indicator (0 or 1) ``` ## Deployment to GitHub Pages (FREE) This project uses a two-repository setup to keep source code private while hosting the app for free. ### One-Time Setup #### 1. Create Public Deployment Repo Go to https://github.com/new and create: - **Name**: `seedpgp-web-app` (or any name you prefer) - **Visibility**: **Public** - **Don't** initialize with README, .gitignore, or license #### 2. Configure Vite Base Path Edit `vite.config.ts`: ```typescript export default defineConfig({ plugins: [react()], base: '/seedpgp-web-app/', // Match your public repo name }) ``` #### 3. Build and Deploy ```bash # Build the production bundle bun run build # Initialize git in dist folder cd dist git init git add . git commit -m "Deploy seedpgp v1.1.0" # Push to your public repo git remote add origin https://github.com/kccleoc/seedpgp-web-app.git git branch -M main git push -u origin main # Return to project root cd .. ``` #### 4. Enable GitHub Pages 1. Go to `https://github.com/kccleoc/seedpgp-web-app/settings/pages` 2. **Source**: Deploy from a branch 3. **Branch**: Select `main` โ†’ `/` (root) 4. Click **Save** Wait 1-2 minutes, then visit: **https://kccleoc.github.io/seedpgp-web-app/** --- ### Deploying Updates (v1.2.0, v1.3.0, etc.) Create `scripts/deploy.sh` in your project root: ```bash #!/bin/bash set -e VERSION=$1 if [ -z "$VERSION" ]; then echo "Usage: ./scripts/deploy.sh v1.2.0" exit 1 fi echo "๐Ÿ”จ Building $VERSION..." bun run build echo "๐Ÿ“ฆ Deploying to GitHub Pages..." cd dist git add . git commit -m "Deploy $VERSION" || echo "No changes to commit" git push cd .. echo "โœ… Deployed to https://kccleoc.github.io/seedpgp-web-app/" echo "๐Ÿท๏ธ Don't forget to tag: git tag $VERSION && git push --tags" ``` Make executable and use: ```bash chmod +x scripts/deploy.sh ./scripts/deploy.sh v1.2.0 ``` --- ### Repository Structure - **seedpgp-web** (Private) - Your source code, active development - **seedpgp-web-app** (Public) - Built files only, served via GitHub Pages **Cost: $0/month** โœ… ## Frame Format ``` SEEDPGP1:FRAME:CRC16:BASE45DATA SEEDPGP1 - Protocol identifier and version 0 - Frame number (0 = single frame) ABCD - 4-digit hex CRC16-CCITT-FALSE checksum BASE45 - Base45-encoded PGP message ``` ## API Reference ### `buildPlaintext(mnemonic, bip39PassphraseUsed, recipientFingerprints?)` Creates a SeedPGP plaintext object. **Parameters:** - `mnemonic` (string): BIP39 mnemonic phrase (12/18/24 words) - `bip39PassphraseUsed` (boolean): Whether a BIP39 passphrase was used - `recipientFingerprints` (string[]): Optional array of recipient key fingerprints **Returns:** `SeedPgpPlaintext` object ### `encryptToSeedPgp(params)` Encrypts a plaintext object to SeedPGP format. **Parameters:** ```typescript { plaintext: SeedPgpPlaintext; publicKeyArmored?: string; // PGP public key (PKESK) messagePassword?: string; // Symmetric password (SKESK) } ``` **Returns:** ```typescript { framed: string; // SEEDPGP1 frame pgpBytes: Uint8Array; // Raw PGP message recipientFingerprint?: string; // Key fingerprint } ``` ### `decryptSeedPgp(params)` Decrypts a SeedPGP frame. **Parameters:** ```typescript { frameText: string; // SEEDPGP1 frame privateKeyArmored?: string; // PGP private key privateKeyPassphrase?: string; // Key unlock password messagePassword?: string; // SKESK password } ``` **Returns:** `SeedPgpPlaintext` object ## Testing ```bash # Run all tests bun test # Run with verbose output bun test --verbose # Watch mode (auto-rerun on changes) bun test --watch ``` ### Test Coverage - โœ… 15 comprehensive tests - โœ… 8 official Trezor BIP39 test vectors - โœ… Edge cases (wrong key, wrong passphrase) - โœ… Frame format validation - โœ… CRC16 integrity checking ## Security Considerations ### โœ… Best Practices - Uses **AES-256** for symmetric encryption - **cv25519** provides ~128-bit security level - **CRC16** detects QR scan errors (not cryptographic) - Key fingerprint validation prevents wrong-key usage ### โš ๏ธ Important Notes - **Never share your private key or encrypted QR codes publicly** - Store backup QR codes in secure physical locations (safe, safety deposit box) - Use a strong PGP key passphrase (20+ characters) - Test decryption immediately after generating backups - Consider password-only (SKESK) encryption as additional fallback ### ๐Ÿ”’ Production Deployment Warning The GitHub Pages deployment at **https://kccleoc.github.io/seedpgp-web-app/** is for: - โœ… Testing and demonstration - โœ… Convenient access for personal use - โš ๏ธ Always verify the URL before use For maximum security with real funds: - Run locally: `bun run dev` - Or self-host on your own domain with HTTPS ## Project Structure ``` seedpgp-web/ โ”œโ”€โ”€ src/ โ”‚ โ”œโ”€โ”€ lib/ โ”‚ โ”‚ โ”œโ”€โ”€ seedpgp.ts # Core encryption/decryption โ”‚ โ”‚ โ”œโ”€โ”€ seedpgp.test.ts # Test vectors โ”‚ โ”‚ โ”œโ”€โ”€ base45.ts # Base45 codec โ”‚ โ”‚ โ”œโ”€โ”€ crc16.ts # CRC16-CCITT-FALSE โ”‚ โ”‚ โ””โ”€โ”€ types.ts # TypeScript definitions โ”‚ โ””โ”€โ”€ App.tsx # React UI โ”œโ”€โ”€ scripts/ โ”‚ โ””โ”€โ”€ deploy.sh # Deployment automation โ”œโ”€โ”€ package.json โ”œโ”€โ”€ DEVELOPMENT.md # Development guide โ””โ”€โ”€ README.md # This file ``` ## Tech Stack - **Runtime**: [Bun](https://bun.sh) v1.3.6+ - **Language**: TypeScript - **Crypto**: [OpenPGP.js](https://openpgpjs.org) v6.3.0 - **Framework**: React + Vite - **Testing**: Bun test runner ## Roadmap - [ ] QR code generation UI - [ ] QR code scanner with camera support - [ ] Multi-frame support for larger payloads - [ ] Hardware wallet integration - [ ] Mobile scanning app - [ ] Shamir Secret Sharing support ## License MIT License - see LICENSE file for details ## Author **kccleoc** - [GitHub](https://github.com/kccleoc) ## Version History ### v1.1.0 (2026-01-28) - Initial public release - Full BIP39 mnemonic support - Trezor test vector validation - Production-ready implementation - GitHub Pages deployment guide --- โš ๏ธ **Disclaimer**: This software is provided as-is. Always test thoroughly before trusting with real funds. The author is not responsible for lost funds due to software bugs or user error. Now create the deployment script: ```bash mkdir -p scripts cat > scripts/deploy.sh << 'EOF' #!/bin/bash set -e VERSION=$1 if [ -z "$VERSION" ]; then echo "Usage: ./scripts/deploy.sh v1.2.0" exit 1 fi echo "๐Ÿ”จ Building $VERSION..." bun run build echo "๐Ÿ“ฆ Deploying to GitHub Pages..." cd dist git add . git commit -m "Deploy $VERSION" || echo "No changes to commit" git push cd .. echo "โœ… Deployed to https://kccleoc.github.io/seedpgp-web-app/" echo "๐Ÿท๏ธ Don't forget to tag: git tag $VERSION && git push --tags" EOF chmod +x scripts/deploy.sh ```