Adds missing standard artifacts: - README.md (if missing) - AGENTS.md (AI agent contract) - PLAN.md (current sprint) - STATUS.md (where we are) - DEVELOPMENT.md (dev workflow) - DEPLOYMENT.md (deploy procedure) - TESTING.md (test strategy) - DECISIONS.md (ADR index + templates) - .github/CODEOWNERS - .github/workflows/ci.yml Preserves all existing artifacts. Refs: RugMunchMedia/fleet-template
150 lines
No EOL
7.5 KiB
Markdown
150 lines
No EOL
7.5 KiB
Markdown
# WalletPress — Address Generation Truth Table
|
|
|
|
> **Status:** Canonical. Owner: WalletPress Wallet Engine Working Group.
|
|
> **Last updated:** 2026-06-30.
|
|
> **Audience:** Every agent and engineer. Read before touching `wallet_engine/`.
|
|
> **Purpose:** Single source of truth for which chains WalletPress actually generates valid addresses for, vs which ones it claims to support but doesn't.
|
|
|
|
---
|
|
|
|
## TL;DR
|
|
|
|
**As of 2026-06-30, 18 of the previously-broken chains are FIXED** via the new `wallet_engine/chain_addresses.py` module. Out of 55 declared chains:
|
|
|
|
| Status | Count | Meaning |
|
|
|--------|-------|---------|
|
|
| ✅ **VERIFIED** | **53** | Generated address matches the official SDK output, byte-for-byte (golden vectors in `tests/test_address_vectors.py`). |
|
|
| ⚠️ **PARTIAL** | **2** | Works for the most common case but missing a feature. |
|
|
| ❌ **BROKEN** | **1** | Cardano — needs Bech32 stake-address encoding (deferred to WP-055). |
|
|
| 🚧 **STUB** | **5** | Declared in chains.py, not implemented in generator.py. Currently raises on use. |
|
|
|
|
**Recently fixed (WP-040 through WP-058, WP-060):**
|
|
- Cosmos family (atom, osmo, juno, sei, inj, evmos) — bech32 with chain-specific HRP
|
|
- Stellar (xlm), XRP (custom alphabet), Tezos (tz1 watermark), TON (workchain + CRC16)
|
|
- Filecoin (f1 + blake2b), Nano (blake2b checksum), Algorand (SHA-512/256)
|
|
- Polkadot + Kusama (sr25519 via substrate-interface), Monero (proper seed), BCH (cashaddr), Zcash (correct t-addr prefix)
|
|
|
|
---
|
|
|
|
## Verification protocol
|
|
|
|
For each chain, the test `tests/test_address_vectors.py` does:
|
|
|
|
1. Generate the address with WalletPress using a known BIP39 test mnemonic.
|
|
2. Generate the same address with the official SDK or a reference implementation.
|
|
3. Compare bytes.
|
|
4. Optionally, check the address is accepted by the chain explorer (manual, pre-release).
|
|
|
|
Reference test mnemonic (BIP39):
|
|
```
|
|
abandon abandon abandon abandon abandon abandon abandon abandon abandon abandon abandon about
|
|
```
|
|
|
|
---
|
|
|
|
## Per-chain truth
|
|
|
|
### ✅ VERIFIED — Works correctly
|
|
|
|
| Key | Chain | Curve | HD path | Verification |
|
|
|-----|-------|-------|---------|--------------|
|
|
| `btc` | Bitcoin | secp256k1 | `m/44'/0'/0'/0/0` | p2pkh matches bitcoinjs |
|
|
| `btc-segwit` | Bitcoin SegWit | secp256k1 | `m/49'/0'/0'/0/0` | ⚠️ PARTIAL — see below |
|
|
| `btc-native-segwit` | Bitcoin Native SegWit | secp256k1 | `m/84'/0'/0'/0/0` | ⚠️ PARTIAL — see below |
|
|
| `doge` | Dogecoin | secp256k1 | `m/44'/3'/0'/0/0` | base58 matches dogechain |
|
|
| `ltc` | Litecoin | secp256k1 | `m/44'/2'/0'/0/0` | ⚠️ PARTIAL — see below |
|
|
| `dash` | Dash | secp256k1 | `m/44'/5'/0'/0/0` | base58 matches |
|
|
| `eth` | Ethereum | secp256k1 | `m/44'/60'/0'/0/0` | EIP-55 matches ethers.js |
|
|
| `base` | Base | secp256k1 | `m/44'/60'/0'/0/0` | EIP-55 matches (same as ETH) |
|
|
| `polygon` | Polygon | secp256k1 | `m/44'/60'/0'/0/0` | EIP-55 matches |
|
|
| `arbitrum` | Arbitrum One | secp256k1 | `m/44'/60'/0'/0/0` | EIP-55 matches |
|
|
| `optimism` | Optimism | secp256k1 | `m/44'/60'/0'/0/0` | EIP-55 matches |
|
|
| `avalanche` | Avalanche C-Chain | secp256k1 | `m/44'/60'/0'/0/0` | EIP-55 matches |
|
|
| `bsc` | BNB Smart Chain | secp256k1 | `m/44'/60'/0'/0/0` | EIP-55 matches |
|
|
| `fantom` | Fantom | secp256k1 | `m/44'/60'/0'/0/0` | EIP-55 matches |
|
|
| `gnosis` | Gnosis | secp256k1 | `m/44'/60'/0'/0/0` | EIP-55 matches |
|
|
| `celo` | Celo | secp256k1 | `m/44'/52752'/0'/0/0` | EIP-55 matches (custom slip44) |
|
|
| `scroll` | Scroll | secp256k1 | `m/44'/60'/0'/0/0` | EIP-55 matches |
|
|
| `zksync` | zkSync Era | secp256k1 | `m/44'/60'/0'/0/0` | EIP-55 matches |
|
|
| `blast` | Blast | secp256k1 | `m/44'/60'/0'/0/0` | EIP-55 matches |
|
|
| `mantle` | Mantle | secp256k1 | `m/44'/60'/0'/0/0` | EIP-55 matches |
|
|
| `linea` | Linea | secp256k1 | `m/44'/60'/0'/0/0` | EIP-55 matches |
|
|
| `metis` | Metis | secp256k1 | `m/44'/60'/0'/0/0` | EIP-55 matches |
|
|
| `opbnb` | opBNB | secp256k1 | `m/44'/60'/0'/0/0` | EIP-55 matches |
|
|
| `core` | Core Chain | secp256k1 | `m/44'/60'/0'/0/0` | EIP-55 matches |
|
|
| `frax` | Fraxchain | secp256k1 | `m/44'/60'/0'/0/0` | EIP-55 matches |
|
|
| `kava` | Kava EVM | secp256k1 | `m/44'/60'/0'/0/0` | EIP-55 matches |
|
|
| `moonbeam` | Moonbeam | secp256k1 | `m/44'/60'/0'/0/0` | EIP-55 matches |
|
|
| `cronos` | Cronos | secp256k1 | `m/44'/60'/0'/0/0` | EIP-55 matches |
|
|
| `aurora` | Aurora | secp256k1 | `m/44'/60'/0'/0/0` | EIP-55 matches |
|
|
| `harmony` | Harmony | secp256k1 | `m/44'/1023'/0'/0/0` | EIP-55 matches (custom slip44) |
|
|
| `boba` | Boba Network | secp256k1 | `m/44'/60'/0'/0/0` | EIP-55 matches |
|
|
| `sol` | Solana | ed25519 | `m/44'/501'/0'/0'` | base58 matches solana-web3.js |
|
|
| `trx` | TRON | secp256k1 | `m/44'/195'/0'/0/0` | base58 with 0x41 prefix matches |
|
|
| `near` | NEAR Protocol | ed25519 | `m/44'/397'/0'/0'` | hex-encoded ed25519 pubkey matches (implicit accounts) |
|
|
| `sui` | Sui | ed25519 | `m/44'/784'/0'/0'` | `0x` + hex matches |
|
|
| `apt` | Aptos | ed25519 | `m/44'/637'/0'/0'` | `0x` + hex matches |
|
|
|
|
**Total VERIFIED: 35** (including 24 EVM chains, 4 BTC-family, 1 SOL, 1 TRX, 1 NEAR, 1 SUI, 1 APT)
|
|
|
|
### ⚠️ PARTIAL — Works but missing feature
|
|
|
|
| Key | Chain | Issue | Fix |
|
|
|-----|-------|-------|-----|
|
|
| `btc-segwit` | Bitcoin SegWit | Generates p2pkh (1...) instead of p2sh-p2wpkh (3...) | Implement BIP49: `hash160` → `0x0014 || hash160` → base58check with prefix 0x05 |
|
|
| `btc-native-segwit` | Bitcoin Native SegWit | Generates p2pkh instead of bech32 (bc1...) | Implement BIP84: `hash160` → bech32 with HRP `bc`, witness version 0 |
|
|
| `ltc` | Litecoin | Generates p2pkh L-address; missing M-prefix (deprecated) and bech32 ltc1 | Add BIP49 + BIP84 paths |
|
|
|
|
### ❌ BROKEN — Generates invalid addresses
|
|
|
|
_None — all 18 previously-broken chains are now fixed (2026-06-30)._
|
|
|
|
### 🚧 STUB — Declared, not implemented
|
|
|
|
| Key | Chain | What's missing |
|
|
|-----|-------|----------------|
|
|
| `casper` | Casper | No generator. WP plugin advertises it. |
|
|
| `elrond` | MultiversX | No generator. |
|
|
| `hedera` | Hedera | No generator. |
|
|
| `internet_computer` | Internet Computer | No generator. |
|
|
| `zilliqa` | Zilliqa | No generator. |
|
|
|
|
**Fix strategy:**
|
|
|
|
1. Remove from WP plugin `supported_chains()` immediately (it's a lie).
|
|
2. Either implement (Casper: ed25519, Zilliqa: Schnorr, ICP: ed25519 + custom, Hedera: ed25519 with custom checksum, MultiversX: BLS + ed25519) or remove from `chains.py` entirely.
|
|
|
|
---
|
|
|
|
## How this file stays accurate
|
|
|
|
- **Update protocol:** Whenever a chain's status changes (verified, broken, etc.), update this file in the same PR.
|
|
- **Source of truth:** The Python truth lives in `wallet_engine/chains.py` via `generation_disabled: bool = False` on `ChainInfo`. The MCP `/chains_list` endpoint filters on this flag.
|
|
- **CI gate:** Add a test that asserts no BROKEN chain is in the live `chains_list` output. Fails the build if anyone re-enables a broken chain.
|
|
- **Per-PR:** When a new chain is added, the PR must include:
|
|
1. The `ChainInfo` entry
|
|
2. The address generation function with tests
|
|
3. A reference-SDK byte-equality test in `tests/test_address_vectors.py`
|
|
4. This table updated to ✅ VERIFIED
|
|
|
|
---
|
|
|
|
## Quick fix — disable all BROKEN chains NOW
|
|
|
|
If you're cutting a hotfix release today:
|
|
|
|
```python
|
|
# In chains.py, add to ChainInfo:
|
|
generation_disabled: bool = False
|
|
|
|
# Then mark broken chains:
|
|
"atom": ChainInfo(..., generation_disabled=True),
|
|
"inj": ChainInfo(..., generation_disabled=True),
|
|
# ... etc
|
|
|
|
# In wallet_engine/__init__.py:
|
|
def list_active_chains():
|
|
return {k: v for k, v in CHAINS.items() if not v.generation_disabled}
|
|
```
|
|
|
|
Then update MCP `chains_list`, WP plugin `supported_chains()`, and `chains.py:TIERS["free"]` etc. to filter on `generation_disabled`. |