The backend for a social app that ranks by “vibe”, not likes — a Claude-powered engine that auto-tags posts, profiles user personality “archetypes”, and flags each post's bias, over a feed tuned with composite indexes for scale.
01 — Overview
Vybstack is the backend for a mobile social platform organised around emotional “vibes” rather than likes. Users react with one of three vibe levels, join interest “Tribes”, and attach music to posts. Two AI hooks set it apart: an “archetype” system that profiles a user's personality from their liked content, and an AI “Bias Indicator” that classifies each post's political lean, agenda risk and emotional framing — “context, not truth”. It's a Node.js / Express + Prisma / PostgreSQL API.
Role
Timeline
Stack
02 — Context
A personalized feed has to rank content cheaply and stay fast as posts and reactions scale, enrich every post with unreliable LLM output without blocking the writer, and evolve its schema without breaking live mobile clients.
I built the entire backend. The hybrid feed ranks candidates by a weighted blend of interest match, tag preference, recency and engagement, served with cursor pagination over a composite (isDeleted, visibility, createdAt) index added in a dedicated index migration. AI enrichment (Claude + Claude Vision auto-tagging, archetype assignment, the Bias Indicator) runs in the background after a fast write, with strict enum and numeric-clamp validation so a misbehaving model can't poison the database. I refactored a per-interest N+1 loop into two batched queries, added global and per-route rate limiting, and shipped continuously via GitHub Actions to EC2 / PM2.
03 — Showcase
04 — Capabilities
05 — Contribution
As Backend Engineer, here is exactly what I owned and delivered on this project.
06 — Engineering
Challenge
Enriching every post with AI without slowing down posting.
Solution
createContent returns immediately, then runs tagging and the Bias Indicator in a background setImmediate block with a foreground / background retry strategy.
Challenge
LLMs return malformed or out-of-range data that could poison the feed.
Solution
Wrapped every AI response in regex JSON extraction, enum validation and numeric clamping, with a null sentinel for “not yet classified”.
Challenge
Creating a post ran 2×N queries to associate interests.
Solution
Refactored the per-interest loop into two batched queries (findMany IN + createMany skipDuplicates).
Challenge
Evolving the schema without breaking shipped mobile clients.
Solution
Dual-wrote the deprecated field alongside new bias columns during the client rollout window.
07 — Toolbox
08 — Impact