← All case studies

ClientPersonal / independent engagement

RoleSole engineer

StackReact · Supabase · Alpha Vantage

StatusLive

Stock Tracker

Outcome below is still a placeholder. Everything else reflects the real project.

The problem, as stated

A client wanted a place to log stock trades with notes attached, deliberately without connecting it to a real brokerage account. No live balances, no read access to an actual portfolio. Manual entry only, by design.

Why off-the-shelf would've fallen short

A generic portfolio tracker either wants a brokerage connection or doesn't support the kind of free-text, versioned annotation the client actually wanted attached to each trade. Scoping the client-facing app to manual entry only was itself the constraint-first move: less risk, less cost, no third-party financial-account access to secure or reason about, and nothing the client didn't ask for. The live-sync piece (SnapTrade, real Fidelity positions) was never a client requirement — it's a personal extension, built against my own portfolio, specifically to explore what a live brokerage connection costs in engineering and design once you take on that risk deliberately rather than by default.

What was built

The client-facing core: log buy/sell trades with free-text notes, filter and paginate history, and a "Journal" view of every annotation with full revision history rather than overwrite-in-place — manual entry throughout, no brokerage connection required or possible for that scope. On top of that, as a personal extension beyond the client engagement, a "Positions" view syncs live brokerage holdings via SnapTrade, verified against a real connected Fidelity account under my own login. Market data (quotes, symbol search, daily history, company profiles) is proxied server-side through four Supabase Edge Functions backed by a Postgres response cache, so the Alpha Vantage API key never reaches the browser. Every table is scoped by Postgres row-level security to the authenticated user, and money is stored as integer cents throughout to avoid floating-point drift. One edge function's deploy was originally Terraform-managed like the rest, then deliberately reverted to a CLI-based deploy after `deno bundle` produced two different checksums from the same unchanged source on separate runs, which broke Terraform's apply-consistency check. The other four edge functions stayed Terraform-managed; that one didn't, and the reasoning is documented in the repo rather than silently worked around.

Outcome

Placeholder.

Full stack

React 19, Vite 8, TypeScript, TanStack Query, React Hook Form + Zod, Tailwind CSS 4 with shadcn/ui. Supabase (Postgres, Auth via magic link with an allowlist gate, Edge Functions). Alpha Vantage for market data, SnapTrade for brokerage account sync. S3 + CloudFront via Terraform, GitHub Actions CI/CD with OIDC (no stored AWS keys). Vitest + Testing Library for unit/component tests, Playwright for end-to-end.

← Previous case study: Pivotal Pathways