Mieux gérer CSS dans les gros projets grâce aux CSS modules.

Jérôme Boukorras
Just-Tech-IT
5 min readJun 4, 2021

--

Dans de nombreux projets web, la gestion des styles présente souvent des difficultés. Il est vrai que dans un contexte d’entreprise où l’on demande aux développeuses et développeurs d’être full-stack, et donc de maîtriser aussi bien le dernier framework C# que la cascade CSS, la tâche est compliquée.
Outre les problèmes de compréhension des règles CSS, deux problèmes récurrents surviennent : la gestion du code mort et de la cascade CSS.

La cascade

Le principe de cascade en CSS est un concept difficile à maîtriser pour beaucoup de développeuses et de développeurs. Sa difficulté de compréhension n’est pas forcément remise en cause, mais plutôt sa difficulté de mise en application. Nombreuses sont les personnes à s’énerver devant leur code en ne comprenant pas pourquoi certains styles ne s’appliquent pas ou bien se demandant d’où viennent ces styles qui viennent s’appliquer.

J’ai toujours été un fervent défenseur du CSS et de son mode de fonctionnement en cascade, mais aujourd’hui, force est de constater que dans le contexte actuel de l’ingénierie logicielle, le principe de cascade n’est peut-être plus aussi pertinent qu’autrefois.
En effet, les grosses applications conçues à l’heure actuelle, doivent bien souvent l’être à l’aide de composants réutilisables et autonomes. Un composant qui hérite des styles d’un autre composant n’est plus autonome et difficilement réutilisable.

Le code mort

Dans les gros projets actuels, beaucoup de développeurs et de développeuses interviennent. En plus des problèmes de manque de maîtrise du principe de cascade, un autre problème survient : le code mort. Il n’est, en effet pas possible de trouver facilement le code non utilisé dans une application, et seule une personne connaissant bien la partie CSS du projet peut repérer du code non utilisé. Ce qui n’est pas évident et laisse place à des erreurs ou des oublis.

Le code mort est un gros problème en CSS. Il y a bien sûr un problème de performance, on télécharge dans le navigateur une certaine quantité de code inutile. Mais il y a plus gênant encore, du code mort en CSS peut quand même s’appliquer à votre code si vos noms de classe sont identiques. A ce moment-là à moins de connaître parfaitement le projet, vous n’avez aucune idée que le code mort est bien … mort. Vous partez donc du principe que ce code est utile et surchargez vos sélecteurs, créant alors involontairement du code trop complexe. Ou pire… vous cédez à la tentation du côté obscur et utilisez !important.

Les solutions utilisées

BEM

La méthode de nommage BEM est très pratique pour créer des noms de classes uniques, et donc isoler du code CSS tout en gardant la logique de cascade. La syntaxe de cette méthode est relativement complexe, à base d’underscore, double-underscore, tiret, double-tiret… cela engendre généralement beaucoup de confusion et d’erreurs.
Le problème vient du manque de vérification, si quelqu’un écrit une classe ne respectant pas la méthode de nommage, le code fonctionne quand même.
Cette méthode dégrade également la lisibilité du code, on se retrouve très vite avec des noms de classe CSS à rallonge.

CSS-in-JS

Les librairies de CSS-in-JS comme styles-components ou emotion résolvent les problèmes cités précédemment, mais au prix d’une grande complexité de mise en place, surtout pour un projet existant. Ces librairies fonctionnent généralement au runtime, ce qui engendre une perte de performance.
Malgré un gain de popularité, sur la plupart des projets, les solutions de CSS-in-JS sont souvent considérées comme de l’over-engineering.

CSS Modules : le parfait compromis

CSS modules n’est pas une librairie, il s’agit d’une manière de compiler le code JavaScript d’une application en important les styles CSS de la même manière qu’un module JavaScript. C’est le bundler (Webpack, Rollup etc.) qui fait le travail lors de la compilation. Ce dernier va alors réécrire les noms de classe CSS en suivant le schéma indiqué dans ces paramètres, ce schéma peut ressembler à celui de BEM par exemple. Il ajoutera également à ce nom de classe un hash unique. Ce qui permettra alors de scoper ces styles à votre composant. Les styles de votre composant ne s’appliqueront alors qu’à votre composant peu importe le nom de classe que vous utiliserez.

Mise en place

Un des avantages de CSS modules, c’est sa facilité de mise en place. Si vous utilisez actuellement Webpack dans votre projet, il vous faut juste configurer css-loader.

Si vous utilisez React avec une version récente de react-scripts (à partir de la 2.0.0), vous pouvez utiliser CSS Modules quasiment sans rien configurer.

Si vous utilisez Svelte, alors vous n’avez rien à faire et vous utilisez déjà CSS Modules (peut-être même sans le savoir).

Utilisation dans le fichier de styles

Vos styles doivent se trouver dans des fichiers *.module.css (ou *module.scss). Le code CSS est le même que ce que vous utilisez habituellement (CSS, SASS ou LESS), la seule différence c’est que vous pouvez simplifier vos noms de classe:

  • monBlock__monElement” devient juste “monElement”.
  • monBlock__monElement monBlock__monElement — monModifier” devient juste “monElement monModifer”.

Imaginons que nous souhaitions créer un composant de modale, le code CSS du module ressemblerai tout simplement à :

.modale {
position: absolute;
}

Il est toujours possible d’appliquer globalement des styles à des éléments non présents dans votre composant en utilisant :global.

Il est également possible de faire de la composition entre différents modules. Reprenons notre modale, si nous voulons lui faire hériter des styles d’un autre composant appelé view, nous pouvons utiliser composes comme ceci :

.modale {
composes: view from "./view.css";
position: absolute;
}

Utilisation dans le fichier JavaScript

Vos modules CSS doivent être importés de la même manière qu’un module JavaScript avec import.

import styles from "./style.css";

Il faut ensuite appliquer vos classes à chaque balise. Dans notre exemple, nous pouvons utiliser la classe modale. Exemple avec du JSX :

<div className={styles.modale}></div>

Suppression du code mort

A l’instar des modules JavaScript, les modules de styles sont importés par votre bundler, ce dernier est alors capable de détecter les modules non utilisés. Vous pouvez installer ce plugin eslint qui permet de surveiller la présence de code mort dans votre application. Si du code mort est détecté, vous aurez un message dans la console de votre build.

Conclusion

CSS modules n’est ni une grosse nouveauté ni la dernière librairie à la mode, il pourrait cependant devenir un vrai quick win pour votre projet tant son ratio gains / difficultés de mise en place est avantageux.

--

--