Click to expand
ClawChives uses a key-file identity system β there are no passwords or accounts on a remote server.
ββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββ
β Identity Key File: clawchives_identity_key.json β
β β
β { β
β "username": "your-username", β
β "uuid": "xxxxxxxx-xxxx-xxxx-xxxx-xxxxxxxxxxxx", β
β "token": "hu-[64 random chars]" β
β } β
β β
β β οΈ This file IS your password. Losing it = lockout. β
β β οΈ Never share it. Never commit it to version control. β
ββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββ
| Prefix | Type | Scope | Storage |
|---|---|---|---|
hu- |
Human Identity Key | One-Field login lookup | Server DB (key_hash UNIQUE index) |
lb- |
Agent Key | Automated agent access | Server DB (agent_keys table) |
api- |
REST Token | API session access | Server DB (api_tokens table) |
Tip
See BLUEPRINT.md Β§ Key System Architecture for full technical details on key generation, storage, and rotation.
Client-Side (Session Memory)
hu-tokens are never stored in plaintext and are never sent to the server.- The
hu-string is immediately hashed on the client using SHA-256 and exchanged viaPOST /api/auth/tokenfor a short-livedapi-bearer token. sessionStorageis used for session state (cc_authenticated,cc_view) β clears automatically on tab close to prevent token theft.
Server-Side (Express & SQLite)
requireAuth: Validates theapi-token via the SQLiteapi_tokenstable. It immediately injectsreq.agentPermissionsfor downstream handlers based on whether the token belongs to a human or anlb-agent key.requireHuman: Restricts sensitive configuration routes (/api/settings,/api/agent-keys) to human tokens only. Lobster keys cannot mutate system configuration.- Key Uniqueness:
key_hashis strictly enforced asUNIQUEto support collision-free one-field lookups. requirePermission(action): Generates strict locks (e.g.,canWrite,canDelete) around all CRUD routes based on the Granular Custom permissions assigned to the underlyinglb-key.- SQLite uses WAL journal mode and foreign key enforcement for data integrity.
Docker Security
- The API container runs on Node 22 β minimal attack surface.
- SQLite data is in a named Docker volume (
sqlite_data) β not exposed on the host filesystem by default. - API only exposes port
4646. The frontend never directly exposes the database. NODE_ENV=productiondisables development stack traces in API error responses.
ClawChives supports AES-256 encryption at rest via SQLCipher. This protects your pinchmarks and agent keys if the database file is stolen.
Generate a secure encryption key:
DB_ENCRYPTION_KEY=$(openssl rand -base64 32)
echo $DB_ENCRYPTION_KEYUsing npm:
export DB_ENCRYPTION_KEY=your-generated-key-here
npm run scuttle:dev-startUsing Docker:
Edit docker-compose.yml and set the environment variable:
environment:
- DB_ENCRYPTION_KEY=your-generated-key-hereThen restart:
docker compose up -d --build| Variable | Default | Purpose |
|---|---|---|
DB_ENCRYPTION_KEY |
"" (empty) |
AES-256 encryption key. Leave empty for plaintext (default). |
Important
First-Time Encryption: If you have an existing plaintext database and enable encryption, ClawChives will automatically migrate it. Your data is preserved.
Encryption happens automatically when you set DB_ENCRYPTION_KEY:
- ClawChives detects an unencrypted database
- Creates a temporary backup
- Encrypts all data in-place
- Verification completes transparently
No manual migration steps required.
To rotate your encryption key:
- Generate a new key:
openssl rand -base64 32 - Update
DB_ENCRYPTION_KEYin your environment - Restart the application
- ClawChives re-encrypts the database with the new key
Caution
Key Management: Keep your DB_ENCRYPTION_KEY safe. If you lose it, your data becomes inaccessible. Store it separately from this repository (e.g., in a password manager or secrets vault).
These are accepted trade-offs for the current development phase.
- Single-user only β no multi-user support per instance currently.
- No HTTPS enforcement β use a reverse proxy (Nginx + Certbot) for public deployments.
- Rate limiting is stored but not enforced β
rateLimiton agent keys is recorded but not yet checked on each request. - No refresh token rotation β
api-tokens persist until manually revoked.
| Threat | Status | Implementation | Details |
|---|---|---|---|
| SQL Injection | β Mitigated | Parameterized queries via better-sqlite3 | All database access uses prepared statements; no string concatenation |
| Cross-Site Scripting (XSS) | β Mitigated | React auto-escapes; no innerHTML |
All user input is rendered safely; no dangling HTML injection vectors |
| Cross-Site Request Forgery (CSRF) | β Mitigated | Bearer token auth (not cookies) | No session cookies; tokens require explicit Authorization header |
| Authentication Bypass | β Mitigated | Constant-time key comparison | Token comparison uses timing-safe functions; no timing attacks |
| Authorization Bypass | β Mitigated | requirePermission() on all routes |
Granular permissions enforced per action; admin routes restricted to humans |
| Data Leakage | β Mitigated | Session storage cleared on tab close | sessionStorage tokens evaporate; no persistent credential storage |
| Rate Limiting | Recorded but not enforced | rateLimit field on agent keys exists; enforcement is roadmapped |
| Key Type | Storage | Risk | Mitigation |
|---|---|---|---|
hu- tokens |
Client memory only (sessionStorage) | Stolen if browser compromised | Never sent to server; cleared on tab close |
api- tokens |
Server DB with expiration | Stolen if DB breached | Short-lived; can be rotated via POST /api/auth/token |
lb- keys |
Server DB, revocable per-agent | Leaked in logs/backups | Revocable in Settings; audit logs track usage |
Risk: Attacker can log in as you and access all your pinchmarks.
Mitigations:
- The key file is protected by the filesystem permissions on your computer
- If compromised, immediately revoke all
api-andlb-tokens in Settings - Generate a new
hu-key by running SetupWizard and re-registering - Back up your identity key offline (secure location like a password manager)
Risk: Attacker can impersonate you on the network.
Mitigations:
- Always use HTTPS in production (reverse proxy + TLS required)
api-tokens are short-lived and can be rotated frequentlysessionStorageclears on tab close, preventing token theft from browser memory- Use VPN or private networks for sensitive operations
Risk: Attacker gains access to the running process and database.
Mitigations:
- Enable database encryption (
DB_ENCRYPTION_KEY) so the data is unreadable without the key - Run Docker with
NODE_ENV=productionto disable stack traces - Restrict port 4646 to localhost; expose via Nginx/Caddy TLS only
- Use Docker security options: read-only root filesystem, dropped capabilities, seccomp profiles
- Regularly rotate encryption keys and API tokens
Risk: Raw SQLite database could be examined offline.
Mitigations:
- Database encryption makes the file unreadable without
DB_ENCRYPTION_KEY - Store backups encrypted at rest (encrypted volumes, S3 with server-side encryption)
- Never commit
DB_ENCRYPTION_KEYto version control - Keep backup locations as secure as the original
Risk: Malicious agent uses your key to read/write bookmarks.
Mitigations:
- Revoke the leaked
lb-key immediately in Settings β Agent Permissions - Audit logs show all actions performed with that key (timestamp + details)
- Generate a new key for the agent with fresh permissions
- Implement request-level rate limiting (roadmap item) to catch abuse early
Do NOT open a public GitHub issue for security vulnerabilities.
Instead, report privately:
- Email: Reach out to the maintainer directly (see GitHub profile).
- Include:
- Description of the vulnerability
- Steps to reproduce
- Potential impact
- Suggested fix (if known)
- Response time: We aim to acknowledge within 72 hours.
- Credit: Reporters are acknowledged in release notes (anonymity respected on request).
Before exposing ClawChives to the public internet:
- Place the API behind Nginx or Caddy with TLS (HTTPS)
- Set
CORS_ORIGINto your specific frontend domain, not* - Restrict port
4646to localhost, proxy via Nginx/Caddy - Enable database encryption via
DB_ENCRYPTION_KEY - Regularly rotate
api-tokens viaPOST /api/auth/token - Revoke unused agent keys in Settings β Agent Permissions
- Back up the
sqlite_dataDocker volume regularly - Store
clawchives_identity_key.jsonin a secure, offline location - Review audit logs for unusual agent activity
- Keep
Node.jsand dependencies updated regularly
- Full key system details: See BLUEPRINT.md Β§ Key System Architecture
- Data flow & architecture: See BLUEPRINT.md Β§ Data Flow
- Deployment instructions: See README.md Β§ Running with Docker
- Contribution security standards: See CONTRIBUTING.md
- ClawStack security alignment: See CRUSTSECURITY.md