React Router est un outil essentiel pour créer la navigation dans les applications React, et ses dernières versions continuent d’améliorer l’expérience des développeurs avec de nouvelles fonctionnalités et des améliorations de performance. À partir de la version 7 (ou d’autres versions à venir), React Router apporte des fonctionnalités avancées telles que des routes imbriquées et des routes de mise en page qui contribuent à construire des applications web robustes et efficaces.
Principales nouvelles fonctionnalités de React Router 7 (ou dernière version)
Voici quelques-unes des améliorations et fonctionnalités significatives introduites dans la dernière version :
1. Définition simplifiée des routes avec les API de données
De nouvelles API de données, comme loader
et action
, permettent de récupérer et de modifier des données de manière plus déclarative au sein des routes.
Dans les anciennes versions, la récupération de données était généralement gérée à l’intérieur des composants React en utilisant useEffect
ou des méthodes de cycle de vie des composants de classe. Cela conduisait souvent à un mélange de la logique de récupération des données avec le rendu de l’interface utilisateur, ce qui pouvait devenir encombrant.
Exemple de React Router v5
import { useEffect, useState } from 'react';
import { useParams } from 'react-router-dom';
function UserPage() {
const { id } = useParams();
const [userData, setUserData] = useState(null);
useEffect(() => {
fetch(`/api/users/${id}`)
.then((response) => response.json())
.then((data) => setUserData(data));
}, [id]);
return (
<div>
<h1>User: {userData?.name}</h1>
</div>
);
}
Les dernières versions introduisent les API Loader
, permettant à la récupération des données de se faire directement au niveau des routes. Cela sépare les préoccupations, simplifie les composants et permet un meilleur rendu concurrent.
Exemple de React Router v7
import { useLoaderData } from 'react-router-dom';
export async function userLoader({ params }) {
const response = await fetch(`/api/users/${params.id}`);
return response.json();
}
function UserPage() {
const userData = useLoaderData();
return (
<div>
<h1>User: {userData.name}</h1>
</div>
);
}
// Route Configuration
<Route path="/users/:id" element={<UserPage />} loader={userLoader} />
Différence
Dans React Router 7, la logique de récupération des données (userLoader
) est découplée du composant, ce qui permet aux composants de se concentrer uniquement sur le rendu. Cette approche permet également de pré-récupérer les données avant le rendu du composant, améliorant ainsi l’expérience utilisateur et rendant les transitions plus fluides.
2. Limites d’Erreur par Route
Une des fonctionnalités utiles introduites dans React Router 7 (ou les versions les plus récentes) est la possibilité de définir des Limites d’Erreur par route. Cela permet aux développeurs de gérer les erreurs à un niveau plus granulaire. Au lieu d’avoir une seule limite d’erreur globale pour l’ensemble de l’application, vous pouvez définir des limites d’erreur spécifiques à des routes individuelles, rendant la gestion des erreurs plus flexible et localisée. La gestion granulaire des erreurs au niveau des routes est désormais possible.
Dans les anciennes versions, la gestion des erreurs était globale ou gérée au niveau du composant. Cela obligeait les développeurs à gérer toutes les erreurs possibles en un seul endroit ou à introduire une logique complexe dans divers composants. Comme mentionné dans l’exemple ci-dessous, la ErrorBoundary
est globale car elle enveloppe tout le Router
, ce qui signifie qu’elle attrapera les erreurs de toutes les routes au sein de l’application.
Exemple React Router v5
function App() {
return (
<ErrorBoundary>
<Router>
<Route path="/" exact component={HomePage} />
<Route path="/about" component={AboutPage} />
</Router>
</ErrorBoundary>
);
}
React Router 7 introduit des limites d’erreur au niveau des routes, rendant possible la gestion des erreurs pour des routes spécifiques. Cela permet un contrôle plus granulaire sur la façon dont les erreurs sont gérées et affichées.
Exemple React Router v7
import { useRouteError } from 'react-router-dom';
function ErrorBoundary() {
const error = useRouteError();
return <div>Error: {error.message}</div>;
}
<Route path="/users/:id" element={<UserPage />} errorElement={<ErrorBoundary />} />
Différence
La gestion des erreurs dans React Router 7 est plus modulaire et localisée. Chaque route peut définir sa propre logique de gestion des erreurs, améliorant l’expérience utilisateur lorsque différentes parties de l’application échouent.
3. Meilleure Gestion des Routes de Mise en Page
Les routes de mise en page sont introduites pour permettre une gestion cohérente de la mise en page à travers différentes parties de l’application, réduisant la duplication de code.
Dans React Router v5, les mises en page comme les en-têtes, les pieds de page ou les barres latérales devaient être duplicées manuellement dans chaque route ou composant. Cela signifiait que les développeurs plaçaient souvent les composants de mise en page (par exemple, Header
, Footer
) directement à l’intérieur du composant App
ou les répétaient à travers différents gestionnaires de routes, comme illustré dans votre exemple.
Exemple de React Router v5
import { BrowserRouter as Router, Route } from 'react-router-dom';
import Header from './Header';
import Footer from './Footer';
import HomePage from './HomePage';
import AboutPage from './AboutPage';
function App() {
return (
<Router>
<Header />
<Route path="/" exact component={HomePage} />
<Route path="/about" component={AboutPage} />
<Footer />
</Router>
);
}
React Router 7 introduit des routes de mise en page, où vous pouvez définir des mises en page partagées qui enveloppent les routes imbriquées, éliminant la duplication de code et assurant une meilleure structure.
Exemple de React Router v7
import { Outlet } from 'react-router-dom';
function SharedLayout() {
return (
<div>
<header>Header Content</header>
<main>
<Outlet /> {/* Nested routes will render here */}
</main>
<footer>Footer Content</footer>
</div>
);
}
// Route Configuration with Layout
<Route path="/" element={<SharedLayout />}>
<Route index element={<HomePage />} />
<Route path="about" element={<AboutPage />} />
</Route>
Différence
Les routes de mise en page permettent une manière propre et réutilisable d’appliquer des mises en page partagées à travers plusieurs routes, sans répéter le code. Outlet
sert de marqueur de position pour les routes enfants, rendant la gestion des mises en page beaucoup plus facile.
4. Capacités de Routage Imbriqué Améliorées
Il existe des moyens plus efficaces de gérer les routes imbriquées, incluant l’héritage des éléments de mise en page et de meilleures stratégies de récupération des données.
Dans les anciennes versions, les routes imbriquées étaient possibles, mais leur configuration était plus laborieuse. Vous deviez gérer explicitement l’imbrication des routes au sein du composant parent en utilisant useRouteMatch()
pour obtenir le chemin actuel, puis définir manuellement les routes imbriquées à l’intérieur du composant parent. Cette approche peut rapidement devenir encombrante, surtout pour des applications complexes avec plusieurs niveaux de routes imbriquées.
Exemple de React Router v5
import { Route, useRouteMatch } from 'react-router-dom';
function Dashboard() {
const { path } = useRouteMatch();
return (
<div>
<h1>Dashboard</h1>
<Route path={`${path}/overview`} component={Overview} />
<Route path={`${path}/settings`} component={Settings} />
</div>
);
}
<Route path="/dashboard" component={Dashboard} />
Dans React Router 7, les routes imbriquées sont désormais configurées de manière déclarative, directement dans la configuration des routes, simplifiant ainsi la structure de routage et rendant le code plus lisible.
Exemple de React Router v7
import { Outlet } from 'react-router-dom';
function DashboardLayout() {
return (
<div>
<h1>Dashboard</h1>
<Outlet /> {/* Nested routes will render here */}
</div>
);
}
// Route Configuration
<Route path="/dashboard" element={<DashboardLayout />}>
<Route path="overview" element={<Overview />} />
<Route path="settings" element={<Settings />} />
</Route>
Différence
Dans React Router 7, les routes imbriquées sont plus simples à gérer car elles sont définies au niveau de la configuration des routes en utilisant le composant Outlet
. Cette structure favorise une séparation claire entre la mise en page et le contenu.
5. Intégration améliorée de Suspense
Vous trouverez désormais un meilleur support pour React 18’s Suspense
et le rendu concurrent pour des expériences de chargement plus fluides.
Dans les anciennes versions, le suspense n’était pris en charge que pour les composants chargés de manière paresseuse dans les anciennes versions, limitant son utilité pour des scénarios complexes de récupération de données.
Exemple de React Router v5
import React, { Suspense, lazy } from 'react';
const HomePage = lazy(() => import('./HomePage'));
<Suspense fallback={<div>Loading</div>}>
<Route path="/" component={HomePage} />
</Suspense>
React Router 7 intègre Suspense
avec ses APIs Loader et Action, permettant un chargement de données plus fluide et concurrent avec un effort minimal.
Exemple de React Router v7
import { Suspense } from 'react';
import { Route, Routes } from 'react-router-dom';
function App() {
return (
<Suspense fallback={<div>Loading</div>}>
<Routes>
<Route path="/" element={<HomePage />} />
<Route path="/about" element={<AboutPage />} />
</Routes>
</Suspense>
);
}
Différence
React Router 7 utilise Suspense
à la fois pour les composants chargés de manière paresseuse et pour le chargement de données, permettant des transitions plus fluides et une interface utilisateur plus réactive.
Conclusion
React Router 7 (ou la dernière version) améliore considérablement le routage dans les applications React en introduisant plusieurs fonctionnalités puissantes. Les nouvelles APIs Loader et Action permettent un chargement de données déclaratif, séparant la logique des données des composants pour un code plus propre. Les Routes de mise en page simplifient la gestion des mises en page partagées, réduisant la redondance. Les Routes imbriquées sont plus efficaces et intuitives, permettant une structure plus claire. De plus, les limites d’erreur par route offrent une gestion précise des erreurs, améliorant la fiabilité. L’intégration complète avec React Suspense
prend en charge un chargement de données plus fluide et des expériences utilisateur améliorées. Ensemble, ces avancées simplifient le développement d’applications React complexes, évolutives et performantes, faisant de React Router 7 une mise à niveau substantielle par rapport aux versions précédentes.
Source:
https://dzone.com/articles/why-react-router-7-is-a-game-changer-for-react-devs