React Router
Client-side routing for Single Page Applications
Routes
Link
NavLink
useParams
1. Introduction: What is React Router?
React Router is the standard routing library for React applications. It enables client-side routing, allowing you to navigate between different components without refreshing the page.
Analogy: React Router acts like a traffic controller for your app. When a user clicks a link or types a URL, it directs them to the correct "page" (component) while keeping the app running smoothly as a Single Page Application (SPA).
JSX // Without React Router: Multi-page app (full page reload)
<a href="/about">About</a>
// With React Router: Single Page App (no reload!)
<Link to="/about">About</Link>
Declarative routing (routes as components)
Nested routes for complex layouts
Dynamic routing with URL parameters
Programmatic navigation with hooks
Lazy loading for code splitting
2. Why React Router? (Single Page Application Navigation)
In a traditional multi-page website, clicking a link makes the browser request a new HTML file from the server — causing a full page reload that is slow and loses application state.
React Router's solution: Intercept link clicks, update the URL, and render the appropriate component without refreshing the page.
The app loads once (a single HTML page)
React Router listens to URL changes
When URL changes, it matches the path to defined routes
It renders the corresponding component
The page never reloads
3. Installation and Setup
3.1 Installing React Router DOM
Bash npm install react-router-dom
# or: yarn add react-router-dom
# or: pnpm add react-router-dom
3.2 Basic Setup with BrowserRouter
JSX import { BrowserRouter } from 'react-router-dom';
import App from './App';
createRoot(document.getElementById('root')).render(
<BrowserRouter>
<App />
</BrowserRouter>
);
React Router needs to know the current URL and provide routing context to all components.
3.3 Modern Setup with RouterProvider (Data Router API)
JSX // Object-based routes (React Router v6.4+)
import { createBrowserRouter, RouterProvider } from 'react-router-dom';
const router = createBrowserRouter([
{
path: '/',
element: <App />,
children: [
{ index: true, element: <Home /> },
{ path: 'about', element: <About /> },
{ path: 'contact', element: <Contact /> },
{ path: 'products/:id', element: <ProductDetail /> },
{ path: '*', element: <NotFound /> }
]
}
]);
createRoot(document.getElementById('root')).render(
<RouterProvider router={router} />
);
Aspect BrowserRouter + Routes RouterProvider (Data Router)
Syntax JSX <Routes><Route> createBrowserRouter object/JSX
Data Loading Manual useEffect Built-in loaders
Error Handling Manual Built-in error boundaries
Best For Simple apps, beginners Complex apps, production
4. Routes and Route Components
4.1 Routes Component (Replaces Switch)
JSX import { Routes, Route } from 'react-router-dom';
function App() {
return (
<Routes>
<Route path="/products/:id" element={<ProductDetail />} />
<Route path="/products" element={<Products />} />
<Route path="*" element={<NotFound />} />
</Routes>
);
}
Important: Routes renders the best matching route. Put more specific paths before catch-all routes.
4.2 Route Component – path and element
Prop Purpose Example
pathURL pattern to match /about, /users/:id
elementComponent to render <About />
4.3 Index Routes (Default Sub-routes)
JSX const router = createBrowserRouter([
{
path: '/dashboard',
element: <DashboardLayout />,
children: [
{ index: true, element: <DashboardOverview /> },
{ path: 'settings', element: <Settings /> }
]
}
]);
function DashboardLayout() {
return (
<div>
<Sidebar />
<Outlet /> {/* Renders index or child route */}
</div>
);
}
4.4 404 Not Found Route (Catch-all with *)
JSX <Route path="*" element={<NotFound />} />
function NotFound() {
return (
<div style={{ textAlign: 'center', padding: '50px' }}>
<h1>404 - Page Not Found</h1>
<p>The page you're looking for doesn't exist.</p>
<Link to="/">Go Back Home</Link>
</div>
);
}
5. Link Component for Navigation
5.1 Basic Link Usage
JSX import { Link } from 'react-router-dom';
function Navigation() {
return (
<nav>
<Link to="/">Home</Link>
<Link to="/about">About</Link>
<Link to="/contact">Contact</Link>
</nav>
);
}
5.2 Link vs Regular Anchor Tag
Aspect <a href="..."> <Link to="...">
Page Reload Full page reload No reload
State Preservation Lost Preserved
SPA Support No Yes
5.3 Relative vs Absolute Paths
JSX // Absolute paths (from root)
<Link to="/products">All Products</Link>
<Link to="/products/123">Product 123</Link>
// Relative paths (from current location)
<Link to="edit">Edit</Link> // /products/123 → /products/123/edit
<Link to="../">Go Back</Link> // Up one level
<Link to=".">Refresh</Link> // Stay on current route
6. NavLink Component for Active Links
6.1 Basic NavLink Usage
JSX import { NavLink } from 'react-router-dom';
function Navigation() {
return (
<nav>
<NavLink to="/">Home</NavLink>
<NavLink to="/about">About</NavLink>
<NavLink to="/contact">Contact</NavLink>
</nav>
);
}
6.2 Styling Active Links (className with isActive)
JSX / CSS <NavLink
to="/about"
className={({ isActive }) => `nav-link ${isActive ? 'active' : ''}`}
>
About
</NavLink>
/* CSS */
.nav-link { color: #333; padding: 8px 16px; }
.nav-link.active { color: #007bff; font-weight: bold; border-bottom: 2px solid #007bff; }
6.3 Styling Active Links (style with isActive)
JSX <NavLink
to="/about"
style={({ isActive }) => ({
color: isActive ? '#007bff' : '#333',
fontWeight: isActive ? 'bold' : 'normal',
borderBottom: isActive ? '2px solid #007bff' : 'none'
})}
>
About
</NavLink>
6.4 end Prop for Exact Matching
JSX // Without end: partial match on '/'
<NavLink to="/">Home</NavLink>
// With end: ONLY matches exact '/'
<NavLink end to="/">Home</NavLink>
<NavLink end to="/dashboard">Overview</NavLink>
<NavLink to="/dashboard/settings">Settings</NavLink>
7. Dynamic Routing with useParams
7.1 Defining Dynamic Routes (Route Parameters)
JSX <Route path="/products/:id" element={<ProductDetail />} />
<Route path="/users/:userId/posts/:postId" element={<PostDetail />} />
Route Pattern Matches Parameter Values
/products/:id/products/123{ id: "123" }
/users/:userId/posts/:postId/users/5/posts/42{ userId: "5", postId: "42" }
7.2 Accessing URL Parameters with useParams
JSX import { useParams } from 'react-router-dom';
function ProductDetail() {
const { id } = useParams();
const [product, setProduct] = useState(null);
const [loading, setLoading] = useState(true);
useEffect(() => {
fetch(`/api/products/${id}`)
.then(res => res.json())
.then(data => { setProduct(data); setLoading(false); });
}, [id]);
if (loading) return <div>Loading...</div>;
return (
<div>
<h1>{product.name}</h1>
<p>Price: ${product.price}</p>
</div>
);
}
7.3 Multiple Parameters and Optional Parameters
JSX function ProductDetail() {
const { categoryId, productId } = useParams();
return <div>Category: {categoryId}, Product: {productId}</div>;
}
// Optional parameters
<Route path="/search/:query?/:page?" element={<SearchResults />} />
function SearchResults() {
const { query, page } = useParams();
const currentPage = page || 1;
return <div>Searching for: {query || 'all'} (Page {currentPage})</div>;
}
// All URL params are strings — convert when needed
const productId = Number(id);
8. Complete Working Examples
8.1 Example 1: Complete Blog Application
JSX const router = createBrowserRouter([
{
path: '/',
element: <BlogLayout />,
children: [
{ index: true, element: <PostList /> },
{ path: 'posts/:slug', element: <PostDetail /> },
{ path: 'about', element: <About /> },
{ path: '*', element: <NotFound /> }
]
}
]);
function BlogLayout() {
return (
<div>
<nav>
<NavLink end to="/">Home</NavLink>
<NavLink to="/about">About</NavLink>
</nav>
<Outlet />
</div>
);
}
function PostDetail() {
const { slug } = useParams();
const post = usePost(slug);
if (!post) return <p>Post not found</p>;
return <article><h1>{post.title}</h1><p>{post.body}</p></article>;
}
8.2 Example 2: E-commerce Product Pages
JSX function AppRoutes() {
return (
<Routes>
<Route path="/" element={<Home />} />
<Route path="/products" element={<ProductList />} />
<Route path="/products/:productId" element={<ProductDetail />} />
<Route path="/cart" element={<Cart />} />
<Route path="*" element={<NotFound />} />
</Routes>
);
}
function ProductList() {
const products = useProducts();
return (
<ul>
{products.map(p => (
<li key={p.id}>
<Link to={`/products/${p.id}`}>{p.name}</Link>
</li>
))}
</ul>
);
}
8.3 Example 3: User Dashboard with Nested Routes
JSX const router = createBrowserRouter([
{
path: '/dashboard',
element: <DashboardLayout />,
children: [
{ index: true, element: <Overview /> },
{ path: 'orders', element: <Orders /> },
{ path: 'orders/:orderId', element: <OrderDetail /> },
{ path: 'settings', element: <Settings /> }
]
}
]);
function DashboardLayout() {
return (
<div className="dashboard">
<aside>
<NavLink end to="/dashboard">Overview</NavLink>
<NavLink to="/dashboard/orders">Orders</NavLink>
<NavLink to="/dashboard/settings">Settings</NavLink>
</aside>
<main><Outlet /></main>
</div>
);
}
9. Common Mistakes and Best Practices
Mistake Problem Solution
No BrowserRouter Hooks return undefined Wrap app with router
Using <a> instead of Link Full page reload Use Link or NavLink
No 404 route Blank page on bad URLs Add path="*"
Missing end on home NavLink Home stays active everywhere Use end prop
URL params as numbers Type mismatches Use Number() or parseInt()
JSX // DO
<Route path="*" element={<NotFound />} />
<NavLink end to="/">Home</NavLink>
const productId = Number(id);
// DON'T
<a href="/about">About</a> // full reload
return <h1>{product.name}</h1>; // crash if product undefined
10. Summary Cheat Sheet
JSX // INSTALLATION
npm install react-router-dom
// BASIC SETUP
<BrowserRouter><App /></BrowserRouter>
// or
<RouterProvider router={router} />
// ROUTES
<Routes>
<Route path="/" element={<Home />} />
<Route path="/about" element={<About />} />
<Route path="/products/:id" element={<ProductDetail />} />
<Route path="*" element={<NotFound />} />
</Routes>
// NESTED ROUTES
<Route path="/dashboard" element={<Layout />}>
<Route index element={<Overview />} />
<Route path="settings" element={<Settings />} />
</Route>
// Layout uses <Outlet />
// NAVIGATION
<Link to="/about">About</Link>
<NavLink end to="/" style={({ isActive }) => ({ fontWeight: isActive ? 'bold' : 'normal' })}>Home</NavLink>
// DYNAMIC PARAMS
const { id } = useParams();
const productId = Number(id);
// PROGRAMMATIC NAVIGATION
const navigate = useNavigate();
navigate('/products');
navigate(-1); // go back
navigate('edit'); // relative
// QUICK REFERENCE
// BrowserRouter → Wrap app for routing context
// Routes / Route → Define URL → component mapping
// Link → Navigate without reload
// NavLink → Link with active state
// useParams → Read URL parameters
// useNavigate → Programmatic navigation
// Outlet → Render nested child routes
// path="*" → 404 catch-all
Next Steps
API Calls – Fetch data for dynamic routes
Protected Routes – Auth guards with Context
Lazy Loading – React.lazy with routes
Redux Toolkit – Global state with routing
React Router MCQ Practice
10 Basic MCQs
10 Advanced MCQs
10 Basic React Router MCQs
1
React Router enables:
A Client-side routing in SPAs
B SQL migrations
C CSS preprocessing
D Node clustering
Explanation: Map URLs to components without full reload.
2
BrowserRouter uses:
A HTML5 history API
B Hash only always
C WebSockets
D Cookies only
Explanation: Clean URLs without # fragment.
3
Route element prop in v6 maps:
A path to element component
B only CSS
C npm scripts
D state only
Explanation: <Route path="/" element={<Home />} />.
4
Link component vs <a>:
A Link prevents full page reload
B No difference
C Link reloads page
D Link only external
Explanation: Client-side navigation updates URL and view.
5
useNavigate hook returns:
A Function to programmatically navigate
B Current CSS
C Redux store
D DOM ref
Explanation: navigate('/dashboard') after login.
6
URL parameters read with:
A useParams
B useState only
C useEffect only
D useRef only
Explanation: const { id } = useParams() for /users/:id.
7
Nested routes render via:
A Outlet in parent layout
B Multiple index.html
C iframe only
D alert
Explanation: Parent layout wraps child routes with Outlet.
8
Navigate component is used to:
A Redirect declaratively
B Fetch data
C Style pages
D Install packages
Explanation: <Navigate to="/login" replace />.
9
Routes must be inside:
A Router provider (BrowserRouter)
B body only raw
C package.json
D CSS file
Explanation: Router supplies routing context.
10
Active link styling uses:
A NavLink with className or style function
B only href
C onLoad
D useMemo only
Explanation: NavLink knows active state from current URL.
10 Advanced React Router MCQs
1
Loader pattern in React Router 6.4+ data APIs:
A Fetch before render on route
B Replaces useEffect always
C Server only
D CSS only
Explanation: Loaders centralize data fetching per route.
2
index route in nested config:
A Default child when parent path matches
B 404 page only
C External link
D API route
Explanation: <Route index element={<Dashboard />} />.
3
useSearchParams manages:
A Query string state
B Path params only
C Cookies only
D Redux
Explanation: ?tab=settings in URL.
4
Protected route pattern:
A Check auth; render Navigate to login if unauthorized
B Always public
C Disable Router
D Use only hash router
Explanation: Wrapper component guards children.
5
Lazy route splitting uses:
A React.lazy + Suspense with route element
B sync require in Router
C No components
D jQuery
Explanation: Code-split per page.
6
404 catch-all route path:
A path="*" element={<NotFound />}
B path="404only"
C no path needed
D path="/"
Explanation: Asterisk matches unmatched paths.
7
relative links in nested routes use:
A relative path or relative Route structure
B absolute only
C full page reload
D window.location only
Explanation: Nested relative navigation simplifies config.
8
History stack replace:true means:
A Replace current entry instead of push
B Delete all history
C Open new tab
D Disable back button forever
Explanation: Avoid duplicate history entries on redirect.
9
Router v6 relative useRoutes helps:
A Define route objects in JS data structure
B Remove components
C CSS modules
D npm
Explanation: Programmatic route config arrays.
10
SSR with Router needs:
A StaticRouter on server, BrowserRouter on client
B Only HashRouter
C No hydration
D CRA only
Explanation: Match server and client URL handling.
Check All Answers
15 React Router Interview Questions & Answers
Easy
Medium
Hard
1 What is React Router?easy
Answer: Library for declarative routing in React SPAs using URL to render components.
2 BrowserRouter vs HashRouter?medium
Answer: BrowserRouter uses clean URLs; HashRouter uses # for legacy servers without fallback.
3 How to navigate programmatically in v6?easy
Answer: useNavigate() hook from react-router-dom.
4 What is useParams?easy
Answer: Hook returning dynamic URL segment values like :id.
5 Purpose of Outlet?medium
Answer: Renders child route inside parent layout for nested routing.
6 How to protect routes?medium
Answer: Check authentication; conditionally render Navigate to login or child routes.
7 Difference Link vs anchor?easy
Answer: Link intercepts navigation for SPA; anchor causes full document reload.
8 What are search params?medium
Answer: Query string key-value pairs after ? in URL.
9 Code splitting with router?hard
Answer: Lazy-load route components wrapped in Suspense.
10 404 handling?medium
Answer: Define catch-all route with path * rendering NotFound page.
11 NavLink benefit?easy
Answer: Applies active styles when route matches current location.
12 React Router data APIs (6.4+)?hard
Answer: Loaders and actions co-locate data/mutations with routes.
13 Deploy SPA routing on static host?hard
Answer: Configure server fallback to index.html for unknown paths.
14 Nested layout pattern?medium
Answer: Parent route with layout component + Outlet for child pages.
15 useLocation provides?medium
Answer: Current location object (pathname, search, hash, state).