🔒 Everything Encrypted, Always

Your private,
encrypted workspace.

SealKeep lets you build custom data apps - contacts, password managers, patient forms, anything - where your data is locked in your browser before it ever reaches the server. No code required.

🏗️ No-code builder 🔑 Shared access 🔍 Search & filter 📱 2FA support 💾 Backup & restore 📦 Offline binaries
SealKeep App Builder - unlocked and ready
🔑 The Big Idea

Your password never leaves your device

Most apps store your data on a server where an employee or a hacker could read it. SealKeep works differently: your password turns into a lock that scrambles your data inside your browser before anything is sent to the server. The server holds a locked box - it has no key to open it.

🛡️

Even if someone stole the entire database, all they would see is scrambled data. Without your password (or a recovery code), the information is permanently unreadable - not even the server owner can access it.

🔐

Locked before sending

Your data is scrambled in the browser using AES-256-GCM encryption. Every record gets its own unique lock.

🧂

Hard to guess

Your password is transformed into an encryption key in a way that is deliberately slow for attackers, making guessing your password impractical.

🔁

Recovery codes

Get 10 one-time backup codes at setup. Each one independently unlocks your data if you forget your password.

🌐

Built into the browser

All encryption uses the browser's built-in security tools - no third-party code handles your keys.

Getting started

From creating an account to managing encrypted records - here's everything you need.

Step 1 - Account

Create your account

Register with an email address and a password. Your password is the only thing that can unlock your data. The server only stores a scrambled version of it - not the password itself.

After registering, you're taken straight to the recovery code setup - it's required before you can do anything else.

Registration form filled

Enter your email and a strong password (8+ characters)

Step 2 - Recovery codes

Save your recovery codes

SealKeep generates 10 one-time backup codes and shows them on screen - they're never stored on the server in a readable form. Each code is a separate key to your data. Store them like you'd store a spare house key: somewhere safe and offline.

⚠️

If you forget your password and lose all your recovery codes, your data is gone forever. There's no "forgot password" email that can recover encrypted data.

Recovery codes screen

10 one-time recovery codes - write these down and keep them safe

Step 3 - App Builder

Design your app without coding

The App Builder lets you create any kind of data tracker - a password manager, a contact list, a patient intake form, an invoice log - by clicking, not coding. Add fields, choose types, set layouts, and hit Save.

Every time you open the Builder, you unlock it with your password. This ensures your key is only in memory when you're actively using it.

Builder with fields defined

Builder - fields defined for a Password Manager app

Step 4 - Your data

Add and manage records

Open your app, enter a record, and click Save. Everything you type is scrambled in the browser before it's sent. When you open the app next time, your records are fetched as scrambled data and unscrambled locally for display.

Edit, delete, tag, and search your records. You can also add rich-text notes with formatting - bold, italics, lists, and tables.

Full record list

Both entries visible - all data decrypted locally for display

🤝 Shared Access

Share an app without sharing your password

You can invite another SealKeep user to access one of your apps - they'll be able to read and add records without ever knowing your password. Access can be revoked at any time with a single click.

🔑

How it works: When you invite someone, SealKeep creates a digital envelope addressed specifically to their account. Only they can open it with their own password - you never share credentials. When you revoke access, the envelope is destroyed and the app's encryption key is rotated automatically.

How to share access

  • The person you want to share with creates an account and opens the Builder once. This generates their unique keypair.
  • In your app's Builder panel, click Shared Access.
  • Enter their email address and click Invite.
  • SealKeep wraps your app's key in a digital envelope addressed to them.
  • They open the app with their own password - and can read and add records immediately.
🚫

To remove someone's access, click Revoke next to their name. Their access ends immediately and the app's key is rotated so old data remains secure.

Shared access panel open

Shared Access panel - invite collaborators by email

📱 Two-Factor Authentication

Add a second lock to your account

Two-factor authentication (2FA) means that even if someone steals your password, they still can't log in - they'd also need your phone. SealKeep supports standard authenticator apps like Google Authenticator, Authy, and 1Password.

Setting up 2FA

  • Open your account settings and click Enable Two-Factor Auth.
  • Scan the QR code with your authenticator app.
  • Save the backup codes shown on screen - you'll need these if you lose your phone.
  • Enter the 6-digit code from the app to confirm setup.
  • From now on, every login requires your password and a fresh code from the app.
🔓

If you lose your authenticator app, use a backup code to regain access. You can also reset your password via the Forgot Password link on the login page, which lets you set a new password and re-enter with a backup code.

TOTP QR code setup

Scan this QR code with any authenticator app

TOTP login prompt

Login prompts for a 6-digit code after password

Backup code input

Lost your phone? Use one of the backup codes to get in

💾 Backup & Restore

Your data, safe even if the server disappears

SealKeep lets you download an encrypted backup of all your records at any time. The backup file is locked with your encryption key - no one can read it without your password. If something goes wrong, restore from the backup and you're back where you left off.

How backup works

  • In the App Builder sidebar, click Backup. A snapshot of all your records is downloaded as an encrypted file.
  • The backup is encrypted with your key - you can store it anywhere safely.
  • To restore, open the App Builder and click Restore. Select your backup file. Records are imported and decrypted locally.
  • Backups don't replace regular records - restoring adds the backed-up records back if they're missing.
📋 Field Types

Build any form you can imagine

Every field type stores its value as encrypted data. Pick the type that matches what you're collecting - the app handles the rest.

text

Short text - names, titles, single-line values

email

Email address - format is checked automatically

tel

Phone number

number

Numeric - quantities, prices, ages

date

Date picker - calendar pop-up

select

Dropdown - one choice from a list you define

radio

Radio buttons - all choices visible at once

checkbox

Multi-select checkboxes - pick several options

textarea

Rich text editor - bold, italic, lists, tables

tags

Label chips - type to add, click to remove

file

File upload - file bytes are encrypted inside the record

lineitems

Invoice rows - description, qty, price, tax, total

Column layout

Each field can be sized independently: Full (entire row), Half, One-third, or Two-thirds. On mobile, all fields automatically expand to full width so nothing gets squished.

Hidden fields

Fields can be hidden in the list view, the form, or both. Use this to keep internal notes or sensitive values out of sight without removing them from the record.

🔐 Security & Encryption

How your data is protected - in plain English

SealKeep uses several layers of protection. Here's what each one does and why it matters.

🔑

Your password becomes a key

When you unlock the app, your password is transformed into an encryption key that lives only in your browser's memory. It is never sent to the server.

The transformation is deliberately designed to be slow for anyone trying to guess your password, making automated attacks impractical.

🔒

Every record is locked individually

Before a record is sent to the server, the browser scrambles the data using AES-256-GCM - the same standard used by banks and governments. Each record gets a unique random component (called an IV) so that identical records look different.

AES-GCM also detects tampering: if the ciphertext is modified in any way, decryption fails immediately with an error.

AES-256-GCM · Unique IV per record · Authenticated encryption
🔁

Recovery codes are separate keys

Each recovery code is an independent key to your data - generated in the browser and never sent to the server in readable form. Using a code removes it from the list so it can't be used again (one-time codes).

The server stores encrypted bundles ("blobs"), each locked by a different code. The codes themselves are only shown to you once and never leave your screen.

HKDF key derivation · AES-256-GCM wrapped blobs · One-time use
🤝

Sharing uses digital envelopes

When you invite a collaborator, SealKeep creates a sealed digital envelope using their public key (a number that can be shared freely). Only their private key - which never leaves their device - can open it.

Revoking access destroys their envelope and generates a fresh key for your app. Past data remains encrypted under the new key.

ECDH key exchange · P-256 curve · Per-grant wrapped DEK
🏷️

Tags are fingerprinted, not stored

Tag labels are stored as mathematical fingerprints (HMACs) on the server - the server can match a search without ever seeing the tag text. The actual label is stored separately in encrypted form.

This means you can filter records by tag server-side without the server knowing what your tags say.

HMAC-SHA-256 fingerprint · Encrypted label stored separately
📱

Two-factor authentication

Optional TOTP (time-based one-time password) support means even a stolen password can't be used to log in alone. The 6-digit code changes every 30 seconds and is generated by an app on your phone.

Backup codes let you regain access if you lose your authenticator. Password reset works without breaking any of your encrypted data.

TOTP (RFC 6238) · HMAC-SHA1 · 30-second window · Backup codes
🚦

Rate limiting on login

The login endpoint limits failed attempts per IP address. After 5 failed attempts within 10 minutes, further attempts are blocked temporarily. This stops automated password-guessing tools from running unhindered.

5 attempts / 10 min per IP · HTTP 429 with Retry-After header
🍪

Sessions via secure cookies

Authentication uses HttpOnly session cookies, which means JavaScript on the page cannot read the session token. This protects against a common attack called cross-site scripting (XSS).

CSRF tokens protect all state-changing requests (POST, PUT, DELETE) from being triggered by malicious third-party websites.

HttpOnly cookies · CSRF tokens · SameSite policy

What the server can and cannot see

Here's every piece of data stored in the database and whether anyone with a copy of that database could read your information.

What's stored What it is Readable without your key?
users.password_hash A scrambled version of your login password (bcrypt) Not reversible
users.encryption_salt A random value used to derive your key (not secret) Visible - not harmful alone
users.recovery_blobs_json Encrypted copies of your data key, one per recovery code 🔒 Encrypted
records.payload Your actual data - scrambled with AES-256-GCM 🔒 Encrypted
records.meta_json Internal record metadata (e.g. migration state) 🔒 Encrypted payload only
app_schemas.fields & app_schemas.title Your app's field definitions and title 🔒 Encrypted
user_tags.tag_hmac Mathematical fingerprint of each tag label 🔒 Not reversible
user_tags.tag_enc Encrypted tag label text 🔒 Encrypted
app_key_grants.* Shared access grants - app key wrapped for collaborator's keypair 🔒 Encrypted per-recipient
users.ecdh_pub_key Collaborator's public key (used for sharing) Public - intentionally visible
users.ecdh_priv_enc Collaborator's private key, encrypted with their password 🔒 Encrypted
users.totp_secret_enc Two-factor authentication secret, encrypted with user's key 🔒 Encrypted
📦 Standalone Mode

Build an offline app anyone can run

Design a form in the Builder, then compile it into a single file that users run on their own computer. No internet, no account, no server. The developer never sees user data - not even with a copy of the database file.

How to build a standalone app

  1. Design your schema in the hosted Builder
  2. Click Export on the app card - downloads a schema file
  3. Run the build script with your schema file and a target platform
  4. Distribute the single binary - users need nothing else
  5. To update: build a new binary with the updated schema. Users replace the file and keep their data.
# Build for Linux (64-bit)
SCHEMA_FILE=contacts-schema.json APP_NAME=my-contacts \
./scripts/build-standalone.sh

# Build for Windows from Linux
SCHEMA_FILE=contacts-schema.json APP_NAME=contacts.exe \
GOOS=windows GOARCH=amd64 \
./scripts/build-standalone.sh
Standalone build modal open

One-click build from the Builder - choose your platform

💻

Cross-platform

Linux, macOS (Intel + Apple Silicon), Windows - all from a single build command.

📁

Single file

Schema, UI, and server all in one binary. Only data.sqlite is created at runtime.

🔒

Developer-blind

The developer can't read user data. Even with a copy of the database, it's all encrypted.

🔄

Safe upgrades

Ship a new binary with an updated schema. Existing records open fine - the key doesn't change.

🚀 Quick start

Up and running in 30 seconds

Clone, run, register, and start building your first encrypted app.

# 1. Start the server
go run ./cmd/server

# 2. Open in your browser
http://localhost:8085/auth/register.html

# 3. Register → save recovery codes → build your first app
Register now → Open Builder