Project Overview & Stack Setup

Personal Catalogue: React, Express & MongoDB

Chapter 1 · Project Overview & Stack Setup

This is one of four courses building the exact same personal cataloguing tool in four genuinely different architectures — Personal Catalogue (PHP & MySQL) and Personal Catalogue (Django & PostgreSQL) are already complete; Personal Catalogue (React & Firebase) remains outlined. This course's own answer deliberately leans into schema flexibility: a MERN-style stack (MongoDB, Express, React, Node) built around the real fact that books, CDs, DVDs, and Blu-rays are genuinely differently-shaped records.

What the App Actually Does

The shared spec every course in the quartet builds toward:

  • Catalogue four kinds of item — books, CDs, DVDs, and Blu-rays — so it's possible to quickly check "do I already own this CD?" or "what Python books do I have?"
  • Tag books with free-form labels (a FastAPI book might get Python, Web Development, Programming, Web Frameworks) so related books can be found by topic later.
  • Add items manually for the first release — title, author/artist, format-specific details, tags where relevant.
  • Search and browse the collection to answer the "do I have this?" question quickly.

Barcode scanning is explicitly out of scope for this first release — a real, obvious way to add items even faster, but deliberately deferred rather than allowed to hold up a release that needs to ship quickly. This course closes with a real, concrete plan for adding it later (Chapter 8), rather than pretending it isn't wanted at all.

Why React, Express & MongoDB for This One

A real relational schema, like the PHP and Django siblings both use, has to decide up front exactly which columns a "catalogue item" table has — even though a book's own real fields (author, ISBN, publisher) and a DVD's real fields (director, runtime, format) genuinely don't overlap much beyond title and year. MongoDB's own document model sidesteps that tension directly: a single, heterogeneous items collection can hold a book document and a DVD document side by side, each with only the fields that item type actually needs, with no wasted null columns and no early commitment to one rigid, shared shape.

A Real Mechanism, Not Just "MongoDB Is Flexible"
Chapter 2 builds this properly using Mongoose discriminators — a real, documented pattern for storing several genuinely different document subtypes in one underlying MongoDB collection, each validated against its own schema, distinguished by a stored discriminator field (this project uses itemType). It isn't "just store whatever JSON shows up" — MongoDB's own flexibility still gets real, per-type schema validation on the way in.
CourseStackData model
Personal Catalogue: PHP & MySQLClassic LAMPNormalized relational tables, real foreign keys
Personal Catalogue: Django & PostgreSQLPython/Django ORMNormalized relational tables via the ORM
Personal Catalogue: React, Express & MongoDBMERN-styleOne heterogeneous document collection, discriminated by item type
Personal Catalogue: React & FirebaseReact + managed BaaSFirestore documents (self-managed MongoDB vs. managed Firestore, compared directly once both exist)

A Real Deadline, Not Just a Framing Device

This project genuinely needs a working first release quickly, exactly as its own two completed siblings describe. That constraint shapes real decisions throughout this course too — a single Express API rather than a separately versioned backend service, Mongoose's own schema validation used in place of hand-rolled checks, and a deliberately plain add-item form before any real polish. Chapter 7 covers where the corners were deliberately cut given that time pressure.

Setting Up: Node, Express & a Working MongoDB Connection

This course assumes Node.js and a MongoDB instance are already available — either a local install (mongod running on the default port) or a free-tier MongoDB Atlas cluster. Confirm both are reachable before continuing.

Scaffold the backend first, since it's what every later chapter builds directly on:

# Backend mkdir catalogue-api && cd catalogue-api npm init -y npm install express mongoose cors dotenv npm install --save-dev nodemon

A single .env file holds the real connection string, kept out of version control:

# .env MONGODB_URI=mongodb://localhost:27017/catalogue PORT=4000

A minimal entry point confirms the connection before any real route exists:

// server.js require('dotenv').config(); const express = require('express'); const mongoose = require('mongoose'); const cors = require('cors'); const app = express(); app.use(cors()); app.use(express.json()); mongoose.connect(process.env.MONGODB_URI) .then(() => console.log('MongoDB connected')) .catch((err) => console.error('MongoDB connection error:', err)); const PORT = process.env.PORT || 4000; app.listen(PORT, () => console.log(`Server running on port ${PORT}`));

Running npx nodemon server.js should log both a successful MongoDB connection and the listening port — confirmation the real backend half of this stack is working before a single schema exists.

Scaffolding the React Frontend

A separate React project, built with Vite for a fast, minimal dev setup, will consume this API over HTTP — exactly the same "two real, independently running processes" pattern this site's own react-food-tracker-1 course already established:

# Frontend, run from a sibling folder to catalogue-api npm create vite@latest catalogue-web -- --template react cd catalogue-web npm install
Two Real Processes, Not One
Unlike the PHP sibling's own single-runtime setup, this variant genuinely runs two separate servers during development — the Express API on port 4000, the Vite dev server on its own default port — talking to each other over real HTTP requests. That separation is exactly why Chapter 3's own CRUD routes, not a template engine, are where this course's real data actually lives.
Don't Commit the Connection String
A real MongoDB Atlas URI embeds a username and password directly in the connection string. Keeping it in .env and adding .env to .gitignore from the very first commit avoids a genuinely common, genuinely real mistake — a credential accidentally pushed to a public repository.

Where This Course Is Headed

A real Mongoose schema for items, discriminated by item type (Chapter 2); the Express CRUD routes every later feature calls (Chapter 3); one React form handling several genuinely different item shapes (Chapter 4); tags — attaching, managing, and filtering by tag on books (Chapter 5); real search across a heterogeneous collection (Chapter 6); the list and detail views in React (Chapter 7); fast manual entry given the project's own real deadline (Chapter 8); deployment (Chapter 9); and a capstone on integrating this catalogue into the existing Astro-based site, plus a real, concrete plan for barcode scanning (Chapter 10).

Hands-On Exercises

Exercise 1

Explain why a genuinely heterogeneous MongoDB collection is a better fit for this project's own item data than a single, rigid relational table — and name the real risk a document database doesn't automatically protect against that a relational one does.

📄 View solution
Exercise 2

Set up the Express backend and confirm a real MongoDB connection via the console log, then explain in one sentence what Mongoose discriminators are for and why they matter for this project specifically.

📄 View solution
Exercise 3

Scaffold the Vite-based React frontend and explain why this variant runs two separate development servers, where the PHP sibling course needed only one.

📄 View solution

Chapter 1 Quick Reference

  • The shared app — a personal catalogue for books/CDs/DVDs/Blu-rays, tags on books, manual entry first, barcode scanning deferred
  • Why this variant — MongoDB's own document flexibility fits genuinely differently-shaped item records directly, without forcing one rigid shared table
  • Database — MongoDB, with Mongoose providing real per-type schema validation via discriminators (built in Chapter 2)
  • Backend — Express + Mongoose, connected via a .env-stored connection string
  • Frontend — a separate Vite-based React app, consuming the API over real HTTP requests
  • Next chapter: Data Modeling in MongoDB — a real heterogeneous items collection, discriminated by item type