Inspiration

I recently had the urge to watch all the Star Wars movies and shows. After not following the series for nearly a decade, I wanted a way to track what shows/movies I wanted to watch in a nice easy visual.

What it does

WatchList is a media planning app for organizing what you want to read, watch, and play next. It supports books, shows, movies, and games in one shared experience, with dedicated pages for each media type.

Users can browse media cards, search within the current tab, run a global search, and manually add new items to their list. Each media type has fields that match its format, like authors and page counts for books, seasons and episodes for shows, runtime and ratings for movies, and platforms and playtime for games.

How we built it

We built WatchList with Next.js, React, TypeScript, and Tailwind CSS. The app uses the Next.js App Router for separate pages like Home, Books, Shows, Movies, Games, Search, and Add. The media cards are reusable client-side components so they can update smoothly while users search. The media pages use shared card-grid and filtering logic, while the search page can search across all media types.

For persistence, we added a local SQLite database using better-sqlite3. The database stores media items, list entries, provider metadata, cached API responses, and image references. We seeded it with placeholder media data so the app works as a complete demo before real API integrations are added.

Challenges we ran into

One challenge was deciding how much data should live locally versus coming directly from external APIs. We looked at Jellyfin’s metadata model and decided that WatchList should own its local saved list, while external providers enrich that list with metadata.

We also ran into runtime differences with SQLite. At first, we tried Node’s built-in node:sqlite, but it depends on newer Node versions. We switched to better-sqlite3 so the app would be more practical for local development.

Another challenge was balancing server-side and client-side behavior. SQLite needs to run on the server, but search filtering should feel instant in the browser. We handled that by loading media from the database on server-rendered routes, then filtering the card list client-side.

Accomplishments that we're proud of

We built WatchList into a working media planning app that can organize books, shows, movies, and games in one place. The app now has dedicated pages for each media type, reusable card layouts, live client-side filtering, global search navigation, and an add-to-list flow for manually saving new items.

We also moved beyond static placeholder data by adding a local SQLite-backed storage layer using better-sqlite3. That gives the project a real foundation for persistence while still keeping it lightweight enough for a demo. The database schema is designed around media items, list entries, provider metadata, cached API responses, and images, which sets us up well for future metadata integrations.

What we learned

We learned how important it is to separate the app’s own saved list data from external metadata provider data. Looking at tools like Jellyfin helped us understand that APIs should enrich the local library, not replace it as the source of truth. We also learned more about building with the Next.js App Router, especially the difference between static routes, dynamic server routes, and client components. Since WatchList uses local database access, the media pages need to run on the Node.js server runtime, while the card filtering and search interactions work best on the client.

What's next for WatchList

Next, we want to connect real metadata providers. For movies and shows, we plan to support TMDb and OMDb. For books, we want to use Open Library and Google Books. For games, IGDB is the strongest fit because it has structured game metadata, platforms, covers, screenshots, genres, companies, release dates, and videos.

We also want to improve the add-to-list flow so users can search external providers, preview results, select the right item, and save it into their local WatchList. After that, we would like to add editable list statuses, richer detail pages, cached cover art, and user-friendly list views like “Watching,” “Backlog,” “Finished,” and “Next Up.”

Built With

Share this project:

Updates

Submission history