Files
trumpsignal-backend/deploy/ENCRYPTION_KEY_BACKUP.md
k b941223c88 fix: complete v5 routing — API exposure, rescore persistence, leverage cap, key backup doc
Three plumbing fixes + one ops doc that close the gaps from the audit.

scripts/rescore_v5.py
  Was overwriting only signal/conf/reasoning/sentiment/relevant/
  prefilter_reason/analysis_version. Now also persists target_asset,
  category, expected_move_pct — without these the bot can't route
  rescored posts correctly (would silently fall back to BTC).

app/schemas.py + app/api/posts.py
  TrumpPost response model didn't expose target_asset/category/
  expected_move_pct, so the frontend had no way to display "this
  signal will trade SOL". Added the three fields + mapping in
  _post_to_schema(). Pre-v5 posts return null. No frontend changes
  yet — display work is a follow-up.

app/services/hyperliquid.py
  HL caps max leverage per asset (BTC/ETH 50×, SOL 20×, memes 3-5×).
  set_leverage() always tried to push self._leverage — if user set
  30× and bot routed to TRUMP, HL rejected the order and the trade
  silently dropped. Added _get_max_leverage() (queries meta()'s
  maxLeverage field) and _clip_leverage() that caps to HL's max.
  set_leverage now returns the effective leverage so callers can
  use it for notional sizing if needed.

deploy/ENCRYPTION_KEY_BACKUP.md
  Documented mandatory backup procedure for the symmetric key that
  encrypts every user's HL API key. Lost key = all users' bots dead
  with no recovery. Includes rotation procedure + quarterly test
  step + things-not-to-do list.

Co-Authored-By: Claude Opus 4.7 <noreply@anthropic.com>
2026-05-08 19:59:30 +08:00

75 lines
2.9 KiB
Markdown

# ENCRYPTION_KEY backup procedure — DO NOT SKIP
The `ENCRYPTION_KEY` env var encrypts every user's Hyperliquid API key
before it touches the database. If this key is **lost** or **rotated
without re-encrypting** the existing rows, every active user's bot
permanently stops trading — there is no recovery path. This is the
single most-load-bearing secret in the project.
## What it looks like
```
ENCRYPTION_KEY=1cf813d6790cc1b1c0981951703ca387d58321d81dc9b5b4982c07487edc478e
```
A 64-char hex string (32 bytes). Used by `app/services/crypto.py` via
Fernet-equivalent symmetric encryption.
## Backup requirements (mandatory before going live)
Store the production value in **at least two locations**, at least one
of which is **offline / non-cloud**:
### 1. Password manager (1Password / Bitwarden / KeePass)
- Item type: "Secure Note"
- Title: `TrumpSignal — ENCRYPTION_KEY (production)`
- Body: the 64-char hex value
- Add note: "Lost = every user's bot dead. No way to recover."
- Tag/folder for fast retrieval
### 2. Offline physical backup
Pick one (or do both):
- **Paper**: print the key on a single sheet, store in a locked drawer
/ safe / safety deposit box. Label: "TrumpSignal encryption key —
do not discard, do not photograph, do not type into computers."
- **Hardware key**: write to a USB drive that lives offline, kept in
the same safe. Label and date it.
### 3. (Optional) Co-founder / trusted-party split
If multiple humans run the project: split the key (Shamir's Secret
Sharing or just give halves to two people) so no single person can
walk off with it AND no single person can lose all copies.
## Before any rotation
Rotating the key is **not free**. To rotate:
1. Generate `NEW_KEY`.
2. **Decrypt every existing `subscriptions.hl_api_key` with the old
key**, re-encrypt with the new key, write back. (Script not
shipped — has to be written carefully.)
3. Only after the migration completes, swap env var and restart.
4. Update both backup locations with `NEW_KEY`.
5. Securely destroy the old key copies after a 30-day cool-off
(during which you confirm no users got broken).
If you skip step 2, every existing user's HL key becomes garbage on
the new server and their bot silently stops working.
## How to test backups (do this once a quarter)
1. Pull the key out of password manager → match against the env var
on the running server.
2. Pull the offline copy → match against the password-manager copy.
3. Confirm both match. If any drift, sync immediately — never assume
the running server has the "true" copy without verifying.
## What NOT to do
- ❌ Don't paste the key into Slack / Discord / email.
- ❌ Don't commit the key to git (`.env` is in `.gitignore`, but
double-check before any `git add -A`).
- ❌ Don't share via screenshot — keys can be OCR'd from anywhere.
- ❌ Don't store only on the server — if the server dies, you lose it.
- ❌ Don't rotate "just because" — it's expensive and risky.