Case study
2025
SceneIt
A swipe-based movie discovery app, with Gemini-driven recommendations on a decoupled AWS architecture.
Role
Sole engineer — frontend, backend, deployment
Status
Released
Services
Applied LLM · Production web & commerce
The idea
Movie discovery is broken. The streaming services know what you’ve watched but optimise for retention. Aggregators surface what’s popular but not what’s right for tonight. The actually-good recommendation engine for a Tuesday evening is your friend group’s text thread, which doesn’t scale.
SceneIt is the version of that text thread that does scale: a swipe-based interface that learns from your reactions, paired with an LLM-backed recommendation pipeline that consumes a richer preference model than the usual five-star rating.
How it works
A new user signs in with Google, then walks through a preference panel that gathers a multi-dimensional read: release-year range, runtime range, IMDb rating range, age-rating filter, language, weighted genre preferences, and a handful of soft sliders — mood intensity, humor, violence, romance, complexity. Each axis is independent. Each can be left blank.
Those preferences become structured input to the recommendation endpoint, which queries the movie database and falls back to the random-discovery endpoint when the filtered set is too small. The result is a stack of cards. The user swipes — right for a like, left for a dislike, click or touch both work — and the underlying ledger maintains two distinct tracks: a session-only like list for the “Review this session” summary, and a persistent like list tied to the user account.
Behind the swipe interface is a Gemini-driven recommendation layer that consumes the preference vector and the persistent like history together. The output is a curated list, not a generic popularity ranking.
Architectural decisions
The two non-obvious choices in this project were the deployment topology and the dual-state model for likes.
Decoupled frontend and backend on AWS. The React app lives on AWS Amplify; the Express API lives on AWS App Runner. They scale independently and deploy independently, and the build pipelines (amplify.yml for the frontend, apprunner.yaml for the backend) are short and readable. This is more architecture than a “class project” demands, but it’s the right architecture for anything that might grow.
Session likes versus persistent likes. A session like is what the user clicks during a single browse — it powers the “here’s what you liked just now” summary view. A persistent like is what’s written to the backend and tied to the account — it powers the profile page and the recommendation feedback loop. Keeping the two separate (and the persistent writes fire-and-forget so a slow API never blocks a swipe) made the swipe interface feel instant and made the like-history feature meaningful.
Stack
React 18 with TypeScript built on Vite. Express on Node.js 20 for the API. Google OAuth 2.0 with HTTP-only session cookies. CORS configured per-environment. Gemini API for recommendations. AWS Amplify for the frontend build and hosting. AWS App Runner for the containerised backend. Environment variables segregated by build so a development frontend points at a local backend and a production frontend at the App Runner URL.
What I’d do differently
I’d add real refresh-token handling — the current session model is short-lived JWT in a cookie. I’d paginate the search results — every result loads at once today. And I’d swap the local component state for a proper store once the swipe interface grows past a single screen. None of these block the experience, but they’re the boundaries the project bumped against.
Why this lives on the Dynamic Reasoning site
SceneIt is the smallest, cleanest example of the LLM-in-product work I do — a real recommendation feature, a real preference model, a real OAuth flow, deployed on real cloud infrastructure. If you’re thinking about adding an AI-driven feature to an existing product, this is roughly the shape of the engagement that gets you there.
Next
Working on something with this shape?
Book a call