- Fonctionnalités
- Pricing

React a complètement transformé la façon dont nous créons les interfaces utilisateur en introduisant une conception basée sur les composants qui favorise l'efficacité et la réutilisabilité. Sa méthode déclarative et sa structure basée sur les composants ont gagné en popularité auprès des développeurs. Mais à mesure que tes projets gagnent en complexité, tu pourrais rencontrer des problèmes de performances liés aux méthodes de rendu et de récupération des données.
Dans les méthodes traditionnelles de rendu côté client, tu dépends du navigateur pour exécuter du JavaScript afin d’afficher l’interface utilisateur initiale. Cela peut entraîner des retards de chargement sur les appareils aux ressources limitées. La récupération de données à partir d’une interface de programmation d’application (API) ajoute une charge supplémentaire à ces appareils, ce qui peut causer un décalage dans l’affichage du contenu et offrir des interactions utilisateur loin d’être idéales.
Les composants serveur offrent une solution à ces obstacles en permettant le rendu des composants sur le serveur. Cela permet au serveur de diffuser les composants vers le côté client, ce qui améliore les performances et les processus de récupération des données, puisque tout le traitement s'effectue sur le serveur et non sur les appareils des utilisateurs.
Dans cet article, tu découvriras comment les méthodes de rendu de React ont évolué au fil du temps, ainsi que les inconvénients liés à l'utilisation de React Suspense et du rendu côté serveur (SSR). De plus, tu en apprendras davantage sur les composants serveur React (RSC) et sur la manière dont ils résolvent ces problèmes.
Avant d'aborder les RSC, il est utile de comprendre les stratégies de rendu antérieures, telles que React Suspense et le SSR.
React Suspense a été introduit pour gérer le rendu asynchrone dans les applications React. Il permet aux composants de « suspendre » le rendu jusqu’à ce que certaines conditions soient remplies, comme la récupération de données ou le fractionnement de code. Voici quelques-uns des avantages de Suspense :
React.lazy pour permettre le fractionnement de code et améliorer les performances en ne chargeant les composants que lorsqu'ils sont nécessaires.Mais React Suspense présente certaines limites dont il faut tenir compte lorsque tu fais évoluer ton application :
Suspense` et des `ErrorBoundary`, ce qui ajoute du code répétitif et rend plus difficile le maintien de la cohérence et de la maintenabilité à mesure que ton application se développe.En ce qui concerne le SSR, les composants React sont rendus sur le serveur, puis le code HTML entièrement généré est envoyé au client pour être affiché. En revanche, avec le RSC, les composants individuels sont rendus dès qu’ils sont prêts, au lieu d’attendre que l’application entière se charge, comme c’est le cas avec le SSR. Cette approche présente plusieurs avantages :
Le SSR présente également des limites à prendre en compte :
Les RSC sont un nouveau type de composants dans React qui fonctionnent côté serveur, contrairement aux composants traditionnels, qui fonctionnent côté client. Ils aident à résoudre les problèmes liés à Suspense et au SSR classique en permettant aux composants d’être traités et diffusés sous forme de HTML du serveur vers le client. Les RSC gèrent également la récupération des données sur le serveur, garantissant ainsi que les informations confidentielles, telles que les clés API, ne soient pas divulguées au client.
Les RSC offrent des avantages significatifs :
Par rapport aux composants côté client, les RSC gèrent l'exécution, la gestion des données et les performances de manière différente.
Les composants traditionnels s’exécutent dans le navigateur (côté client), où JavaScript est nécessaire pour afficher l’interface utilisateur (UI). Les RSC s’exécutent sur le serveur en envoyant du HTML pré-rendu à l’appareil client au lieu de tout traiter localement. Cette approche réduit la charge de travail sur l’appareil de l’utilisateur et améliore la vitesse de chargement. La gestion des mises en page et du contenu statique côté serveur est également idéale pour les composants non interactifs ou basés sur des données. Les composants client peuvent être imbriqués dans des RSC là où l'interactivité est nécessaire, comme pour les boutons ou les formulaires, tout en conservant les données sensibles en sécurité sur le serveur.
Les composants traditionnels peuvent augmenter la taille du bundle JavaScript côté client, ce qui peut ralentir les performances de l'application. Les RSC n'augmentent pas la taille du package client puisqu'ils fonctionnent côté serveur, ce qui réduit les téléchargements et accélère le chargement des pages. Tu peux aussi utiliser les RSC pour améliorer la mise en cache. Le contenu rendu par le serveur est plus facile à mettre en cache, ce qui accélère les réponses pour les données fréquemment consultées, comme les produits populaires d'une boutique en ligne, sans avoir à interroger la base de données à plusieurs reprises.
Pour implémenter les RSC dans ton projet, suis ces étapes pour configurer ton environnement et commencer à utiliser efficacement les composants côté serveur et côté client.
Tout d'abord, assure-toi que la dernière version de Node.js est installée sur ta machine. La première étape consiste à créer un nouveau projet React depuis ton shell ou ton terminal :
npx create-react-app your-app --template cra-template-pwa
cd your-appUne fois ton projet initialisé, installe les dépendances requises pour les RSC :
npm install react@18 react-dom@18 babel-loader@8 @babel/preset-react webpack@5 webpack-cli
Pour plus d'informations, tu peux consulter la documentation officielle relative à chacune de ces bibliothèques : React, react-dom, webpack, Babel et webpack-cli.
Exécute la commande suivante pour installer les chargeurs pour les fichiers CSS et les fichiers de ressources tels que les SVG, ce qui permettra à ton application de traiter et d'inclure des feuilles de style et des fichiers multimédias :
npm install css-loader style-loader file-loader --save-devConfigure Babel en créant un fichier .babelrc fichier à la racine de ton projet avec le contenu suivant :
{
"presets": ["@babel/preset-react"]
}Crée un nouveau fichier nommé webpack.config.js dans le répertoire racine de ton projet et ajoute la configuration suivante pour configurer webpack :
const path = require("path");
module.exports = [
// Server-side configuration
{
entry: "./src/server.js", // Server entry point
target: "node",
output: {
path: path.resolve(__dirname, "dist"),
filename: "server.js",
},
module: {
rules: [
{
test: /\.jsx?$/,
use: "babel-loader",
exclude: /node_modules/,
},
{
test: /\.css$/, // Rule for CSS files
use: ["style-loader", "css-loader"],
},
{
test: /\.(png|jpe?g|gif|svg)$/, // Rule for image files
use: ["file-loader"],
},
],
},
resolve: {
extensions: [".js", ".jsx"],
},
},
// Client-side configuration
{
entry: "./src/index.js", // Client entry point
target: "web", // This tells Webpack to bundle for the browser
output: {
path: path.resolve(__dirname, "dist"),
filename: "client.js", // Client-side bundle
},
module: {
rules: [
{
test: /\.jsx?$/,
use: "babel-loader",
exclude: /node_modules/,
},
{
test: /\.css$/, // Rule for CSS files
use: ["style-loader", "css-loader"],
},
{
test: /\.(png|jpe?g|gif|svg)$/, // Rule for image files
use: ["file-loader"],
},
],
},
resolve: {
extensions: [".js", ".jsx"],
},
},
];Une fois webpack configuré, tu peux maintenant créer un fichier nommé server.js à l'intérieur du dossier src avec le code suivant pour configurer le point d'entrée de ton serveur :
import React from "react";
const express = require("express");
const ReactDOMServer = require("react-dom/server");
const App = require("./App").default;
const app = express();
// Serve the static files from the 'dist' folder (where Webpack will put client.js)
app.use(express.static("dist"));
app.get("*", (req, res) => {
const appHtml = ReactDOMServer.renderToString(<App />);
res.send(`
<!DOCTYPE html>
<html lang="en">
<head><title>React Server Components</title></head>
<body>
<div id="root">${appHtml}</div>
<!-- Include the client-side bundle -->
<script src="/client.js"></script>
</body>
</html>
`);
});
app.listen(3000, () => console.log("Server running on port 3000"));Dans le dossier src, crée un nouveau fichier appelé UserList.server.js pour configurer un composant serveur de base qui récupère des données :
import React from "react";
function UserList() {
// Dummy array of users
const users = [
{ id: 1, name: "John Doe" },
{ id: 2, name: "Jane Smith" },
{ id: 3, name: "Alice Johnson" },
];
return (
<ul>
{users.map((user) => (
<li key={user.id}>{user.name}</li>
))}
</ul>
);
}
export default UserList;Ce composant affiche les données utilisateur et renvoie une liste HTML. Pour ajouter de l'interactivité côté client, crée un fichier nommé Counter.client.js dans le répertoire src pour ton composant client :
import React, { useState } from "react";
function Counter({ initialCount }) {
const [count, setCount] = useState(initialCount);
return (
<div>
<button
onClick={() => {
setCount((prevCount) => {
const newCount = prevCount + 1;
return newCount;
});
}}
>
Increment 1
</button>
<p>Count: {count}</p>
</div>
);
}
export default Counter;De cette façon, le serveur initialise l'état et le client gère l'interactivité. Tu as maintenant configuré un processus complet pour les RSC, créé un composant serveur, transmis des données à un composant client et activé l'interactivité côté client.
Ensuite, mets à jour src/App.js pour y inclure le code suivant, qui intègre à la fois les composants serveur et client :
import React from "react";
import UserList from "./UserList.server";
import Counter from "./Counter.client";
function App() {
return (
<div>
<h1>Users</h1>
<UserList />
<Counter initialCount={50} />
</div>
);
}
export default App;Désormais, lorsque le serveur rend le composant App, il rendra également l'Dashboard UserList en tant que composant serveur et enverra le code HTML au client.
Pour exécuter ton serveur, compile le code et lance-le :
npx webpack
node dist/server.jsL'exécution de ces commandes renverra Server running on port 3000. À ce stade, ton application affiche des composants React à la fois sur le client et sur le serveur !
Comme les RSC gèrent la majeure partie du rendu côté serveur, transférer autant que possible le rendu de ton application vers le serveur peut améliorer considérablement les performances tout en conservant les fonctionnalités interactives là où c’est nécessaire. Voici quelques bonnes pratiques qui peuvent t’aider à y parvenir et à améliorer la vitesse, la flexibilité et la facilité de gestion de ton application grâce aux RSC.
Tout d'abord, utilise les RSC pour récupérer des données depuis des API ou des bases de données. Si tu as déjà récupéré des données sur le serveur, ne les récupère pas à nouveau côté client. Par exemple, si tu charges des données utilisateur sur le serveur et que tu les transmets au client, il n'est pas nécessaire d'effectuer un deuxième appel API côté client, sauf si les données changent.
Décomposer le code en petits morceaux et charger de manière sélective les scripts nécessaires à l’aide d’outils tels que Vite ou webpack peut aider à améliorer les temps de chargement. Crée des composants réutilisables dans toute ton application. Par exemple, si plusieurs pages doivent afficher une liste d’utilisateurs, crée un composant « UserList » qui fonctionne partout.
Enfin, veille à ce que les composants serveur restent légers en les concentrant uniquement sur le rendu des données, car ils n’ont pas besoin de gérer l’état comme le font les composants client. Concentre-toi sur leur légèreté et sur leur rôle exclusif de rendu des données. N’hydrate que les parties d’une page qui doivent être interactives. Par exemple, si la page est principalement statique mais comporte un formulaire ou un bouton interactif, n’hydrate que ces composants.
Bien que les RSC présentent des avantages, il est également important de comprendre les obstacles et les limites liés à leur intégration dans ton projet.
Les composants serveur ne peuvent pas interagir avec les méthodes de cycle de vie telles que `useEffect` ou `useState`. Cela signifie que tu ne peux pas gérer l'interactivité côté client au sein des composants serveur. Par exemple, si un formulaire est rendu côté serveur, tu auras besoin d'un composant client pour gérer les modifications de saisie en temps réel.
Lorsque tu utilises à la fois des composants côté client et côté serveur dans tes projets, il est important de gérer l’interaction entre ces deux types de composants dans toute ton application pour éviter tout problème. Par exemple, si ton application récupère des données depuis le serveur et permet aux utilisateurs de modifier ces données localement sur leurs appareils, tu pourrais rencontrer des problèmes pour maintenir la cohérence des données entre le serveur et les composants côté client.
Les composants côté serveur ne peuvent utiliser que des props sérialisables, ce qui signifie que tu ne peux pas passer de fonctions, de symboles ou d'objets complexes qui ne peuvent pas être sérialisés. Par exemple, envoyer une fonction de rappel d'un composant côté serveur vers un composant client entraînera un message d'erreur. Les composants côté serveur n'ont pas accès aux API du navigateur telles que window, document ou localStorage. Si tu as besoin d'interagir avec le DOM, cela doit se faire dans un composant client.
Si le code HTML affiché par le serveur ne correspond pas à ce qu'attend le JavaScript côté client, cela peut entraîner des problèmes pendant le processus d'hydratation. Par exemple, des différences dans le formatage des dates entre le serveur et le client peuvent causer de subtils décalages. Les décalages d'hydratation peuvent être difficiles à déboguer car la cause profonde n'est pas toujours évidente.
Certaines bibliothèques tierces peuvent ne pas fonctionner correctement avec les RSC, en particulier celles qui dépendent fortement des techniques de rendu côté client ou des API spécifiques aux navigateurs. Par exemple, des bibliothèques telles qu’react-router-dom nécessitent un rendu côté client. Tu devras peut-être remplacer ou adapter certaines bibliothèques pour qu’elles fonctionnent avec les RSC.
Il existe des solutions pratiques que tu peux mettre en œuvre pour maintenir la cohérence et résoudre les problèmes courants liés aux RSC.
Utilise des outils de gestion d'état qui fonctionnent à la fois sur le serveur et le client, comme Redux ou Zustand. Ces bibliothèques te permettent de centraliser ton état afin que les composants rendus par le serveur et ceux côté client puissent accéder aux mêmes données. Par exemple, tu pourrais utiliser Redux pour stocker un état global accessible aux deux côtés de l'application.
Assure-toi de maintenir un flux de données entre le serveur et le client en partageant le contexte. Par exemple, lorsque tu transfères des données utilisateur entre les composants serveur et client, assure-toi que les informations sont gérées de manière centralisée pour éviter toute divergence.
Envisage d'utiliser des outils de développement ou des linters de code pour identifier les propriétés non sérialisables susceptibles de causer des problèmes avec les RSC. Par exemple, des outils tels qu'ESLint peuvent être configurés pour détecter les props de fonction transmises depuis des composants côté serveur.
Veille à refactoriser les composants pour t'assurer que les props peuvent être sérialisées et éviter tout problème avec le SSR. Une façon de procéder consiste à déplacer certaines opérations, comme les gestionnaires d'événements, vers les composants client. Par exemple, lorsque tu transmets une fonction de rappel depuis un composant serveur, assure-toi que le code est adapté pour que l'opération se déroule au sein du composant client où elle est utilisée.
Pour résoudre les incohérences d'hydratation, il faut recourir à des techniques de test et de débogage proactives :
Si un logiciel tiers ne fonctionne pas avec les composants serveur comme l’exigent les exigences de ton projet, explore d’autres options compatibles avec le serveur. Si tu utilises une bibliothèque open source pour ton projet, tu pourrais envisager de contribuer à son développement pour y inclure la prise en charge des RSC. En contribuant, tu peux améliorer ta propre application et avoir un impact positif sur la communauté au sens large qui s’appuie sur cette même bibliothèque pour son travail.
En relevant ces défis avec des stratégies adaptées, tu peux contourner efficacement les limites des RSC et créer des applications robustes et performantes.
Dans cet article, nous avons expliqué les techniques de rendu de React. Nous avons présenté React Suspense et le SSR, et fourni un guide plus approfondi sur les RSC. Tu peux utiliser les RSC pour améliorer les performances de ton application en réduisant le besoin de traitement JavaScript côté client et en accélérant le chargement initial des pages.
Si tu souhaites tester les RSC dans tes projets, la première étape consiste à identifier les composants de ton application qui pourraient tirer parti du SSR. Tu pourras ensuite intégrer progressivement les RSC dans ton code.
La gestion de l'infrastructure pour le SSR et les composants serveur peut s'avérer complexe. L'utilisation d'Upsun, une plateforme en tant que service (PaaS), simplifie le déploiement et la mise à l'échelle de tes applications React. Grâce à sa prise en charge intégrée de Node.js et à sa scalabilité automatique, Upsun peut t'aider à gérer les pics de trafic en toute fluidité. Il fournit également des outils de surveillance et de sécurité et te permet de gérer plusieurs applications ou microservices dans différents langages au sein d'un même projet. Ainsi, tu peux te concentrer sur le développement de ton application React tandis qu'Upsun gère l'infrastructure de base.
