web-dev-qa-db-fra.com

Qu'est-ce que TypeScript et pourquoi devrais-je l'utiliser à la place de JavaScript?

Pouvez-vous s'il vous plaît décrire ce qu'est le langage TypeScript?

Que peut-il faire que JavaScript ou les bibliothèques disponibles ne peuvent pas faire, cela me donnerait une raison de le considérer?

1579
Mohammed Thabet

A l'origine, j'avais écrit cette réponse quand TypeScript était encore à chaud. Cinq ans plus tard, c'est un bon aperçu, mais regardez réponse de Lodewijk ci-dessous pour plus de détails.

Vue de 1000 pieds ...

TypeScript est un sur-ensemble de JavaScript qui fournit principalement du typage statique optionnel, des classes et des interfaces. L'un des principaux avantages est de permettre aux IDE de fournir un environnement plus riche pour détecter les erreurs courantes lors de la saisie du code .

Pour avoir une idée de ce que je veux dire, regardez vidéo d'introduction de Microsoft sur la langue.

Pour un grand projet JavaScript, l’adoption de TypeScript peut donner lieu à un logiciel plus robuste, tout en restant déployable là où une application JavaScript normale serait exécutée.

C'est une source ouverte, mais vous n'obtenez l'intelligent Intellisense au fur et à mesure que vous tapez si vous utilisez un IDE pris en charge. À l’origine, il s’agissait uniquement de Visual Studio de Microsoft (également noté dans l’article de blog de Miguel de Icaza ). De nos jours, d'autres IDE offrent aussi le support TypeScript .

Existe-t-il d'autres technologies similaires?

Il y a CoffeeScript , mais cela sert vraiment un but différent. IMHO, CoffeeScript fournit la lisibilité pour les humains, mais TypeScript fournit également une lisibilité profonde pour les outils via son typage statique optionnel (voir ceci article de blog récent pour un peu plus de critique). Il y a aussi Dart mais c'est un remplacement complet de JavaScript (même si peut produire du code JavaScript )

Exemple

À titre d’exemple, voici un peu de TypeScript (vous pouvez jouer avec cela dans le TypeScript Playground )

class Greeter {
    greeting: string;
    constructor (message: string) {
        this.greeting = message;
    }
    greet() {
        return "Hello, " + this.greeting;
    }
}  

Et voici le code JavaScript que cela produirait

var Greeter = (function () {
    function Greeter(message) {
        this.greeting = message;
    }
    Greeter.prototype.greet = function () {
        return "Hello, " + this.greeting;
    };
    return Greeter;
})();

Notez que TypeScript définit le type des variables membres et des paramètres de méthode de classe. Ceci est supprimé lors de la traduction en JavaScript, mais utilisé par le IDE et le compilateur pour détecter les erreurs, comme le fait de passer un type numérique au constructeur.

Il est également capable d'inférer des types qui ne sont pas explicitement déclarés. Par exemple, il déterminerait que la méthode greet() renvoie une chaîne.

Débogage TypeScript

De nombreux navigateurs et IDE offrent une prise en charge directe du débogage via des cartes sources. Consultez cette question de débordement de pile pour plus de détails: Débogage de code TypeScript avec Visual Studio

Veut en savoir plus?

A l'origine, j'avais écrit cette réponse quand TypeScript était encore à chaud. Départ réponse de Lodewijk à cette question pour des détails plus actuels.

1228
Paul Dixon

Bien que la réponse acceptée soit correcte, j’ai pensé que cela ne rendait vraiment pas justice à TypeScript à ce stade. Ce n'est plus les débuts. TypeScript est de plus en plus adopté avec plusieurs frameworks populaires écrits en TypeScript. Les raisons pour lesquelles vous devriez choisir TypeScript au lieu de JavaScript sont nombreuses maintenant.

Relation à JavaScript

TypeScript est JavaScript + types modernes. Il s'agit de détecter les bogues tôt et de faire de vous un développeur plus efficace, tout en tirant parti de la communauté JavaScript.

JavaScript est normalisé selon les normes ECMAScript. Les anciens navigateurs ne supportent pas toutes les fonctionnalités des nouvelles normes ECMAScript (voir this table ). TypeScript prend en charge les nouvelles normes ECMAScript et les compile en cibles (plus anciennes) ECMAScript de votre choix (les cibles actuelles sont 3, 5 et 6 [a.k.a. 2015]). Cela signifie que vous pouvez utiliser les fonctionnalités d'ES2015 et au-delà, telles que les modules, les fonctions lambda, les classes, l'opérateur d'étalement et la déstructuration, tout en restant compatible avec les anciens navigateurs.

La prise en charge des types ne fait pas partie de la norme ECMAScript et pourrait ne jamais être due à la nature interprétée plutôt qu'à la nature compilée de JavaScript. Le système de types de TypeScript est incroyablement riche et comprend: des interfaces, des énumérations, des types hybrides, des génériques, des types d'union/intersection, des modificateurs d'accès et bien plus encore. Le site officiel de TypeScript donne un aperçu de ces fonctionnalités. Le système de types de TypeScript est aujourd'hui à égalité avec les autres langages typés et, dans certains cas, sans doute plus puissant.

Relation avec d'autres langues de ciblage JavaScript

TypeScript a une philosophie unique comparée à d'autres langages compilant JavaScript. Le code JavaScript est un code TypeScript valide. TypeScript est un sur-ensemble de JavaScript. Vous pouvez presque renommer vos fichiers .js en .ts et commencer à utiliser TypeScript (voir "Interopérabilité de JavaScript" ci-dessous). Les fichiers TypeScript sont compilés en JavaScript lisible, de sorte que la migration est possible et que la compréhension de TypeScript compilé n’est pas du tout difficile. TypeScript s'appuie sur les succès de JavaScript tout en améliorant ses faiblesses.

D'une part, vous avez des outils évolutifs qui reprennent les normes ECMAScript modernes et les compilent dans des versions JavaScript plus anciennes, Babel étant la plus populaire. D'autre part, vous avez des langages qui peuvent totalement différer de JavaScript qui cible JavaScript, comme CoffeeScript, Clojure, Dart, Orme, Haxe, Scala.js, et tout un hôte en plus (voir this liste ) . Ces langues, bien qu’elles soient meilleures que celles auxquelles l’avenir de JavaScript pourrait être destiné, risquent davantage de ne pas être adoptées suffisamment pour que leur avenir soit garanti. Vous pourriez également avoir plus de difficulté à trouver des développeurs expérimentés pour certaines de ces langues, même si celles que vous rencontrerez sont souvent plus enthousiastes. L'interopérabilité avec JavaScript peut également être un peu plus complexe, car ils sont plus éloignés de ce que JavaScript est en réalité.

TypeScript se situe entre ces deux extrêmes, équilibrant ainsi le risque. TypeScript n'est pas un choix risqué selon toutes les normes. Il faut très peu d’efforts pour s’y habituer si vous êtes familiarisé avec JavaScript, car ce n’est pas un langage complètement différent, il offre une excellente prise en charge de l’interopérabilité de JavaScript et il a été adopté beaucoup récemment.

Typage statique et inférence de type éventuellement

JavaScript est typé dynamiquement. Cela signifie que JavaScript ne sait pas quel type de variable est jusqu'à ce qu'elle soit réellement instanciée au moment de l'exécution. Cela signifie également qu'il est peut-être trop tard. TypeScript ajoute le support de type à JavaScript. Les bugs causés par de fausses suppositions relatives à une variable d'un certain type peuvent être complètement supprimés si vous jouez correctement les cartes (la précision avec laquelle vous tapez votre code ou si vous tapez votre code dépend de vous).

TypeScript rend la saisie un peu plus facile et beaucoup moins explicite par l'utilisation de l'inférence de type. Par exemple: var x = "hello" dans TypeScript est identique à var x : string = "hello". Le type est simplement déduit de son utilisation. Même si vous ne tapez pas explicitement les types, ils sont toujours là pour vous éviter de faire quelque chose qui, sinon, résulterait en une erreur d'exécution.

TypeScript est éventuellement saisi par défaut. Par exemple, function divideByTwo(x) { return x / 2 } est une fonction valide dans TypeScript qui peut être appelée avec n’importe quel type de paramètre , même si l’appel avec une chaîne est évident. entraîner une erreur d'exécution . Tout comme vous êtes habitué à JavaScript. Cela fonctionne car, quand aucun type n'était explicitement attribué et que le type ne pouvait pas être déduit, comme dans l'exemple divideByTwo, TypeScript affectera implicitement le type any. Cela signifie que la signature de type de la fonction divideByTwo devient automatiquement function divideByTwo(x : any) : any. Un indicateur du compilateur interdit ce comportement: --noImplicitAny. L'activation de ce drapeau augmente le niveau de sécurité, mais vous oblige également à taper davantage.

Les types ont un coût qui leur est associé. Tout d’abord, il ya une courbe d’apprentissage, et deuxièmement, bien sûr, il vous faudra un peu plus de temps pour mettre en place une base de code en utilisant également une frappe correcte. D'après mon expérience, ces coûts en valent totalement la peine pour toute base de code sérieuse que vous partagez avec d'autres. ne étude à grande échelle des langages de programmation et de la qualité de code dans Github suggère que "les langages statiques, en général, sont moins sujets aux défauts que les types dynamiques, et que le typage vaut mieux que le typage faible dans le même sens ".

Il est intéressant de noter que ce même papier constate que TypeScript est moins sujet aux erreurs que JavaScript:

Pour ceux qui ont des coefficients positifs, on peut s’attendre à ce que la langue soit associée, ceteris paribus, à un plus grand nombre de corrections de défauts. Ces langages incluent C, C++, JavaScript , Objective-C, Php et Python. Les langages Clojure, Haskell, Ruby, Scala et TypeScript ont tous des coefficients négatifs, ce qui implique que ces langages sont moins susceptibles que la moyenne d’entraîner une correction des anomalies. commet.

Prise en charge améliorée de IDE

L'expérience de développement avec TypeScript représente une amélioration considérable par rapport à JavaScript. Le IDE est informé en temps réel par le compilateur TypeScript de ses informations de type riche. Cela donne quelques avantages majeurs. Par exemple, avec TypeScript, vous pouvez effectuer en toute sécurité des refactorisations telles que les renommages de votre base de code entière. En complétant le code, vous pouvez obtenir une aide en ligne sur les fonctions qu'une bibliothèque peut offrir. Plus besoin de vous en souvenir ni de les consulter dans des références en ligne. Les erreurs de compilation sont signalées directement dans IDE avec une ligne ondulée rouge pendant que vous êtes en train de coder. Au total, cela permet un gain de productivité significatif par rapport à l'utilisation de JavaScript. On peut passer plus de temps à coder et moins de temps à déboguer.

Un grand nombre d'EDI offrant un excellent support pour TypeScript, tels que Code Visual Studio, WebStorm, Atom et Sublime.

Contrôles nuls stricts

Les erreurs d'exécution de la forme cannot read property 'x' of undefined ou undefined is not a function sont très souvent causées par des bogues dans le code JavaScript. TypeScript prêt à l'emploi réduit déjà la probabilité de ce type d'erreur, car il est impossible d'utiliser une variable inconnue du compilateur TypeScript (à l'exception des propriétés des variables typées any). Il est toujours possible d'utiliser par erreur une variable définie sur undefined. Cependant, avec la version 2.0 de TypeScript, vous pouvez éliminer ces types d’erreurs en utilisant des types non nullables. Cela fonctionne comme suit:

Lorsque les vérifications de null stricte sont activées (indicateur de compilateur --strictNullChecks), le compilateur TypeScript n'autorisera pas l'affectation de undefined à une variable, à moins que vous ne le déclariez explicitement comme étant de type nullable. Par exemple, let x : number = undefined entraînera une erreur de compilation. Cela correspond parfaitement à la théorie des types car undefined n'est pas un nombre. On peut définir x comme un type somme de number et undefined pour corriger ceci: let x : number | undefined = undefined.

Une fois qu'un type est connu comme pouvant être nullable, c'est-à-dire qu'il a un type qui peut également être de la valeur null ou undefined, le compilateur TypeScript peut déterminer par l'analyse de type basée sur le flux de contrôle si votre code peut utiliser en toute sécurité une variable ou non. En d'autres termes, lorsque vous vérifiez qu'une variable est undefined par le biais, par exemple, d'une instruction if, le compilateur TypeScript déduira que le type figurant dans cette branche du flux de contrôle de votre code n'est plus nullable et peut donc être utilisé en toute sécurité. . Voici un exemple simple:

let x: number | undefined;
if (x !== undefined) x += 1; // this line will compile, because x is checked.
x += 1; // this line will fail compilation, because x might be undefined.

Lors de la construction, le co-concepteur de TypeScript Anders Hejlsberg lors de la conférence 2016 a donné une explication détaillée et une démonstration de cette fonctionnalité: video (de 44h30 à 56h30).

Compilation

Pour utiliser TypeScript, vous avez besoin d'un processus de construction pour compiler en code JavaScript. Le processus de construction ne prend généralement que quelques secondes, selon la taille de votre projet. Le compilateur TypeScript prend en charge la compilation incrémentielle (indicateur de compilation --watch) afin que toutes les modifications ultérieures puissent être compilées à une vitesse supérieure.

Le compilateur TypeScript peut intégrer des informations de mappage source dans les fichiers .js générés ou créer des fichiers .map distincts. Les informations de carte source peuvent être utilisées par des utilitaires de débogage tels que Chrome DevTools et d'autres IDE pour associer les lignes du code JavaScript à celles qui les ont générées dans TypeScript. Cela vous permet de définir des points d'arrêt et d'inspecter des variables pendant l'exécution directement sur votre code TypeScript. Les informations de carte source fonctionnent assez bien, cela remonte bien avant TypeScript, mais le débogage de TypeScript n’est généralement pas aussi performant que lors de l’utilisation directe de JavaScript. Prenez le mot clé this par exemple. En raison de la sémantique modifiée du mot clé this autour des fermetures depuis ES2015, il est possible que this existe réellement pendant l'exécution à titre de variable appelée _this (voir cette réponse ). Cela peut vous dérouter pendant le débogage, mais ce n’est généralement pas un problème si vous le connaissez ou si vous inspectez le code JavaScript. Il convient de noter que Babel souffre exactement du même type de problème.

Le compilateur TypeScript peut effectuer quelques autres astuces, telles que la génération de code d'interception basé sur décorateurs , la génération de code de chargement de module pour différents systèmes de modules et l'analyse JSX . Cependant, vous aurez probablement besoin d'un outil de génération en plus du compilateur TypeScript. Par exemple, si vous voulez compresser votre code, vous devrez pour cela ajouter d’autres outils à votre processus de construction.

Il existe des plugins de compilation TypeScript disponibles pour Webpack , Gulp , Grunt et à peu près n'importe quel autre outil de construction JavaScript. La documentation TypeScript contient une section sur intégration avec les outils de construction qui les couvre tous. Un linter est également disponible au cas où vous souhaiteriez encore plus de vérification du temps de construction. Il existe également un grand nombre de projets de départ qui vous initieront à l'utilisation de TypeScript en combinaison avec une foule d'autres technologies telles que Angular 2, React, Ember, SystemJS, Webpack, Gulp, etc.

Interopérabilité JavaScript

Puisque TypeScript est si étroitement lié à JavaScript, il offre d'excellentes capacités d'interopérabilité. Toutefois, un travail supplémentaire est nécessaire pour travailler avec les bibliothèques JavaScript dans TypeScript. Les définitions TypeScript sont nécessaires pour que le compilateur TypeScript comprenne que les appels de fonction tels que _.groupBy ou angular.copy ou $.fadeOut ne sont pas des instructions illégales. Les définitions de ces fonctions sont placées dans des fichiers .d.ts.

La définition la plus simple qu'une définition puisse prendre consiste à permettre à un identificateur d'être utilisé de quelque manière que ce soit. Par exemple, lorsque vous utilisez Lodash , un fichier de définition de ligne unique declare var _ : any vous permettra d’appeler n’importe quelle fonction de votre choix sur _, mais vous resterez bien entendu également actif. capable de faire des erreurs: _.foobar() serait un appel TypeScript légal, mais est bien entendu un appel illégal au moment de l'exécution. Si vous voulez que le type et le code soient corrects, votre fichier de définition doit être plus précis (voir définitions de lodash pour un exemple).

Les modules Npm fournis avec leurs propres définitions de type sont automatiquement compris par le compilateur TypeScript (voir documentation ). Pour à peu près toutes les autres bibliothèques JavaScript semi-populaires qui n'incluent pas leurs propres définitions, quelqu'un a déjà rendu les définitions de types disponibles via un autre module npm. Ces modules sont préfixés par "@ types /" et proviennent d'un référentiel Github appelé DefinitelyTyped .

Il y a un inconvénient: les définitions de type doivent correspondre à la version de la bibliothèque que vous utilisez au moment de l'exécution. Si ce n'est pas le cas, TypeScript peut vous empêcher d'appeler une fonction ou de déréférencer une variable existante ou de vous permettre d'appeler une fonction ou de déréférencer une variable qui n'existe pas, tout simplement parce que les types ne correspondent pas à l'exécution au moment de la compilation . Assurez-vous donc de charger la bonne version des définitions de types pour la bonne version de la bibliothèque que vous utilisez.

Pour être honnête, cela pose quelques problèmes et c'est peut-être l'une des raisons pour lesquelles vous ne choisissez pas TypeScript, mais optez pour quelque chose comme Babel qui ne souffre pas de la nécessité d'obtenir des définitions de type. D'autre part, si vous savez ce que vous faites, vous pouvez facilement résoudre tout type de problème causé par des fichiers de définition incorrects ou manquants.

Conversion de JavaScript en TypeScript

Tous les fichiers .js peuvent être renommés en un fichier .ts et être exécutés via le compilateur TypeScript pour obtenir le même code JavaScript que le résultat (s'il était syntaxiquement correct au départ). Même lorsque le compilateur TypeScript rencontre des erreurs de compilation, il génère toujours un fichier .js. Il peut même accepter les fichiers .js en tant qu'entrée avec l'indicateur --allowJs. Cela vous permet de commencer immédiatement avec TypeScript. Malheureusement, des erreurs de compilation risquent de se produire au début. Il ne faut pas oublier que ce ne sont pas des erreurs révélatrices comme vous le faites peut-être avec d'autres compilateurs.

Les erreurs de compilation commises au début lors de la conversion d'un projet JavaScript en un projet TypeScript sont inévitables par nature. TypeScript vérifie tout le code pour en vérifier la validité. Il doit donc connaître toutes les fonctions et variables utilisées. Par conséquent, les définitions de types doivent être en place pour toutes, sinon des erreurs de compilation sont inévitables. Comme mentionné dans le chapitre ci-dessus, pour pratiquement tous les environnements JavaScript, il existe .d.ts fichiers pouvant être facilement acquis avec l’installation de paquets DefinitelyTyped . Cependant, il se peut que vous ayez utilisé une bibliothèque obscure pour laquelle aucune définition TypeScript n’est disponible ou que vous ayez créé une polyfilling de certaines primitives JavaScript. Dans ce cas, vous devez fournir des définitions de type pour ces bits pour que les erreurs de compilation disparaissent. Créez simplement un fichier .d.ts et incluez-le dans le tableau files du tsconfig.json, afin qu'il soit toujours pris en compte par le compilateur TypeScript. Dans ce document, déclarez ces bits inconnus de TypeScript comme type any. Une fois que vous avez éliminé toutes les erreurs, vous pouvez introduire progressivement la saisie en fonction de vos besoins.

Certains travaux sur la (re) configuration de votre pipeline de construction seront également nécessaires pour insérer TypeScript dans le pipeline de construction. Comme mentionné dans le chapitre sur la compilation, il existe de nombreuses ressources utiles et je vous encourage à rechercher des projets de développement qui combinent les outils avec lesquels vous souhaitez travailler.

Le principal obstacle est la courbe d'apprentissage. Je vous encourage à jouer avec un petit projet au début. Regardez comment cela fonctionne, comment il construit, quels fichiers il utilise, comment il est configuré, comment il fonctionne dans votre IDE, comment il est structuré, quels outils il utilise, etc. Convertir une grande base de code JavaScript en TypeScript est faisable quand vous le savez que fais tu. Lisez ce blog par exemple sur conversion de 600k lignes en TypeScript en 72 heures ). Assurez-vous simplement de bien maîtriser la langue avant de faire le saut.

Adoption

TypeScript est open-source (sous licence Apache 2, voir GitHub ) et soutenu par Microsoft. Anders Hejlsberg , l'architecte principal de C # est le fer de lance du projet. C'est un projet très actif. l'équipe TypeScript a publié de nombreuses nouvelles fonctionnalités ces dernières années et de nombreuses autres sont encore prévues (voir le roadmap ).

Dans le enquête auprès des développeurs de StackOverflow de 2017 , TypeScript était le transpiler JavaScript le plus populaire (9ème au total) et a remporté la troisième place dans la catégorie des langages de programmation les plus appréciés.

981
Lodewijk Bogaards

TypeScript fait quelque chose de similaire à ce que less ou sass fait pour CSS. Ce sont de super-ensembles, ce qui signifie que chaque code JS que vous écrivez est un code TypeScript valide. De plus, vous pouvez utiliser les autres goodies que cela ajoute à la langue, et le code transpilé sera valide js. Vous pouvez même définir la version de JS sur laquelle vous voulez que votre code résultant.

Actuellement, TypeScript est un super ensemble d'ES2015; il peut donc s'avérer un bon choix pour commencer à apprendre les nouvelles fonctionnalités de js et à les transpiler selon les normes requises par votre projet.

75
lebobbi

"Notions fondamentales sur TypeScript" - un cours vidéo Pluralsight de Dan Wahlin et John Papa est un très bon moment (mars 25, 2016) mis à jour pour refléter TypeScript 1.8, introduction à TypeScript.

Pour moi, les très bonnes caractéristiques, outre les possibilités de Nice pour intellisense, sont les classes, interfaces, modules, la facilité d'implémentation d'AMD, et la possibilité d'utiliser le débogueur Visual Studio TypeScript lorsqu'il est appelé avec IE.

Pour résumer : S'il est utilisé comme prévu, TypeScript peut rendre la programmation JavaScript plus fiable et plus facile. Il peut augmenter considérablement la productivité du programmeur JavaScript par rapport au SDLC complet.

40
Dimitre Novatchev

Ecma script 5 (ES5) supporté par tous les navigateurs et précompilé. ES6/ES2015 et ES/2016 ont été introduits cette année avec de nombreux changements. Par conséquent, pour que ces modifications apparaissent, il y a quelque chose entre les deux qui devrait prendre en compte le typeScript.

• TypeScript is Types -> signifie que nous devons définir le type de données de chaque propriété et méthode. Si vous connaissez C #, alors TypeScript est facile à comprendre.

• Le gros avantage de TypeScript est que nous identifions les problèmes liés aux types très tôt avant de passer en production. Cela permet aux tests unitaires d’échouer s’il existe une incompatibilité de type.

13
Mayank Jain