Importer et exporter des composants

La magie des composants réside dans leur réutilisabilité : vous pouvez créer des composants qui sont composés d’autres composants. Mais plus vous imbriquez de composants, plus il devient judicieux de les répartir en différents fichiers. Ça vous permet de garder vos fichiers faciles à analyser et de réutiliser les composants à davantage d’endroits.

Vous allez apprendre

  • Qu’est-ce qu’un fichier de composant racine
  • Comment importer et exporter un composant
  • Quand utiliser les imports/exports par défaut et nommés
  • Comment importer et exporter plusieurs composants à partir d’un seul fichier
  • Comment découper les composants en plusieurs fichiers

Le fichier de composant racine

Dans Votre premier composant, vous avez créé un composant Profile et un composant Gallery qui l’affiche :

function Profile() {
  return (
    <img
      src="https://i.imgur.com/MK3eW3As.jpg"
      alt="Katherine Johnson"
    />
  );
}

export default function Gallery() {
  return (
    <section>
      <h1>Scientifiques de renom</h1>
      <Profile />
      <Profile />
      <Profile />
    </section>
  );
}

Ces composants sont actuellement déclarés dans un fichier de composant racine, nommé App.js dans cet exemple. Si vous utilisez Create React App, votre appli se trouve dans src/App.js. Selon votre configuration, votre composant racine pourrait toutefois être dans un autre fichier. Si vous utilisez un framework avec un système de routage basé sur les fichiers, comme Next.js, votre composant racine sera différent pour chaque page.

Exporter et importer un composant

Et si vous souhaitiez changer l’écran d’accueil à l’avenir et y mettre une liste de livres de science ? Ou encore placer tous les profils ailleurs ? Il est logique de déplacer Gallery et Profile en dehors du fichier de composant racine. Ça les rendra plus modulaires et réutilisables par d’autres fichiers. Vous pouvez déplacer un composant en trois étapes :

  1. Créez un nouveau fichier JS pour y mettre les composants.
  2. Exportez votre fonction composant à partir de ce fichier (en utilisant soit les exports par défaut soit les exports nommés).
  3. Importez-la dans le fichier qui utilisera le composant (en utilisant la technique correspondante pour importer les exports par défaut ou nommés).

À présent que les deux composants Profile et Gallery ont été déplacés du fichier App.js vers un nouveau fichier Gallery.js, Vous pouvez modifier App.js pour importer le composant Gallery depuis Gallery.js :

import Gallery from './Gallery.js';

export default function App() {
  return (
    <Gallery />
  );
}

Voyez comme cet exemple est désormais découpé en deux fichiers de composants :

  1. Gallery.js:
    • Définit le composant Profile qui n’est utilisé qu’au sein de ce même fichier et n’est pas exporté.
    • Exporte le composant Gallery en tant qu’export par défaut.
  2. App.js:
    • Importe Gallery en tant qu’import par défaut depuis Gallery.js.
    • Exporte le composant racine App en tant qu’export par défaut.

Remarque

Il se peut que vous rencontriez des fichiers qui omettent l’extension .js comme ceci :

import Gallery from './Gallery';

'./Gallery.js' ou './Gallery' fonctionneront tous les deux avec React, bien que la première syntaxe soit plus proche du fonctionnement des modules ES natifs.

En détail

Exports par défaut vs. exports nommés

Il existe deux façons principales d’exporter des valeurs avec JavaScript : les exports par défaut et les exports nommés. Jusqu’à présent, nos exemples n’ont utilisé que des exports par défaut. Mais vous pouvez utiliser l’un ou l’autre, ou les deux, dans le même fichier. Un fichier ne peut avoir qu’un seul export par défaut, mais il peut avoir autant d’exports nommés que vous le souhaitez.

Exports par défaut et nommés

La manière dont vous exportez votre composant dicte la manière dont vous devez l’importer. Vous obtiendrez une erreur si vous essayez d’importer un export par défaut de la même manière que vous le feriez pour un export nommé ! Ce tableau peut vous aider à vous y retrouver :

SyntaxeDéclaration d’exportDéclaration d’import
Par défautexport default function Button() {}import Button from './Button.js';
Nomméexport function Button() {}import { Button } from './Button.js';

Lorsque vous utilisez un import par défaut, vous pouvez mettre n’importe quel nom après import. Par exemple, vous pourriez écrire import Banana from './Button.js' et ça vous fournirait toujours le même export par défaut. En revanche, avec les imports nommés, le nom doit correspondre des deux côtés. C’est pour ça qu’on parle d’imports nommés.

On utilise souvent les exports par défaut si le fichier n’exporte qu’un seul composant, et les exports nommés si l’on souhaite exporter plusieurs composants et valeurs. Quel que soit le style de développement que vous préférez, donnez toujours des noms descriptifs à vos fonctions composants et aux fichiers qui les contiennent. Les composants anonymes, du genre export default () => {}, sont à proscrire car ils rendent le débogage plus difficile.

Exporter et importer plusieurs composants depuis le même fichier

Et si vous vouliez afficher un seul Profile au lieu d’une galerie ? Vous pouvez également exporter le composant Profile. Mais Gallery.js a déjà un export par défaut, et vous ne pouvez pas en avoir deux dans un même fichier. Dans ce cas, vous pouvez créer un nouveau fichier avec un export par défaut, ou ajouter un export nommé pour le composant Profile. Un fichier ne peut avoir qu’un seul export par défaut, mais il peut avoir de nombreux exports nommés !

Remarque

Pour réduire la confusion potentielle entre les exports par défaut et nommés, certaines équipes choisissent de ne s’en tenir qu’à un seul style (par défaut ou nommé), ou évitent simplement de les mélanger dans un seul fichier. Faites ce qui vous convient le mieux !

Tout d’abord, exportez Profile depuis Gallery.js en utilisant un export nommé (sans le mot-clé default) :

export function Profile() {
// ...
}

Puis, importez Profile depuis Gallery.js dans App.js en utilisant un import nommé (avec les accolades) :

import { Profile } from './Gallery.js';

Enfin, affichez <Profile /> depuis le composant App :

export default function App() {
return <Profile />;
}

Désormais, Gallery.js contient deux exports : un export par défaut Gallery, et un export nommé Profile. App.js importe à présent les deux. Essayez de passer de <Profile /> à <Gallery /> et inversement dans cet exemple :

import Gallery from './Gallery.js';
import { Profile } from './Gallery.js';

export default function App() {
  return (
    <Profile />
  );
}

Vous utilisez à présent un mélange d’exports par défaut et nommés :

  • Gallery.js:
    • Exporte le composant Profile en tant qu’export nommé appelé Profile.
    • Exporte le composant Gallery en tant qu’export par défaut.
  • App.js:
    • Importe Profile en tant qu’import nommé appelé Profile depuis Gallery.js.
    • Importe Gallery en tant qu’import par défaut depuis Gallery.js.
    • Exporte le composant racine App en tant qu’export par défaut.

En résumé

Dans cette page, vous avez appris :

  • Ce qu’est un fichier de composant racine
  • Comment importer et exporter un composant
  • Quand et comment utiliser les imports/exports par défaut et nommés
  • Comment importer plusieurs composants depuis le même fichier

Défi 1 sur 1 ·
Découper davantage les composants

Pour le moment, Gallery.js exporte à la fois Profile et Gallery, ce qui est un peu déroutant.

Déplacez le composant Profile vers son propre fichier Profile.js, puis modifiez le composant App pour qu’il affiche à la fois <Profile /> et <Gallery /> l’un après l’autre.

Vous pouvez utiliser soit un export par défaut, soit un export nommé pour le composant Profile, mais assurez-vous d’utiliser la syntaxe d’importation correspondante dans App.js et Gallery.js ! N’hésitez pas à vous référer au tableau de la partie « En détail » vue plus tôt :

SyntaxeDéclaration d’exportDéclaration d’import
Par défautexport default function Button() {}import Button from './Button.js';
Nomméexport function Button() {}import { Button } from './Button.js';
// Déplace-moi vers Profile.js !
export function Profile() {
  return (
    <img
      src="https://i.imgur.com/QIrZWGIs.jpg"
      alt="Alan L. Hart"
    />
  );
}

export default function Gallery() {
  return (
    <section>
      <h1>Scientifiques de renom</h1>
      <Profile />
      <Profile />
      <Profile />
    </section>
  );
}

Après avoir réussi à faire fonctionner votre composant avec un type d’export, faites-le fonctionner avec l’autre type.