Go to the Centreon Community website

Introduction

Cet article est à destination de notre communauté et a été réalisé à partir des travaux et méthodes de travail utilisés au sein de notre équipe de développement et qui ont fait leurs preuves. 

L’équipe de développement de Centreon est toujours en recherche constante de nouvelles méthodes pour améliorer la qualité du code produit mais aussi pour gagner en productivité et cela pour nous permettre de nous concentrer sur ce qui rend le codage vraiment intéressant: créer de grandes et belles apps ! C’est la raison pour laquelle nous partageons avec vous ce tuto qui vous explique comment exploiter deux outils que nous aimons particulièrement ESLint et Prettier et que nous utilisons pour mieux collaborer et garder un code toujours “nickel” !

Commençons par quelques notions de base: si vous savez déjà à quoi sert de linter son code, vous pouvez passer directement au détail du tuto pour apprendre à mieux collaborer au sein d’un projet React avec ESLint et Prettier. Dans le cas contraire, lisez le paragraphe ci-dessous !

Qu’est-ce que le code linting (à quoi cela sert de linter son code) ?

Pour commencer, rappelons que Linting en anglais signifie peluchage en référence aux “peluches” qui peuvent rester sur vos vêtements et qui font que votre linge n’est pas totalement “clean”. Pour vous aider à comprendre comment fonctionne le linting de code, comparons-le avec le sèche-linge qui va “attraper” les peluches et rendre votre linge propre .  En programmation, le linter est un outil d’analyse de code statique qui permet de maintenir le code sans erreur ( et sans “peluche”) et de garantir que le style de codage et la construction restent cohérents, quelle que soit la personne qui code. Comme pour la charte graphique, le code va respecter un certain nombre de règles pour éviter de produire des “peluches”.

Comme la plupart des membres de la communauté JavaScript, nous privilégions l'outil ESLint qui permet de scanner le code sans avoir à l’exécuter. L’outil est très flexible et combine une bibliothèque de plugins qui permettent de répondre à de nombreux besoins et qui propose des configurations prêtes à l’emploi. 

Parmi ces plugins, il y a Prettier, sur lequel nous allons faire un focus car il permet de re formater automatiquement le code, garantissant ainsi le respect des règles concernant l'indentation, l'espacement , les points virgules et les guillemets. 

Le tutoriel porte donc sur l’utilisation de ce plugin et sur la façon de configurer ESLint et Prettier pour optimiser la collaboration d’une équipe dans un environnement React.

Installation et configuration

Pour ce tutoriel, nous allons partir de l'exemple d’une application React. Le moyen le plus simple est d’utiliser le générateur create-react-app, de manière à partir d’une application de base déjà fonctionnelle. Commençons par générer notre application en lançant :

$ npx create-react-app my-app
ESLint peut être installé comme n’importe quel packet NPM. Nous allons donc l’installer en utilisant :
$ cd my-app
$ npm install --save-dev eslint

Nous allons ensuite générer les fichiers de configuration permettant d’indiquer à ESLint quelles règles devront être suivies lors de l'exécution de l’analyse :

$ npx eslint --init

La CLI (interpréteur de ligne de commande) va ensuite poser un ensemble de questions. Voici les réponses à apporter:  :

How would you like to use ESLint? To check syntax, find problems, and enforce code style
What type of modules does your project use? JavaScript modules (import / export)
Which framework does your project use? React
Does your project use TypeScript? No
Where does your code run? Browser
How would you like to define a style for your project? Use a popular style guide
Which style guide do you want to follow? Airbnb
What format do you want your config file to be in? JavaScript

Après avoir répondu à ces questions, les dépendances requises vont être installées sur votre projet.

Le Airbnb JavaScript Style Guide est devenu un standard solide en ce qui concerne les bonnes pratiques JavaScript, en plus de bénéficier d’une bonne maintenance de sa configuration JavaScript et d’une importante communauté. C’est la raison pour laquelle nous avons décidé, chez Centreon, de l’utiliser comme base pour nos projets JavaScript. Nous vous recommandons de faire de même.

Ajoutons maintenant un script dans le fichier package.json afin de vérifier les problèmes de linting, ainsi qu’un autre pour corriger les erreurs qui peuvent l’être automatiquement :

// package.json

{
  "name": "my-app",
  ...
  },
  "scripts": {
    ...
    "eslint": "eslint src --ext .js,.jsx",
    "eslint:fix": "npm run eslint -- --fix"
  },
  ...
}

Ensuite, lançons la commande pour découvrir les problèmes qui en résultent :

$ npm run eslint

> my-app@0.1.0 eslint
> eslint src --ext .js,.jsx


/Users/brunodauria/my-app/src/App.js
   6:5   error  'React' must be in scope when using JSX                      react/react-in-jsx-scope
   6:5   error  JSX not allowed in files with extension '.js'                react/jsx-filename-extension
   7:7   error  'React' must be in scope when using JSX                      react/react-in-jsx-scope
   8:9   error  'React' must be in scope when using JSX                      react/react-in-jsx-scope
   9:9   error  'React' must be in scope when using JSX                      react/react-in-jsx-scope
  10:16  error  `code` must be placed on a new line                          react/jsx-one-expression-per-line
  10:16  error  'React' must be in scope when using JSX                      react/react-in-jsx-scope
  10:39  error  ` and save to reload.        ` must be placed on a new line  react/jsx-one-expression-per-line
  12:9   error  'React' must be in scope when using JSX                      react/react-in-jsx-scope

/Users/brunodauria/my-app/src/App.test.js
  4:1   error  'test' is not defined                          no-undef
  5:10  error  'React' must be in scope when using JSX        react/react-in-jsx-scope
  5:10  error  JSX not allowed in files with extension '.js'  react/jsx-filename-extension
  7:3   error  'expect' is not defined                        no-undef

/Users/brunodauria/my-app/src/index.js
   8:3   error  JSX not allowed in files with extension '.js'  react/jsx-filename-extension
  11:34  error  Missing trailing comma                         comma-dangle

/Users/brunodauria/my-app/src/reportWebVitals.js
  1:25  error  Expected parentheses around arrow function argument  arrow-parens
  3:32  error  Expected a line break after this opening brace       object-curly-newline
  3:74  error  Expected a line break before this closing brace      object-curly-newline

18 problems (18 errors, 0 warnings)
  6 errors and 0 warnings potentially fixable with the `--fix` option.

En premier lieu, corrigeons les problèmes qui peuvent l’être automatiquement grâce à la commande que nous avons ajoutée :

$ npm run eslint:fix

> my-app@0.1.0 eslint:fix
> npm run eslint -- --fix


> my-app@0.1.0 eslint
> eslint src "--fix"


/Users/brunodauria/my-app/src/App.js
   6:5   error  'React' must be in scope when using JSX        react/react-in-jsx-scope
   6:5   error  JSX not allowed in files with extension '.js'  react/jsx-filename-extension
   7:7   error  'React' must be in scope when using JSX        react/react-in-jsx-scope
   8:9   error  'React' must be in scope when using JSX        react/react-in-jsx-scope
   9:9   error  'React' must be in scope when using JSX        react/react-in-jsx-scope
  12:11  error  'React' must be in scope when using JSX        react/react-in-jsx-scope
  16:9   error  'React' must be in scope when using JSX        react/react-in-jsx-scope

/Users/brunodauria/my-app/src/App.test.js
  4:1   error  'test' is not defined                          no-undef
  5:10  error  'React' must be in scope when using JSX        react/react-in-jsx-scope
  5:10  error  JSX not allowed in files with extension '.js'  react/jsx-filename-extension
  7:3   error  'expect' is not defined                        no-undef

/Users/brunodauria/my-app/src/index.js
  8:3  error  JSX not allowed in files with extension '.js'  react/jsx-filename-extension

12 problems (12 errors, 0 warnings)

Vous pouvez voir un grand nombre de problèmes, y compris certains indiquant que React doit être dans le scope lorsque du code JSX est utilisé. Depuis React v17, cela n’est plus requis, nous allons donc désactiver cette règle dans le fichier .eslintrc.js:

module.exports = {
  ...
  rules: {
    'react/react-in-jsx-scope': 'off',
  },
};

Renommons ensuite les fichiers contenant du code JSX en utilisant l’extension .jsx

$ mv src/App.js src/App.jsx

$ mv src/index.js src/index.jsx

$ mv src/index.test.js src/index.test.jsx

Il reste à présent seulement deux erreurs :

$ npm run eslint 

> my-app@0.1.0 eslint
> eslint src --ext .js,.jsx


/Users/brunodauria/my-app/src/App.test.jsx
  4:1  error  'test' is not defined    no-undef
  7:3  error  'expect' is not defined  no-undef

2 problems (2 errors, 0 warnings)

Comme elles sont liées directement au fonctionnement de Jest (framework de test JavaScript), nous pouvons, soit les désactiver (au moins pour les fichiers de test), soit ajouter un plugin ESLint dédié. C’est ce que nous allons faire afin d’éviter d’écrire du code qui pourrait potentiellement passer à travers nos règles de linting.

Installons d’abord le plugin :

$ npm install --save-dev eslint-plugin-jest

Ensuite ajoutons le plugin à la configuration :

// .eslintrc.js

module.exports = {
  env: {
    ...
    'jest/globals': true,
  },
  ...
  plugins: [
    ...
    'jest',
  ],
  ...
};

Ce qui devrait nous soulager des erreurs restantes !

Ajouter les règles de formatage avec le plugin Prettier

Formater le code automatiquement afin de le rendre plus clair et plus lisible est une chose cruciale quand il s’agit de travailler en équipe (et de façon générale cela aide beaucoup le développeur même quand il travaille seul !). Cela peut faire gagner beaucoup de temps, particulièrement lors des revues de diffs provenant d’une Pull request, et cela permet de se concentrer sur le code à écrire plutôt que sa présentation esthétique. 

Prettier permet cela, grâce à une configuration minimale et sans avoir à se préoccuper de la gestion de règles trop nombreuses (gérer celles de base suffisent amplement !). Un plugin ESLint est disponible pour réaliser son intégration complète, évitant ainsi d’avoir à utiliser plusieurs outils. Toute violation des règles de formatage devient un problème de linting qui va être remonté par ESLint et qui pourra être éventuellement corrigé automatiquement.  

En premier lieu, nous allons indiquer à ESLint quelles règles doivent être désactivées afin d’éviter les conflits avec Prettier. Cela est fait par le paquet eslint-config-prettier.

Installons-le :

$ npm install --save-dev eslint-config-prettier
Ensuite, ajoutons-le au fichier de configuration :
// .eslintrc.js

module.exports = {
  ...
  extends: [

    ...
    'prettier',
  ],
  ...

};

A présent, installons le plugin Prettier de ESLint :

$ npm install --save-dev eslint-plugin-prettier

Ajoutons le plugin dans la configuration, en plus de la règle correspondante :

//.eslintrc.js

module.exports = {
  ...
  plugins: [
    ...
    'prettier'
  ],
  ...
  rules: {
    ...
    "prettier/prettier": "error",
  },
};

Une vérification des problèmes donne :

$ npm run eslint

> my-app@0.1.0 eslint
> eslint src --ext .js,.jsx


/Users/brunodauria/my-app/src/App.jsx
   1:18  error  Replace `'./logo.svg'` with `"./logo.svg"`                                                                                prettier/prettier
   2:8   error  Replace `'./App.css'` with `"./App.css"`                                                                                  prettier/prettier
  10:15  error  Replace `⏎··········{'·'}⏎··········<code>src/App.jsx</code>⏎··········{'·'}⏎·········` with `·<code>src/App.jsx</code>`  prettier/prettier

/Users/brunodauria/my-app/src/App.test.jsx
  1:32  error  Replace `'@testing-library/react'` with `"@testing-library/react"`      prettier/prettier
  2:17  error  Replace `'./App'` with `"./App"`                                        prettier/prettier
  4:6   error  Replace `'renders·learn·react·link'` with `"renders·learn·react·link"`  prettier/prettier

/Users/brunodauria/my-app/src/index.jsx
   1:19  error  Replace `'react'` with `"react"`                          prettier/prettier
   2:22  error  Replace `'react-dom'` with `"react-dom"`                  prettier/prettier
   3:8   error  Replace `'./index.css'` with `"./index.css"`              prettier/prettier
   4:17  error  Replace `'./App'` with `"./App"`                          prettier/prettier
   5:29  error  Replace `'./reportWebVitals'` with `"./reportWebVitals"`  prettier/prettier
  11:27  error  Replace `'root'),` with `"root")`                         prettier/prettier

/Users/brunodauria/my-app/src/reportWebVitals.js
  3:12  error  Replace `'web-vitals').then(({⏎······getCLS,·getFID,·getFCP,·getLCP,·getTTFB,⏎···` with `"web-vitals").then(({·getCLS,·getFID,·getFCP,·getLCP,·getTTFB`  prettier/prettier

/Users/brunodauria/my-app/src/setupTests.js
  5:8  error  Replace `'@testing-library/jest-dom'` with `"@testing-library/jest-dom"`  prettier/prettier

14 problems (14 errors, 0 warnings)
  14 errors and 0 warnings potentially fixable with the `--fix` option.

La bonne nouvelle est que la plupart des erreurs identifiées par Prettier peuvent être corrigées automatiquement. Pour corriger les erreurs remontées, lançons simplement :

$ npm run eslint:fix

Résultat : un code libre de toute erreur !

Nous allons voir dans la prochaine section qu’il existe un moyen de remonter ces problèmes encore plus rapidement, directement depuis VSCode, si c’est votre éditeur de choix, et sinon, il est peut-être temps d’y passer:)

Configurer ESLint dans VSCode

Un des bons points à propos de VSCode : le nombre important d’extensions disponibles! ESLint est l’une d’entre elles et va permettre de réduire le temps de réponse au niveau de processus de linting. Pour l’installer, sélectionnez le menu d'extensions, recherchez ESLint, et installez-la : 

Il faut ensuite autoriser la vérification de fichiers en cliquant sur le bouton correspondant dans la barre des tâches à droite. Une fois cette action réalisée, vous obtenez un indicateur précisant que la vérification est fonctionnelle : 

Ensuite, afin d’indiquer quels types de sources vous souhaitez faire valider par ESLint lors de l’écriture du code, allez dans le fichier de configuration de VSCode nommé settings.json (File > Preferences > Settings) :

...
    "eslint.validate": [
        "javascript",
        "javascriptreact"
    ]

Pour corriger automatiquement les problèmes résultant au moment de la sauvegarde d’un fichier, ajoutez le paramètre suivant :

...

    "editor.codeActionsOnSave": {
        "source.fixAll.eslint": true
    }

Maintenant, en plus d’obtenir les erreurs de linting (ce qui inclut celles au niveau du formatage remontées par Prettier), la sauvegarde va également corriger automatiquement les erreurs qui peuvent l’être :

Et nous sommes maintenant prêts à commettre notre code !

Si vous avez des questions ou suggestions par rapport à cet article, réagissez sur The Watch.


Bruno D'Auria, Team Leader - Modern UX/UI

Diplômé d’un master en Informatique, Réseaux et Télécommunications à l’IMT Atlantique (Ex Télécom Bretagne), Bruno a travaillé en tant que développeur logiciel dans diverses industries : télécommunications, sport, énergie, immobilier et domotique. Il a ensuite choisi de se spécialiser dans le développement d’interfaces web et mobile. Bruno a rejoint Centreon il y a 3 ans et il est aujourd’hui responsable de l'équipe “Modern UI/UX”. Sa mission est de concevoir et d’implémenter les interfaces de demain dans le but de rendre l’expérience utilisateur encore plus ergonomique et agréable.