Développement 8 janvier 2026 14 min de lecture

React Server Components en pratique

Les RSC changent fondamentalement la façon d'architecturer une app React. Quand les utiliser, comment les combiner avec les Client Components, et les pièges à éviter.

Les React Server Components (RSC) représentent le changement de paradigme le plus significatif dans l'écosystème React depuis l'introduction des Hooks. Pas parce qu'ils ajoutent une feature de plus — mais parce qu'ils remettent fondamentalement en question la frontière entre serveur et client dans une application React.

Si vous travaillez avec Next.js 14 ou 15, vous utilisez déjà les RSC — peut-être sans en avoir une compréhension claire de leurs mécanismes. Voici ce que vous devez savoir pour les utiliser à leur plein potentiel, avec les patterns qui fonctionnent et les pièges à éviter.

Le problème que les RSC résolvent

Avant les RSC, tout composant React était un Client Component : il était rendu côté client, dans le navigateur, en JavaScript. Pour afficher des données, on utilisait un useEffect combiné à un fetch, ou une librairie comme React Query ou SWR. Résultat : une page vide ou un état skeleton pendant le chargement des données, et l'intégralité du JavaScript du composant envoyée au navigateur de l'utilisateur — même pour des composants purement affichage.

Les RSC permettent de rendre certains composants côté serveur, en n'envoyant au client que le HTML résultant. Pas de JavaScript pour ce composant — les données sont fetched directement sur le serveur, au plus près de la source, sans round-trip réseau supplémentaire.

Les RSC réduisent la taille du bundle JavaScript envoyé au client de 30 à 70 % sur les applications data-heavy, avec un impact direct sur le temps d'interaction initial et les performances perçues.

Server Components vs Client Components

La distinction fondamentale à intégrer :

Server Components — rendu sur le serveur. Aucun JavaScript envoyé au client pour ce composant. Peuvent accéder directement aux bases de données, aux fichiers système, aux APIs internes. Ne peuvent pas utiliser d'interactivité (pas de useState, useEffect, ni event handlers). C'est le comportement par défaut dans Next.js App Router.

Client Components — rendu sur le client (et côté serveur pour le SSR initial). Le JavaScript est envoyé au navigateur. Peuvent utiliser tous les Hooks React et les APIs navigateur. Se déclarent avec la directive "use client" en première ligne du fichier.

Comment décider

Un composant doit être un Client Component si et seulement si :

  • Il utilise useState, useReducer, useContext
  • Il utilise useEffect ou ses variantes
  • Il attache des event listeners (onClick, onChange, onSubmit...)
  • Il utilise des APIs navigateur (window, document, localStorage...)
  • Il dépend de librairies qui requièrent les APIs navigateur (certaines bibliothèques d'animation, de formulaires...)

Tous les autres composants peuvent — et devraient — être des Server Components. Dans une application Next.js bien architecturée, 70 à 80 % des composants peuvent être des Server Components.

Le data fetching avec les RSC

C'est là que les RSC brillent vraiment. Dans un Server Component, on peut faire du data fetching directement avec async/await, sans useEffect, sans état de chargement intermédiaire, sans gestion d'erreurs côté client.

La donnée est fetched au moment du rendu sur le serveur, et seul le HTML résultant est envoyé au client. L'utilisateur reçoit une page déjà remplie avec ses données — pas un squelette qui se remplira quelques secondes après.

Parallel data fetching

Dans un Server Component, on peut paralléliser les fetches pour éviter les cascades de requêtes. Au lieu d'attendre que la première requête soit terminée pour lancer la deuxième, on lance tout en parallèle avec Promise.all. Cette approche peut réduire le temps de chargement de données complexes de 40 à 60 % par rapport à des fetches séquentiels.

Le caching intégré

Next.js 15 introduit un système de caching sophistiqué pour les fetches dans les Server Components. Par défaut, les requêtes ne sont pas mises en cache (comportement modifié depuis Next.js 14). On peut contrôler finement le cache par requête : cache statique, revalidation à intervalle, revalidation à la demande via tags.

Ce contrôle granulaire du cache permet d'optimiser les performances sans sacrifier la fraîcheur des données.

Les patterns courants

Server Component qui wrap un Client Component

Le pattern le plus commun et le plus puissant : un Server Component qui fetche les données, puis les passe à un Client Component qui gère l'interactivité.

Le Server Component s'occupe de récupérer les données en async/await, directement depuis la base de données ou l'API. Il passe ces données comme props à un Client Component qui, lui, gère le tri, le filtrage, les animations — tout ce qui requiert de l'interactivité. La donnée est fetched côté serveur, l'interactivité est gérée côté client. Le meilleur des deux mondes.

Suspense et streaming

Les RSC s'intègrent parfaitement avec React Suspense pour le streaming : envoyer progressivement les parties de la page au fur et à mesure qu'elles sont prêtes, sans attendre que tout le contenu soit disponible.

Concrètement : le header et les parties statiques de la page sont envoyés immédiatement. Les sections dont les données ne sont pas encore prêtes sont remplacées par un fallback (skeleton, spinner). Quand les données arrivent, le contenu réel remplace le fallback — sans rechargement de page, en streaming depuis le serveur.

L'utilisateur voit quelque chose d'utile immédiatement, et le contenu apparaît progressivement plutôt que d'attendre un chargement complet.

Server Actions

Next.js 15 stabilise les Server Actions — des fonctions asynchrones qui s'exécutent sur le serveur, déclenchées depuis un Client Component via un formulaire ou un event handler.

Elles permettent de gérer les mutations de données (créer, modifier, supprimer) sans créer d'API route explicite. La fonction est marquée avec la directive "use server", elle s'exécute côté serveur, et peut ensuite invalider le cache pour que les données soient refetched.

Ce pattern simplifie considérablement l'architecture des applications full-stack en Next.js — moins de routes d'API à maintenir, moins de surface d'exposition.

Les pièges à éviter

Le "use client" propagation

Quand vous marquez un composant comme Client Component avec "use client", tous ses imports de composants deviennent également des Client Components — même s'ils n'ont pas besoin d'interactivité. C'est l'erreur la plus fréquente.

La solution : pousser "use client" au plus bas possible dans l'arborescence de composants, sur les feuilles de l'arbre qui ont réellement besoin d'interactivité. Cela maximise le nombre de Server Components.

La sérialisation des props

Les données passées d'un Server Component à un Client Component doivent être sérialisables : des primitives JavaScript (strings, numbers, booleans, arrays, plain objects). Vous ne pouvez pas passer des fonctions, des classes, des instances de Date non converties, ou des objets avec des méthodes.

Si vous devez passer une fonction de callback à un Client Component, cette fonction doit venir d'un autre Client Component — pas d'un Server Component.

L'excès d'optimisme sur le cache

Dans Next.js 14, les fetches dans les Server Components étaient mis en cache par défaut — ce qui pouvait entraîner des données périmées en production sans que le développeur s'en rende compte. Dans Next.js 15, ce comportement a changé : les fetches ne sont plus mis en cache par défaut. Connaître la version de Next.js avec laquelle vous travaillez et ses comportements de cache est essentiel pour éviter des bugs subtils.

Les Contexts dans les Server Components

Vous ne pouvez pas utiliser useContext dans un Server Component. Les Providers sont par nature des Client Components — ils créent un contexte qui ne peut être consommé que côté client. Pour partager des données entre Server Components, la solution est de les fetcher indépendamment (bénéficiant du déduplication automatique de Next.js) ou de les passer par les props depuis un composant parent.

Next.js 15 — l'état de l'art

Next.js 15 pousse les RSC encore plus loin avec plusieurs innovations majeures :

  • Partial Prerendering (PPR) — combiner rendu statique et dynamique dans une même page : le shell statique est pré-rendu à la compilation, les parties dynamiques sont streamées à la demande. Le meilleur du SSG et du SSR en un seul composant.
  • after() — exécuter du code côté serveur après que la réponse a été envoyée. Idéal pour les analytics, le logging, les notifications — sans impacter le temps de réponse perçu par l'utilisateur.
  • Amélioration des Server Actions — meilleure gestion des erreurs, support des formulaires progressifs, intégration avec useOptimistic pour des mises à jour optimistes.

Avec Next.js 15 et les RSC bien utilisés, des applications qui auraient nécessité une architecture Backend-for-Frontend complexe peuvent être construites avec un seul framework et une cohérence totale entre rendu serveur et interactivité client.

Par où commencer

Si vous démarrez avec les RSC dans Next.js :

  • Commencez par identifier dans votre application existante quels composants n'ont pas besoin d'interactivité
  • Retirez "use client" de ces composants et testez que tout fonctionne toujours
  • Déplacez progressivement le data fetching des Client Components vers des Server Components parents
  • Utilisez React DevTools pour visualiser l'arbre de composants et identifier où se situent vos Client Components

Les RSC ne remplacent pas les Client Components — ils les complètent. La clé est de développer le réflexe de se demander, pour chaque composant : "est-ce que ce composant a réellement besoin d'interactivité côté client ?" Si la réponse est non, c'est un Server Component. Et votre bundle JavaScript vous remerciera.

Thématiques
ReactNext.jsRSCArchitecture