Web Frameworks & Stacks lessons
Why frameworks exist
React, Next.js and Express shown as stacked building blocks.
A framework is a pre-built structure of code that handles common tasks so you do not have to write everything from scratch. Vanilla JavaScript can build anything, but managing DOM updates, routing, and state by hand becomes painful as apps grow.
Frameworks like React, Vue, and Angular give you patterns for organising code into reusable pieces. They also handle performance optimisations that would take months to build yourself.
Vanilla JS vs framework approach
In vanilla JS you manually find elements with document.getElementById and update their content. Every change requires you to locate the element, modify it, and hope nothing else breaks.
// Vanilla JS — manual DOM update
const btn = document.getElementById("counter");
let count = 0;
btn.addEventListener("click", () => {
count++;
btn.textContent = `Clicked ${count} times`;
});A framework lets you declare what the UI should look like for a given state, and it updates the DOM for you automatically.
How a framework fits in
Your code, the framework, and the browser DOM in a left-to-right flow.
Your code describes the desired UI. The framework compares old and new states, then applies only the necessary DOM changes. This pattern is called declarative rendering.
Practice: Match the concepts
Match framework concepts to their descriptions.
Single-page apps vs multi-page
A multi-page app (MPA) loads a new HTML page from the server every time you navigate. A single-page app (SPA) loads once, then swaps content dynamically using JavaScript.
SPAs feel faster because only data travels over the network, not entire pages. The tradeoff is a larger initial JavaScript bundle and more complexity around SEO.
Request flow comparison
Animated side-by-side of the MPA and SPA request flows.
Most modern frameworks default to the SPA model. Next.js and similar meta-frameworks bring back server rendering while keeping the SPA navigation feel.
Practice: SPA or MPA?
Classify statements as SPA or MPA, one at a time.
React: components and JSX
React builds UIs from components, which are JavaScript functions that return JSX. JSX looks like HTML but lives inside your JavaScript files.
function Greeting() {
return <h1>Hello, world!</h1>;
}Each component is a self-contained piece of UI. You compose them together like building blocks to create full pages.
Passing data with props
Props are inputs passed from a parent component to a child. They flow in one direction only: parent to child.
function Welcome({ name }) {
return <p>Welcome, {name}!</p>;
}
// Usage:
<Welcome name="Alice" />Curly braces {} inside JSX embed JavaScript expressions. This is how dynamic values get into your markup.
Practice: Complete the component
Fill the blanks to complete a React component.
State and reactivity
State is data that can change over time. When state changes, React re-renders the component to reflect the new values.
import { useState } from "react";
function Counter() {
const [count, setCount] = useState(0);
return (
<button onClick={() => setCount(count + 1)}>
Clicked {count} times
</button>
);
}The useState hook returns the current value and a setter function. Calling the setter triggers a re-render with the updated value.
State vs props
Parent state passed down as props to a child, with the setState re-render loop.
State is owned and managed by the component that creates it. Props are read-only values received from a parent. A child cannot modify its own props.
Practice: State or props?
Label each characteristic as State or Props.
Next.js and server-side rendering
Next.js is a meta-framework built on top of React. It adds routing, server-side rendering (SSR), and static generation out of the box.
With SSR, the server runs your React components and sends finished HTML to the browser. The page is visible immediately, then React "hydrates" it to make it interactive.
// app/page.tsx — a Next.js server component
export default function HomePage() {
return <h1>This HTML is generated on the server</h1>;
}Rendering strategies
Interactive CSR / SSR / SSG comparison table.
Next.js lets you mix strategies per page. A marketing homepage can be statically generated while a user dashboard uses server-side rendering.
Practice: Pick the rendering strategy
Pick CSR, SSR or SSG for each scenario.
Express: backend basics
Express is a minimal Node.js framework for building servers and APIs. It handles incoming HTTP requests and sends responses.
const express = require("express");
const app = express();
app.get("/api/hello", (req, res) => {
res.json({ message: "Hello from the server!" });
});
app.listen(3001);The app.get method registers a route. When a browser visits /api/hello, Express runs the callback and returns JSON.
The full stack
A full-stack application has three layers: a frontend (React/Next.js), a backend (Express/Node), and a database (MySQL, PostgreSQL, MongoDB).
The three-layer full stack: frontend, backend and database.
The frontend sends HTTP requests to the backend. The backend processes the request, queries the database if needed, and sends data back as JSON.
Practice: Order the request flow
Order the six steps of a full-stack request.
Client-side vs server-side routing
Server-side routing means every URL change sends a request to the server, which returns a new page. Client-side routing intercepts navigation in JavaScript and swaps components without a full page reload.
// Next.js file-based routing
// app/about/page.tsx → accessible at /about
// app/blog/[slug]/page.tsx → accessible at /blog/any-slug
export default function AboutPage() {
return <h1>About us</h1>;
}Next.js uses file-based routing. Creating a file at app/contact/page.tsx automatically creates the /contact route.
File-based routing in action
Interactive Next.js file tree — click a file to see its URL.
Square brackets like [slug] create dynamic routes. The value in the URL becomes available as a parameter inside the component.
Practice: Map files to routes
Match Next.js file paths to the URLs they create.
Package managers: npm and yarn
A package manager downloads and manages third-party libraries your project depends on. The two most common are npm and yarn.
# Install a package
npm install react
# Or with yarn
yarn add react
# Dependencies are saved in package.json
{
"dependencies": {
"react": "^18.2.0"
}
}The package.json file lists every dependency. Running npm install reads this file and downloads everything into the node_modules folder.
Creating a new project
Animated terminal walkthrough of create-next-app.
The npx create-next-app command scaffolds a complete project with routing, configuration, and dev server already set up.
Practice: Read the package.json
Read a package.json and answer three questions about it.
Build tools and bundlers
Browsers cannot run JSX, TypeScript, or import statements directly. A bundler like Webpack or Vite transforms your source code into plain JavaScript and CSS the browser understands.
The build step also minifies code, removes dead code (tree shaking), and splits your app into smaller chunks for faster loading.
The build pipeline
Animated build pipeline plus a framework bundle-size comparison chart.
Smaller bundle sizes mean faster page loads. Tools like Vite use native ES modules in development for near-instant hot reloading, then bundle for production.
Practice: Build tool concepts
Drag-and-drop matching. Left column: "Transpilation", "Minification", "Tree shaking", "Code splitting", "Hot module replacement". Right column (shuffled): "Converts JSX/TS to plain JavaScript", "Removes whitespace and shortens variable names", "Eliminates unused code from the bundle", "Loads only the JS needed for the current page", "Updates code in the browser without full reload". User drags right items to match left. Validate all five. Hint: "Each step reduces what the browser has to download or process."