11 files updated to reflect current state (v0.0.22 → v0.0.46): ARCHITECTURE.md: - Ring tones, group calls, read receipts, markdown rendering sections - Bot API expanded (BotFather, numeric IDs, Telegram compat) - Admin commands, known issues, 155 tests TASK_PLAN.md: - All P1-P4 marked DONE with version numbers - Additional completed work section (bots, ETH, ring tones, group calls) - New FC-P7 (Voice & Transport): cpal, Sender Keys, WebTransport - FC-P6-T9/T10 added PROGRESS.md: - Full version history table v0.0.22 through v0.0.46 - Known issues section README.md: - Voice calls, ring tones, group calls, read receipts, markdown, 155 tests SECURITY.md: - Bot API security, voice call security, admin commands sections - Updated protection tables USAGE.md: - Group calls, read receipts, markdown formatting, admin commands CLIENT.md: - Call commands, read receipts, markdown rendering LLM_HELP.md + LLM_BOT_DEV.md: - Call/group call/admin commands, ring tones, per-bot numeric IDs TESTING_E2E.md: - Tests 16-18: ring tones, group calls, admin commands CLAUDE.md: - Ring tone notes, group signal endpoint, MLS roadmap Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
4.7 KiB
featherChat — Design Principles & Conventions
MANDATORY: Version Bumping
After every set of changes that modifies functionality, bump the version:
Cargo.tomlworkspace version (e.g.0.0.22→0.0.23)crates/warzone-protocol/Cargo.tomlstandalone version (same)crates/warzone-server/src/routes/web.rsJSVERSIONconstantcrates/warzone-server/src/routes/web.rsservice workerCACHEversion (wz-vN→wz-v(N+1))
Never commit functional changes without bumping all four. The service worker cache MUST be bumped or browsers will serve stale WASM.
Architecture Principles
-
Single seed, multiple identities — Ed25519 (messaging), X25519 (encryption), secp256k1 (ETH address) all derived from one BIP39 seed via HKDF with domain-separated info strings.
-
E2E by default — All user messages are Double Ratchet encrypted. The server NEVER sees plaintext. Friend lists are client-side encrypted. Only bot messages are plaintext (v1). Group calls are transport-encrypted only (QUIC/TLS); MLS (RFC 9420) E2E encryption for group calls is planned but not yet implemented.
-
Server is semi-trusted — Server sees metadata (who talks to whom, timing, groups) but cannot read message content. Design all features with this trust boundary in mind.
-
Federation is transparent — Users don't need to know which server their peer is on. Key lookup, alias resolution, and message delivery automatically proxy through federation.
-
Telegram Bot API compatibility — Bot API follows Telegram conventions (getUpdates, sendMessage, token-in-URL). Bot aliases must end with Bot/bot/_bot.
-
Auth on writes, open reads — All POST/write endpoints require bearer tokens. GET/read endpoints are public (needed for key exchange before auth is possible).
Coding Conventions
Rust
- Workspace crates: protocol (no I/O), server (axum), client (ratatui), wasm (wasm-bindgen), mule (future)
- Error handling:
AppResult<T>in server,anyhow::Resultin client,ProtocolErrorin protocol - State:
AppStatewithArc<Mutex<>>for shared state,Arc<Database>for sled - Auth:
AuthFingerprintextractor as first handler param for protected routes - Fingerprints: always normalize with
normfp()(strip non-hex, lowercase) - New routes: create
routes/<name>.rs, addpub fn routes() -> Router<AppState>, merge inroutes/mod.rs
TUI
- 7 modules in
tui/: types, draw, commands, input, file_transfer, network, mod - All ChatLine must include
timestamp: Local::now() - Add new commands to both the handler chain AND
/helptext - Self-messaging prevention: check
normfp(&peer) != normfp(&self.our_fp)
Web (WASM)
- JS embedded in
routes/web.rsas Rust raw string — careful with escaping - Service worker cache version must be bumped on WASM changes (
wz-vN) WasmSession::initiate()stores X3DH result —encrypt_key_exchangemust NOT re-initiate- Ring tones use Web Audio API oscillators (no audio files) — see
startRingTone()/startRingbackTone()/stopRingTone()inweb.rs
Federation
- Persistent WS between servers, NOT HTTP polling
- Presence re-pushed every 10s + on connect
- Key lookup: proxy to peer for non-local fingerprints (never cache remote bundles)
- Alias resolution: fall back to peer if not found locally
- Registration: check peer to enforce global uniqueness
Bot API
- Token stored as
bot:<token>in tokens tree - Reverse lookup:
bot_fp:<fingerprint>→ token - Alias auto-registered on bot creation with
_botsuffix - Reserved aliases:
*Bot,*bot,*_botblocked for non-bots
Task Naming
FC-P{phase}-T{task}[-S{subtask}]
See docs/TASK_PLAN.md for the full breakdown.
Testing
- Protocol: unit tests in each module's
#[cfg(test)] - TUI: unit tests for types, input, draw (using ratatui TestBackend)
- WASM: can't test natively (js-sys dependency) — test equivalent logic in protocol crate
- Server: no integration tests yet (planned)
Key Files
| What | Where |
|---|---|
| Wire format | warzone-protocol/src/message.rs |
| Crypto primitives | warzone-protocol/src/crypto.rs |
| Server state | warzone-server/src/state.rs |
| All routes | warzone-server/src/routes/mod.rs |
| Federation | warzone-server/src/federation.rs |
| TUI commands | warzone-client/src/tui/commands.rs |
| Web client | warzone-server/src/routes/web.rs |
| WASM bridge | warzone-wasm/src/lib.rs |
| Group signal endpoint | warzone-server/src/routes/groups.rs (signal_group) |
| Ring tone functions | warzone-server/src/routes/web.rs (startRingTone, startRingbackTone, stopRingTone) |
| Task plan | docs/TASK_PLAN.md |
| Bot API docs | docs/BOT_API.md |
| LLM help ref | docs/LLM_HELP.md |