Utilité typescript à quoi il sert en pratique, par rapport à Javascript, pour bien débuter la programmation TS avec des bases en JS débutant

À quoi sert TypeScript exactement ? Et pourquoi utiliser ce langage ?

Maintenant que nous avons vu qu’est-ce que TypeScript, vous vous demandez peut-être à quoi sert vraiment TypeScript ? Et pourquoi s'embêter à ajouter cette couche supplémentaire à JavaScript, alourdissant en apparence son code ? Eh bien c'est tout l'objet de cet article, qui vous montrera comment TypeScript peut vous sauver de bugs inattendus et sournois, afin de sécuriser vos projets !

Comme vous l'aurez compris Ici, il s'agira pour moi de vous montrer l’utilité concrète de TS (TypeScript), afin de bien comprendre pourquoi il peut être indispensable de développer avec ! C'est pourquoi nous verrons notamment pourquoi utiliser TypeScript afin d'anticiper d'éventuelles erreurs à l'exécution du code, et des cas d'usages concrets, pour être plus parlant encore ! Alors, intéressé ? Si oui, par ici la suite !

Remarque : je vous ferais des articles plus détaillés ensuite, afin que vous puissiez mieux comprendre tout ça. Pour l'heure, je vous fais juste un tour d'horizon, afin de vous faire découvrir TypeScript !

Salut ! Bienvenue sur LeCoinTS, où je partage des tutos TypeScript gratuits et sans pub. Envie de me soutenir dans cette aventure, avec un café ? ☕

Offrez moi un café LeCoinTS

Pourquoi utiliser TypeScript ?

En fait, JavaScript est simple et flexible, et c'est pour ça qu'on l'aime ! Mais il faut savoir que cette liberté à un prix, et peut coûter cher, avec des bugs parfois difficiles à remonter ! En effet, des erreurs peuvent passer inaperçues, y compris au moment de l’exécution (du fait de la grande permissivité de JavaScript), et peuvent conduire à, par exemple, des enregistrements faussés en base de données (ce qui peut être dur et long à corriger ensuite, si l'on souhaite conserver les données déjà enregistrées en BDD). C'est pourquoi TypeScript est si intéressant, car il intervient en amont, grâce à ses types statiques. En clair : TypeScript permet d'anticiper certains problèmes à venir, et c'est pour ça que les "bons" développeurs préfèrent TypeScript à JavaScript, une fois qu'ils l'ont pratiqué 😉

Toujours pas convaincu ? Alors laissez moi vous illustrer cela, avec 3 exemples typiques d'erreurs involontaires ou inattendues, que l'on peut couramment rencontrer avec Javascript (et qu'on aurait identifié dès le départ, avec TypeScript !).

Le mauvais typage de variables

Il faut savoir qu'avec Javascript, rien n’empêche d’assigner un type différent à une variable préalablement typée. Du coup, on peut malencontreusement mélanger des types en cours de route, sans le faire exprès, jusqu'au moment où le programme plante ou transmet des informations incohérentes !

Pour vous illustrer cela, voici un exemple de code JS incohérent (mais parfaitement correct, du point de vue du langage Javascript) :

// JavaScript
let age = 45;
age = "masculin"; // Pas d’erreur côté Javascript, mais la logique … n'est pas logique !

Admettons que cet exemple permette de caractériser une personne. Ici, on a bien déclaré une variable "age" dans laquelle on aurait mis l'âge de cette personne ; imaginons ensuite qu'on ait voulu renseigné le sexe de cette personne, mais, que par erreur, on enregistre cette valeur dans la variable "age". Eh bien à l'exécution de ce code Javascript ne remonte pas la moindre erreur, car JS est très permissif en cela. Du coup, on affecte du texte à une variable numérique, et le code continue à s'exécuter comme si de rien n'était, provoquant au mieux des incohérences, au pire un crash programme !

Et bien, en TypeScript, on aurait identifié le mélange de typage bien avant d'avoir exécuté le code ; car le compilateur nous aurait immédiatement remonté l'erreur ! Pour "preuve" :

// TypeScript
let age = 45;
age = "masculin"; // Erreur : Type 'string' is not assignable to type 'number'

En bref, on a le signalement d'erreur, avant l'exécution de ce code ! Ici, cela nous montre que la variable "age", qui a préalablement été initialisée avec une valeur numérique, ne peut pas ensuite recevoir du texte (car ça n'aurait pas de sens, évidemment !). Autrement dit : en TypeScript, on peut garantir un certain niveau de contrôle en amont, avant d'exécuter tel ou tel programme (même si, on est d'accord, on peut se tromper de bien d'autres manières !).

Nota : vous verrez plus tard qu'on peut explicitement préciser le type de chaque variable, dès leur déclaration initiale. Par exemple, on aurait pu écrire ici "let age: number;" pour initier cette variable, ce qui reviendrait à dire que seules des valeurs numériques (de type number, donc) seraient admises ici, et rien d'autre !

Les erreurs "undefined" ou "null" inattendues

Croyez moi ou pas, mais en JS (JavaScript), il est facile d’appeler une propriété ou une fonction qui n’existe pas (et qui donc renvoie "undefined", c'est à dire "non défini", en français) et pourtant continuer l'exécution du code (et ce, sur un retour d'information potentiellement erronée !).

Voici un exemple Javascript illustrant cela :

// JavaScript
const utilisateur = {};
if(utilisateur.habite_en_France)
  console.log("Vous habitez en France !");
else
  console.log("Vous habitez en dehors de la France"); // <-- réponse retournée, car "habite_en_France" n'est pas défini ;
                                                      //     pas la moindre erreur est remontée ici, donc le programme
                                                      //     continue sa route !

Si vous lancez ce code avec Javascript, aucune erreur ne sera retournée. Et vous verrez apparaître dans la console le message suivant : "Vous habitez en dehors de la France" (ce qui peut être vrai … ou totalement faux !).

Par contre, avec TypeScript, on constate l'erreur au moment de la compilation, c'est à dire, avant l'exécution du programme. Du coup, en TS, voici ce que nous aurions :

// TypeScript
const utilisateur = {};
if(utilisateur.habite_en_France) // <----------- signalement d'erreur Typescript :    Property 'habite_en_France'
  console.log("Vous habitez en France !"); //                                         does not exist on type '{}'.
else
  console.log("Vous habitez en dehors de la France.");

Ici, on a donc bien une erreur identifiée par TypeScript, là où Javascript continuait l'exécution de son code, sur la base d'informations potentiellement fausses !

Arguments de fonction mal passés

Il faut savoir que, lorsqu'on fait appel à une fonction préalablement définie, JS ne vérifie pas si les entrées (paramètres) sont cohérentes. Or cela peut entraîner des bugs par la suite (bugs qui sont parfois subtils et difficiles à identifier !).

Alors, pour vous illustrer cela, voici un exemple de code JS, simple, avec une erreur dedans (si vous regardez de près, vous devriez la repérer avec que je vous dise où elle se trouve !) :

// JavaScript
function afficherInfosUtilisateur(prenom, age, sexe) {
  console.log(`L'utilisateur ${prenom} a ${age} ans ; il est de sexe ${sexe}.`);
}
afficherInfosUtilisateur("Raphaël", "masculin", 45);

Et voici ce que retourne la console Javascript, après exécution de ce code : "L'utilisateur Raphaël a masculin ans ; il est de sexe 45.". Autrement dit, ça ne veut rien dire ! Et effectivement, si l'on examine le code de plus près, on s'aperçoit vite d'où vient l'erreur : l'ordre des paramètres dans l'appel de fonction afficherInfosUtilisateur("Raphaël", "masculin", 45) est incorrect (car il fallait passer en argument, et dans cet ordre, le prénom, puis l'âge, puis le sexe !). En clair, il aurait fallut écrire les choses de cette manière : afficherInfosUtilisateur("Raphaël", 45, "masculin") ; mais bon, Javascript ne bronche pas, malheureusement 😉

Là encore, avec TS, ce genre d'erreur aurait été détecté dès la compilation. Car en ayant permuté l'âge et le sexe, on a en fait permuté une valeur numérique avec une valeur texte. Et ça, TypeScript l'aurait immédiatement repéré ! Pour "preuve", encore une fois :

// TypeScript
function afficherInfosUtilisateur(prenom: string, age: number, sexe: string) {
  console.log(`L'utilisateur ${prenom} a ${age} ans ; il est de sexe ${sexe}.`);
}
afficherInfosUtilisateur("Raphaël", "masculin", 45); // <-------- Argument of type 'string' is not assignable
//                                   ^^^^^^^^                     to parameter of type 'number'.

Vous noterez au passage un exemple de typage TS, au niveau des entrées (paramètres) de cette fonction. Ici, vous noterez que :

  • "prenom: string" signifie que la variable "prenom" ne pourra contenir qu'une chaîne de caractères
  • "age: number" signifie que la variable "age" ne pourra contenir qu'une valeur numérique
  • "sexe: string" signifie que la variable "sexe" ne pourra contenir qu'une chaîne de caractères

Cela permet au compilateur TypeScript d'immédiatement relever l'erreur de type, à l'appel de la fonction afficherInfosUtilisateur, où le paramètre age reçoit la valeur "masculin" ! Il sait donc à ce moment là qu'il y a une erreur au niveau du code, et le signale clairement. Ainsi, on évite les absurdités affichées par JS, en typant les variables avec TS 🙂

Exemple de mélange de types contrôlés par TypeScript, ici du type string vers le type number, en paramètre de fonction TS avec typage

Cas d’usages concrets (avantages à utiliser TypeScript)

Au-delà de la détection d'erreurs, TypeScript permet d'encadrer les choses, ce qui aide grandement au travail collaboratif. Voici quelques cas d'usage très parlants, illustrant l'atout que représente TypeScript, dans les développements réalisés à plusieurs !

Projets d’équipe

Quand plusieurs programmeurs collaborent ensemble, TypeScript peut permettre de définir un cadre de travail clair, et bien défini. Par exemple, on peut utiliser des "interfaces" (des structures définissant le type de données qu'on attend) pour définir ce que doit retourner tel ou tel objet, classe, API, ou autre.

// Déclaration de la structure d'un "Produit"
interface Produit {
  id: number;
  nom: string;
  prix: number;
}

// Création d'une fonction qui nous permettra d'afficher le prix d'un produit passé en paramètre
function afficherPrixProduit(produit: Produit) {
  console.log(`${produit.nom} = ${produit.prix}€`);
}

Ici, le fait d'utiliser une interface pour caractériser un "Produit" permet de cadrer les choses ; ainsi, on saura que le produit passé en entrée (paramètre) de fonction sera bien typé (c'est à dire qu'il aura bien un id, un nom, et un prix). Du coup, on sera certain que si on utilise la fonction afficherPrixProduit(produit: Produit) avec tel ou tel produit, fidèle à l'interface "Produit", tout le code se déroulera bien !

On teste ensemble, pour vérifier que tout soit cohérent en sortie :

// Définition de produits (par exemple… des fruits !), en respectant l'interface "Produit"
const maPommeGolden: Produit = {
    id: 1,
    nom: "Pomme golden",
    prix: 0.97
};

const monCitronVert: Produit = {
    id: 2,
    nom: "Citron vert",
    prix: 2.13
};

// Et appel de la fonction précédemment créée, en passant en paramètre un de nos produits
afficherPrixProduit(monCitronVert);

Après compilation TypeScript, la console retourne : "Citron vert = 2.13€". Donc tout est ok, côté transmission de paramètres ! Et s'il avait manqué la moindre propriété, comme l'id, par exemple, TS aurait signalé une erreur !

Frameworks modernes

Les frameworks modernes tels que React, Angular, et Vue.js, par exemple, adorent TypeScript. Avec React, par exemple, typer les props (arguments d'éléments) évite facilement les erreurs de typage ou manque de paramètres, en cadrant les choses dès la source.

Voici un exemple de fonction React, avec son "interface" TypeScript associée, définissant les arguments attendus en "props" :

// Interface
interface CustomNumericInputInterface {
  unique_id: string
  input_classname?: string
  value: string
  returnInputValue(value: string): any
  autoComplete?: string
  disabled?: boolean
  placeholder?: string
}

// Élément
const CustomNumericInput = (props: CustomNumericInputInterface) => {
...
}

Ici, vous remarquez que l'élément "CustomNumericInput" attend en propriété un argument structuré de la manière définie par "CustomNumericInputInterface". Ainsi, aucun risque d'avoir des paramètres manquants (au niveau de ceux qui sont obligatoires), ni d'erreur de typage avec TypeScript, car tout est cadré et défini par avance !

Nota : juste pour votre culture, les propriétés définies avec un "?" à la fin indique qu'ils sont optionnels. En clair, si props ne contient pas la propriété "input_classname", par exemple, il n'y a aucun soucis. Par contre, les autres propriétés "sans ?" sont obligatoirement requises (comme unique_id, par exemple).

Intégration d’APIs

Par ailleurs, le typage de réponses d’API avec TypeScript permet de préciser le type de données reçues, si tout s'est bien passé. Par exemple :

interface ReponseAPI {
  id: number;
  titre: string;
}

fetch("https://api.exemple.com")
  .then(reponse => reponse.json() as Promise<ReponseAPI>);

Ici, on précise que "reponse" sera un objet, typé avec 2 propriétés : un id numérique (number), et un titre au format texte (string).

Conclusion

À travers tous les exemples que je vous ai partagé dans cet article, vous devinez certainement à quoi sert TypeScript ! En clair, il sert à rendre son code plus sûr, en anticipant d'éventuelles erreurs (undefined, mauvais types, etc.), et à structurer ses projets (qu'ils soient petits ou grands, d'ailleurs !). En bref : c’est un allié pour coder sérieusement. Alors ne passez pas à côté 😉

Du reste, si vous souhaitez m'aider à produire plus de contenu sur LeCoinTS, n'hésitez pas à m'offrir un café ! (en cliquant sur le bouton jaune ci-dessous). Merci !

Merci d’avoir lu cet article ! LeCoinTS reste gratuit et sans pub grâce à vous.
Un petit don pour soutenir le site ? ☕

Offrez moi un café LeCoinTS
Site LeCoinTS.fr

JEROME

Passionné par tout ce qui touche à la programmation informatique en TypeScript, sans toutefois en être expert, j'ai à coeur de vous partager ici, peu à peu, tout ce que j'ai appris, découvert, réalisé, et testé jusqu'à présent ! En espérant que tout cela puisse vous servir, ainsi qu'au plus grand nombre de francophones possible !

(*) Mis à jour le 13/04/2025

Laisser un commentaire

Votre adresse e-mail ne sera pas publiée. Les champs obligatoires sont indiqués avec *

Résolvez cette soustraction :

63 - ____ = 57

Soutenir LeCoinTS

×

Soutenez le site LeCoinTS en offrant un café symbolique, afin que celui-ci reste 100% gratuit et sans pub, et pour me motiver à faire d'autres articles !
1 café = 5 € environ
Plusieurs cafés = au top !!!

→ Via Logo PayPal
Soutenir avec PayPal
→ Via Logo Stripe
Soutenir avec Stripe
Merci à vous ❤️