|
| 1 | +# CLAUDE.md - Development Context for Hone |
| 2 | + |
| 3 | +This file provides context for AI-assisted development sessions. |
| 4 | + |
| 5 | +## Project Overview |
| 6 | + |
| 7 | +Hone is a self-hosted personal finance tool that detects wasteful spending: |
| 8 | +- Zombie subscriptions (forgotten recurring charges) |
| 9 | +- Price increases (services that quietly raised prices) |
| 10 | +- Duplicate services (multiple streaming/storage/etc) |
| 11 | + |
| 12 | +## Architecture |
| 13 | + |
| 14 | +See `README.md` for architecture diagram. Stack: React + Vite frontend, Axum REST API, SQLite database. |
| 15 | + |
| 16 | +## Crate Structure |
| 17 | + |
| 18 | +- **hone-core**: Shared library |
| 19 | + - `db/` - SQLite with r2d2 pooling, SQLCipher encryption |
| 20 | + - `backup/` - Pluggable backup system (local filesystem, R2 stub) |
| 21 | + - `models.rs` - Domain types |
| 22 | + - `import.rs` - CSV parsers for major US banks |
| 23 | + - `export.rs` - Transaction CSV export, full JSON backup/restore |
| 24 | + - `detect.rs` - Waste detection algorithms |
| 25 | + - `tags.rs` - Tag assignment engine |
| 26 | + - `ai/` - Pluggable local AI backend (Ollama, OpenAI-compatible, Mock) |
| 27 | + - `prompts.rs` - Prompt library with override support |
| 28 | + - `model_router.rs` - Task-based model routing with health tracking |
| 29 | + - `context.rs` - Context assembler for LLM prompts |
| 30 | + - `training.rs`, `training_pipeline.rs` - Fine-tuning infrastructure |
| 31 | + - `insights/` - Proactive financial insights engine |
| 32 | + |
| 33 | +- **hone-cli**: Command-line interface |
| 34 | + - `commands/` - Command implementations split by domain |
| 35 | + - Commands: init, import, detect, serve, dashboard, status, accounts, transactions, subscriptions, alerts, entities, tags, rules, tag, untag, report, receipts, ollama, prompts, training, export, import-full, backup, rebuild, reset |
| 36 | + |
| 37 | +- **hone-server**: Axum REST API |
| 38 | + - `lib.rs` - Server config, router, auth middleware, security headers |
| 39 | + - `handlers/` - Domain-specific HTTP handlers (22 modules) |
| 40 | + - `mcp/` - MCP server for LLM tool access (enable with `--mcp-port 3001`) |
| 41 | + - Cloudflare Access authentication, audit logging |
| 42 | + |
| 43 | +## Key Design Decisions |
| 44 | + |
| 45 | +1. **CSV-only import** - No bank credentials stored, privacy-first |
| 46 | +2. **Encryption required** - SQLCipher encryption by default (`HONE_DB_KEY`); `--no-encrypt` for dev |
| 47 | +3. **Local AI only** - Ollama and OpenAI-compatible servers. No cloud APIs |
| 48 | +4. **Deduplication** - SHA256 hash of (date, description, amount) prevents double-imports |
| 49 | +5. **Secure by default** - Cloudflare Access auth required; `--no-auth` for local dev |
| 50 | +6. **Audit logging** - All API access logged |
| 51 | +7. **Full processing by default** - Import runs tagging + detection automatically |
| 52 | +8. **Raw data preservation** - Original CSV data stored as JSON for reprocessing |
| 53 | + |
| 54 | +## Development Stage |
| 55 | + |
| 56 | +**Pre-shipping**: We are NOT yet at the "shipping" stage. This means: |
| 57 | +- **No migrations required** - Schema changes can be made directly; just reset the database |
| 58 | +- **No backwards compatibility** - APIs, data formats, and behavior can change freely |
| 59 | +- **No deprecation cycles** - Old code/approaches can be removed immediately |
| 60 | + |
| 61 | +When we explicitly agree to enter the "shipping" stage, we'll add migrations and maintain backwards compatibility. |
| 62 | + |
| 63 | +## Database Schema |
| 64 | + |
| 65 | +Key tables (see `docs/SPLITS_DESIGN.md` for entity/split schema): |
| 66 | +- `accounts` - Bank accounts with optional `entity_id` |
| 67 | +- `transactions` - Individual charges (with `archived`, `original_data`, `import_format`) |
| 68 | +- `subscriptions` - Detected recurring patterns with `account_id` |
| 69 | +- `alerts` - Waste detection findings |
| 70 | +- `tags` - Hierarchical category tags (17 root tags seeded) |
| 71 | +- `transaction_tags` - Transaction-to-tag mapping with source tracking |
| 72 | +- `tag_rules` - User-defined patterns for auto-tagging |
| 73 | +- `audit_log` - API access history |
| 74 | +- `entities` - People, pets, vehicles, properties |
| 75 | +- `locations`, `trips`, `mileage_logs` - Location and travel tracking |
| 76 | +- `receipts` - Receipt storage with status workflow |
| 77 | +- `merchant_*_cache` - Learned merchant classifications, names, tags |
| 78 | +- `import_sessions`, `import_skipped_transactions` - Import tracking |
| 79 | +- `user_feedback` - Feedback on AI-generated content |
| 80 | +- `training_experiments` - Fine-tuning experiment tracking |
| 81 | +- `reprocess_runs`, `reprocess_snapshots` - Reprocess comparison |
| 82 | +- `insight_findings` - Proactive financial insights |
| 83 | +- `ollama_metrics` - AI call tracking (latency, success, tool calls metadata for explore queries) |
| 84 | + |
| 85 | +## Current State |
| 86 | + |
| 87 | +See `docs/FEATURES.md` for comprehensive feature list. |
| 88 | + |
| 89 | +**Test coverage**: 788 Rust tests, Playwright UX tests |
| 90 | + |
| 91 | +**Not yet implemented**: Cloud backup to Cloudflare R2 (stub ready) |
| 92 | + |
| 93 | +## Detection Algorithms |
| 94 | + |
| 95 | +See `docs/DETECTION.md` for algorithm details. Six algorithms: |
| 96 | +- Zombie Detection - forgotten recurring charges |
| 97 | +- Price Increase Detection - subscription price changes |
| 98 | +- Duplicate Detection - multiple services in same category |
| 99 | +- Auto-Cancellation Detection - stopped subscriptions |
| 100 | +- Resume Detection - reactivated subscriptions |
| 101 | +- Spending Anomaly Detection - unusual spending patterns |
| 102 | + |
| 103 | +## AI Integration |
| 104 | + |
| 105 | +See `docs/ollama.md` for setup and configuration. |
| 106 | + |
| 107 | +**Three modes:** |
| 108 | +1. **Classification Mode** (`OLLAMA_HOST`) - merchant classification, normalization, subscription detection |
| 109 | +2. **Agentic Mode** (`ANTHROPIC_COMPATIBLE_HOST`) - tool-calling for deeper analysis |
| 110 | +3. **Explore Mode** - conversational interface using agentic mode to answer financial questions |
| 111 | + - Multi-turn conversations with session persistence |
| 112 | + - Model selector to switch between available Ollama models at runtime |
| 113 | + - Queries tracked in AI Metrics as `explore_query` operations with tool call history |
| 114 | + |
| 115 | +**Prompts**: Stored in `prompts/` with override support (`~/.local/share/hone/prompts/overrides/`) |
| 116 | + |
| 117 | +**Model routing**: Config in `config/models.toml` with task-based routing and health tracking |
| 118 | + |
| 119 | +## Development Commands |
| 120 | + |
| 121 | +```bash |
| 122 | +# Build |
| 123 | +make build |
| 124 | + |
| 125 | +# Run backend (port 3000) |
| 126 | +export HONE_DB_KEY="your-passphrase-here" |
| 127 | +cargo run -- serve --port 3000 |
| 128 | + |
| 129 | +# Run frontend dev server (port 5173) |
| 130 | +cd ui && npm run dev |
| 131 | + |
| 132 | +# Enable Ollama |
| 133 | +export OLLAMA_HOST="http://localhost:11434" |
| 134 | +export OLLAMA_MODEL="gemma3" |
| 135 | + |
| 136 | +# Quick test flow |
| 137 | +cargo run -- --no-encrypt init |
| 138 | +cargo run -- --no-encrypt import --file samples/sample.csv |
| 139 | +cargo run -- --no-encrypt dashboard |
| 140 | + |
| 141 | +# Reset database |
| 142 | +cargo run -- --no-encrypt reset --soft -y |
| 143 | + |
| 144 | +# Run tests |
| 145 | +cd ui && npm run test:ux |
| 146 | +``` |
| 147 | + |
| 148 | +## UI Structure |
| 149 | + |
| 150 | +``` |
| 151 | +ui/src/ |
| 152 | +├── components/ |
| 153 | +│ ├── common/ # Shared UI components |
| 154 | +│ ├── Dashboard/ # Dashboard view |
| 155 | +│ ├── Transactions/ # Transaction list, detail tabs |
| 156 | +│ ├── Subscriptions/ # Subscription management |
| 157 | +│ ├── Alerts/ # Alert cards with detail modal |
| 158 | +│ ├── Insights/ # Proactive insights |
| 159 | +│ ├── Import/ # CSV import, history |
| 160 | +│ ├── Tags/ # Tag tree management |
| 161 | +│ ├── Reports/ # Charts and reports (Recharts) |
| 162 | +│ ├── Receipts/ # Receipt upload, linking |
| 163 | +│ ├── Ollama/ # AI Metrics page (all AI call tracking) |
| 164 | +│ ├── Feedback/ # Feedback history page |
| 165 | +│ └── Explore/ # Conversational query interface with model selector |
| 166 | +├── hooks/ # Custom React hooks |
| 167 | +├── App.tsx # Layout and routing |
| 168 | +├── api.ts # API client |
| 169 | +└── types.ts # TypeScript interfaces |
| 170 | +``` |
| 171 | + |
| 172 | +## Code Style |
| 173 | + |
| 174 | +- Rust: Follow standard idioms, use Result types, propagate errors with `?` |
| 175 | +- TypeScript: Strict mode, prefer named exports |
| 176 | +- CSS: Tailwind utilities, custom components in index.css |
| 177 | +- Comments: Explain "why" not "what" |
| 178 | + |
| 179 | +## UI Design Principles |
| 180 | + |
| 181 | +- Clean, confident typography - numbers feel important |
| 182 | +- Semantic color: green=income, amber=attention, red=waste (not all expenses) |
| 183 | +- Normal expenses use neutral colors |
| 184 | +- Subtle motion - alive but not distracting |
| 185 | +- Satisfying interactions |
| 186 | +- No clutter - every element earns its place |
| 187 | + |
| 188 | +## Dark Mode Patterns |
| 189 | + |
| 190 | +Tailwind dark mode uses `dark:` prefix (follows system preference). |
| 191 | + |
| 192 | +- Primary text: `text-hone-900 dark:text-hone-100` |
| 193 | +- Secondary text: `text-hone-600 dark:text-hone-400` |
| 194 | +- Cards: `bg-white dark:bg-hone-900` (via `.card` class) |
| 195 | +- Table headers: `bg-hone-50 dark:bg-hone-800` |
| 196 | +- Hover: `hover:bg-hone-50 dark:hover:bg-hone-800` |
| 197 | + |
| 198 | +## Test Data Guidelines |
| 199 | + |
| 200 | +- Major public company names are fine (Netflix, Amazon, Costco) |
| 201 | +- Avoid small regional/local business names |
| 202 | +- Use fictional names for non-public entities |
| 203 | + |
| 204 | +## Deployment |
| 205 | + |
| 206 | +See `docs/deployment.md` for Docker deployment guide. |
| 207 | + |
| 208 | +Docker images: `ghcr.io/heskew/hone-money` (multi-arch: amd64, arm64) |
0 commit comments