WalletPress — Python backend (FastAPI) + WordPress plugin. Wallet engine, x402 service, chain vault, hosting. CLI for wallet management. Production-grade wallet-as-a-service.
Five P0 security/correctness bugs fixed in this commit:
WP-002 (P0-1) — Free x402 credits
x402_service.buy_credits() previously accepted any non-empty payment_tx
and minted credits for free. Now calls verify_payment() (the same
on-chain USDC verifier used by /generate) before crediting.
Direct theft vector closed.
WP-003 (P0-2) — Unsalted SHA-256 hosted passwords
hosting.py used hashlib.sha256(password.encode()).hexdigest() with
no salt — rainbow-table crackable. Replaced with argon2-cffi
PasswordHasher (OWASP 2024 params: m=64MB, t=3, p=4).
Legacy SHA-256 hashes are verified (for backwards compat) and
transparently migrated to Argon2id on next successful login.
login() now also strips password_hash from the response (P2-11).
WP-004 (P0-3) — In-memory _team_keys + no role enforcement
main.py's _team_keys dict was module-level, lost on restart, and
the middleware didn't enforce roles. Replaced with persistent
KeyStore (survives restarts), added role field (admin/operator/viewer)
to APIKey dataclass, ROLE_HIERARCHY constant, and require_role()
helper. Middleware now:
- attaches verified APIKey to request.state.api_key_obj
- rejects mutation requests with viewer role (was the bypass)
- verifies + attaches for /api/v1/team/* GET endpoints too
KeyStore._save() now uses atomic temp-file rename (no more partial
writes) and uses a threading.Lock for safety. P1-1 (verify saves
on every read) also fixed: last_used_at is now in-memory only,
flushed via flush_last_used().
WP-005 (P0-5) — Env-only vault KEK
config.py now resolves the vault KEK in priority order:
1. WP_VAULT_PASSWORD env var (legacy, dev only)
2. ~/.walletpress/vault.key file (mode 0600)
3. {data_dir}/vault.key file (mode 0600)
4. Auto-generate on first run, persisted to vault.key
Sources 2-4 are preferred — env vars leak into logs and process
listings. Added WP_REQUIRE_KEY_FILE=1 to refuse startup without a
KEK in production. _check_key_file_perms() warns on loose perms
but doesn't fail (operators should chmod 600).
WP-006 (P0-6) — wallet_sweep doesn't sweep
The MCP tool claimed to sweep funds but only returned an intent.
Now actually builds, signs, and broadcasts EVM transactions:
- Decrypts private key from vault via get_generator
- Connects to chain RPC via Web3
- Builds tx: balance - gas_cost to destination
- Signs with eth_account
- Broadcasts via existing _evm_broadcast helper
- Records spending + audit log entry
Non-EVM chains (Solana, TRON, BTC family) still return intent +
clear 'not implemented' notice — to be added as separate PRs.
Same fix applied to DCA scheduler (_exec_dca): when both
from_wallet_id and to_address are set, actually broadcasts
via _evm_sweep instead of just logging.
Test results:
pytest tests/ tests/test_address_vectors.py
# 80 + 22 = 102 passed, 5 skipped, no regressions
Refs: AUDIT.md, SECURITY.md, BUILDER.md
Closes: WP-002, WP-003, WP-004, WP-005, WP-006
|
||
|---|---|---|
| backend | ||
| cli | ||
| installers | ||
| wp-plugin | ||
| .gitignore | ||
| .pre-commit-config.yaml | ||
| about.html | ||
| ADDRESS_GENERATION.md | ||
| ARCHITECTURE.md | ||
| AUDIT.md | ||
| BUILDER.md | ||
| buy.html | ||
| contact.html | ||
| CONTRIBUTING.md | ||
| docs.html | ||
| features.html | ||
| index.html | ||
| logo.svg | ||
| privacy.html | ||
| PROGRESS.md | ||
| ROADMAP.md | ||
| ROADMAP_V2.md | ||
| robots.txt | ||
| SECURITY.md | ||
| sitemap.xml | ||
| STRATEGY.md | ||
| terms.html | ||
| thanks.html | ||
| verify.html | ||
| walletpress-docs.pdf | ||
| WALLETPRESS.md | ||