A mobile-first SPA for tracking a crypto portfolio against target allocations. Holdings are stored in a long-lived browser cookie, live EUR prices and history come from the CoinGecko API.
- HOLDINGS editor — add/remove tracked coins, set amounts, Save (writes a long-lived browser cookie, 1 year) or Reset to defaults
- Portfolio Value — total net worth plus a performance line plot (1M / 6M / 1Y periods) with a hover tooltip showing date · net worth
- Target Delta — per-category stat cards highlighting what to buy (negative =
--danger) - Portfolio Split — allocation shares as progress bars
- Dark theme, mobile-first layout, Italian-formatted dates and numbers (
it-IT)
- Svelte 5 (runes:
$state/$derived/$props) + TypeScript - Vite 8 build, uPlot for the chart (canvas-based)
- Docker — two-stage build (
node:24-alpine→nginx:alpine), serves the staticdist/on host port3004 - CoinGecko keyless API with throttling/retry/caching hardening
npm ci # install deps (Node >= 22.12)
npm run dev # Vite dev server
npm run check # svelte-check typecheck
npm run build # production bundle to dist/
npm run preview # serve dist/ locallyDocker:
docker compose up --build -d # serves http://localhost:3004The keyless CoinGecko pool is IP-shared (~10–30 calls/min). To raise the limit to the Demo plan's ~100/min, copy .env.example to .env and set VITE_COINGECKO_API_KEY to a free demo key. The key is inlined into the client bundle, so only use a demo-tier key here.
This project started as a previous version of the app built without AI assistance. It was then expanded — upgraded, redesigned and extended with new features — with the help of an AI coding agent (opencode), running the DeepSeek V4 Flash model. The agent drafted, refactored and reviewed the code under human direction.