Blog · Orma · · 6 min read

Building a Personal Analytics Platform with Supabase and Next.js

The architecture decisions behind xeve — why Supabase over Firebase, why native Swift over Electron, and what I learned building a full-stack analytics platform as a solo developer.

xeve started as a weekend project to track my app usage. Eighteen months later, it is a full personal analytics platform with a native macOS app, iOS companion app, web dashboard, VS Code extension, and Claude Code integration. Here is how the architecture evolved and what I learned.

Why Supabase Over Firebase

The backend decision came down to two options: Firebase and Supabase. I chose Supabase for three reasons:

RPC Functions for Aggregations

One architectural pattern that worked well: using PostgreSQL RPC functions for all dashboard queries. Instead of fetching raw rows and aggregating in JavaScript, the database does the heavy lifting. Functions like get_app_usage_summary, get_hourly_activity, and compute_correlation return pre-aggregated data. This keeps the web app fast and the data transfer minimal.

Why Native Swift Over Electron

The macOS tracker had to be a native app. There was no other option. Here is why:

Next.js App Router for the Dashboard

The web dashboard uses Next.js 15 with the App Router. Server components by default, client components only for charts (Recharts) and animations (Framer Motion). This keeps the initial page load fast and reduces client-side JavaScript.

The design system follows an industrial minimalist aesthetic: monospace typography, dark backgrounds, orange accents, sharp corners. Every component uses the same design tokens defined in CSS custom properties.

Date Handling

One surprising challenge was timezone-safe date handling. Users in different timezones need their "today" to align with their local day, not UTC. The solution is a getDateRange utility that adds a 12-hour buffer to date boundaries, ensuring queries capture the full local day regardless of timezone offset.

iOS Companion App

The iOS app adds HealthKit data (steps, energy, sleep, heart rate), location tracking (home/work detection), and widgets. Key learnings:

The Correlation Engine

The correlation engine computes Pearson correlation coefficients across 19 metric pairs automatically. It runs as part of the daily rollup edge function, pulling from daily summaries. Each correlation gets a plain-English interpretation and a statistical significance flag.

The hardest part was choosing which metric pairs to correlate. Too many pairs and you get noise. Too few and you miss insights. The current 19 pairs cover the most actionable relationships: sleep vs. productivity, exercise vs. focus, music vs. coding, and more.

Lessons Learned

What is Next

The roadmap includes Whoop OAuth integration for recovery and strain data, Stripe billing for a Pro tier, and interactive iOS widgets. The architecture is solid enough to support these additions without major refactoring — which is the whole point of getting the foundation right.

If you want to try xeve, it is free during early access. Sign up at xeve.io/signup.