Welcome to your first lesson in building a modern React frontend! In this course, you will learn how to create a user-friendly web application that connects to a NestJS API. Before you can build advanced features, it is important to set up a strong foundation. Two key parts of this foundation are the application layout and client-side routing.
A shared layout gives your app a consistent look and feel. It usually includes a header, navigation bar, main content area, and footer. Client-side routing lets users move between different pages of your app without reloading the whole page. This makes your app feel fast and smooth, just like the best modern websites.
In this unit, we transform a barebones React app into a multi-page experience with a persistent layout and client-side routing. The shared layout keeps the header, navigation, main content area, and footer consistent on every page. React Router lets us switch between views instantly without full page reloads, which makes the app feel fast and cohesive. We will wire the router at the entry point, define nested routes, implement a reusable layout with NavLink-based navigation, and stub pages for Home, Catalog, My Shelf, and a UI Demo page.
Since this is the first lesson of the course, you are starting with a basic React app. The app is already set up with the necessary folders and files. You do not need to worry about installing libraries in the CodeSignal environment, but it is good to know that we are using React Router for navigation.
Here is a quick look at how the app is started in src/index.tsx:
This code sets up the React app and tells it to use the router we will define. The RouterProvider component from react-router-dom enables routing throughout the app.
- We import
RouterProviderand pass therouterobject so all navigation is handled on the client with the History API (no full reloads). - The non-null assertion
document.getElementById('root')!tells TypeScript that the container exists; if it doesn’t, the app throws early rather than failing silently. React.StrictModeruns additional development checks (like highlighting potential side effects) without affecting production behavior.
A shared layout is a component that wraps all your pages and provides a consistent structure. In this app, the layout includes a header with navigation links, a main content area, and a footer.
Here is the layout component in src/App.tsx:
Explanation:
-
The
Appcomponent is the main layout for your app. -
The
<header>contains a navigation bar with links to different pages. -
The
<main>area is where the content of each page will appear. -
The
<footer>displays a copyright. -
The
<Outlet />component is a special placeholder from React Router. It will display the content of the current page.
Client-side routing lets your app show different pages without reloading. In React, this is done with React Router. You define routes that map URLs to components.
Here is how the routes are set up in src/routes/router.tsx:
Explanation:
createBrowserRoutercreates a router for your app. It uses the browser’s History API to manage navigation cleanly.- The root path
/uses theApplayout component. - The
childrenarray defines the pages:- The home page (
/) showsHomePage.{ index: true }marks the default child for/(so/showsHomePagewithout needing an explicit ).
- The home page (
Navigation links let users move between pages. In React Router, you use the NavLink component. It can also show which link is active (the current page).
Here is how navigation links are set up in the layout:
Explanation:
- Each
NavLinkpoints to a different route. - The
linkStylesfunction changes the style based on whether the link is active. - The active link is highlighted, so users know which page they are on.
What you see in the browser:
- The current page’s link is styled differently (for example, with a blue background).
- Clicking a link changes the page content without reloading.
src/pages/HomePage.tsx
- A minimal page component with a semantic
<section>, heading, and supporting copy. - Exporting a default function keeps imports concise in the router (no named import braces).
- Tailwind classes apply consistent typography and spacing matching the layout’s visual language.
- This page serves as the index content for
/.
Why this matters: Even simple pages establish your project’s patterns: component structure, naming conventions, and styling approach. This makes later pages faster to build and easier to maintain, because you can copy and adapt a known template.
src/features/catalog/CatalogPage.tsx
- Stubbed route target for
/catalog, structured the same way as other pages. - Clear heading establishes the page’s purpose for users and assistive tech.
- Text content makes it obvious during testing that navigation is functioning.
Why this matters: Consistent page scaffolding lets you later drop in real data and UI (search, grid, pagination) without changing routing or layout code. Verifying the stub renders correctly ensures the path and router wiring are correct.
src/features/shelf/MyShelfPage.tsx
In this lesson, you learned how to set up a shared layout and client-side routing in a React app. You saw how the layout keeps your app consistent and how routing lets users move between pages smoothly. You also learned how navigation links work and how to highlight the current page.
You mounted React Router at the app’s root, implemented a persistent layout with a header and footer, created accessible navigation with NavLink, and defined nested routes that render inside <Outlet />. You verified active states, direct URL handling, and observed how missing or mistyped routes affect rendering. With this foundation, your app behaves like a modern, multi-page SPA while keeping global UI stable.
Next, you will get to practice these concepts by working with the layout and routes yourself. This hands-on experience will help you become comfortable with building modern, user-friendly web apps.
