Skip to content

2.Concepts

TS & VS Code

  • Transpilation
    • 3 méthodes:
      • Via terminal intégré + commande tsc .ts [options]
      • Via terminal intégré + commande tsc sans fichiers ni options (s'appuie alors sur tsconfig.json)
        • Transpile tous les fichier *.ts du répertoire courant et sous répertoires
      • Via tâche de build VS Code intégrée: Ctrl+Shift+B
      • Via tâche de build VS code par défaut: F12
        • "group": { "kind": "build", "isDefault": true, }
    • tsconfig.json:
      • Contient les spécifications des options de transpilation
      • tsc --init pour créer un fichier par défaut
  • Debugging:
    • Paramétrer le fichier de config du debugger "Launch.json":
      • Construit à la volée par VSCode si tsc lancé avec sourcemap puis lancement du debugger
      • Autrement le construire : Debugger > "Ouvrir launch.json" (roue crantée) + sauvegarder
      • Ajouter "preLaunchTask": "${defaultBuildTask}" pour transpiler systématiquement avant de lancer le debug
    • Mapping JS <-> TS :
      • Soit option --sourcemap de transpilation (+ fichiers à transpiler)
        • Ex: tsc test.ts --sourcemap
      • Soit objet sourceMap du fichier tsconfig.json (sans indiquer de fichier)
        • Ex: tsc
    • Ctrl + Shift + M : ouvre la fenêtre des problèmes
  • IntelliSense
    • Fournit via TypeScript service dans VS Code
    • TypeScript version & location used by VS Code présent dans la status bar lors de visu fichier ts

Exemple de config

  • .vscode/launch.json:
{
    // Utilisez IntelliSense pour en savoir plus sur les attributs possibles.
    // Pointez pour afficher la description des attributs existants.
    // Pour plus d'informations, visitez : https://go.microsoft.com/fwlink/?linkid=830387
    "version": "0.2.0",
    "configurations": [
        {
            "type": "node",
            "request": "launch",
            "name": "Lancer le programme",
            "program": "${workspaceFolder}/index.ts",
            "preLaunchTask": "${defaultBuildTask}",
            "env": {
                "HTTP_PORT": "8080"
            },
            "outFiles": [
                "${workspaceFolder}/**/*.js"
            ]
        }
    ]
}
  • .vscode/tasks.json:
{
// Consultez https://go.microsoft.com/fwlink/?LinkId=733558 
    // pour voir la documentation sur le format de tasks.json
    "version": "2.0.0",
    "tasks": [
        {
            "type": "typescript",
            "tsconfig": "tsconfig.json",
            "problemMatcher": [
                "$tsc"
            ],
            "group": {
                "kind": "build",
                "isDefault": true,
            }
        }
    ]
}
  • tsconfig.json:
{
  "compilerOptions": {
    "target": "es5",                          /* Specify ECMAScript target version: 'ES3' (default), 'ES5', 'ES2015', 'ES2016', 'ES2017', 'ES2018', 'ES2019' or 'ESNEXT'. */
    "module": "commonjs",                     /* Specify module code generation: 'none', 'commonjs', 'amd', 'system', 'umd', 'es2015', or 'ESNext'. */
    "sourceMap": true,                     /* Generates corresponding '.map' file. */
    "outDir": "out",                        /* Redirect output structure to the directory. */
    "strict": true,                           /* Enable all strict type-checking options. */
    "esModuleInterop": true,                  /* Enables emit interoperability between CommonJS and ES Modules via creation of namespace objects for all imports. Implies 'allowSyntheticDefaultImports'. */
    "forceConsistentCasingInFileNames": true  /* Disallow inconsistently-cased references to the same file. */
  }
}

TS & Node.js

  • Ne sait lancer qu'un fichier js:
    • TypeScript: compile en JS donc pas de problème
    • Spécifier l'entry point dans package.json
  • Librairies NPM:
    • Installer la lib npm: npm install --save
    • Install la même lib pour TS: npm install --save-dev @types/
      • Si elle existe !
    • Pour les lib natives node.js: npm install --save-dev @types/node

Types

  • Built-in Types:
    • Same types as with JavaScript: Boolean, Number, String, Array, null, undefined, Object
    • let <nom var>: <type> [= <value>];
    • Template String:
      • Permet d'utiliser des variables, la valeur est inséré au runtime: xxx ${nomVar} yyyy;
      • Permet de définir des string en multi lignes
    • Tuple:
      • let <nom var>: [<type 1>, <type 2>];
      • var[0] est de type 1
      • var[1] est de type 2
    • Enum:
      • enum <nom> { <label> }
      • Indice de début à 0, possible de surcharger : <label> = <indice>, …
      • Possible également de surcharger l'indice d'un label à n'importe quel moment
      • Lire le libellé d'une valeur <nom enum>[<indice>]
    • any:
      • Type polymorphique, peut prendre n'importe quel type
      • Est défini au moment du runtime
    • void:
      • Pour type retour fonction/interface
    • never:
      • Type pour les fonctions qui ne retournent jamais quelque chose / qui déclanchent une exception
    • Type assertion:
      • Equivalent d'un cast
      • Uniquement une "vue" de la mémoire différente, ne modifie pas la donnée mémoire elle-même
      • <type>(<var>);
  • Type Inference:
    • Used to provide type information
    • Best common type algorithm utilisé pour déterminer le type des variables au runtime lorsque celui-ci n'est pas explicite
    • Contextual typing: when the type of an expression is implied by its location
      • Possible de désactiver avec le flag de compilation --noImplicitAny
  • Type Compatibility:
    • Based on structural subtyping (= se base sur les membres)
    • x is compatible with y if y has at least the same members as x

Declarations

  • Variables:
    • let
    • const:
      • La variable ne peut plus changer de valeur
      • Si c'est un objet:
        • La valeur des propriétés peut changer
        • La structure de l'objet ne peut pas changer (pas d'ajout / suppression de propriétés)
  • Interfaces:
    • Le compilateur vérifie que les propriétés déclarée dans une interface sont bien définies dans un object
    • Optional property : <prop name>?: <prop type>;
    • Read only property:
      • Assignable uniquement à la création
      • readonly <prop name>: <prop type>;
    • Utilisation:
      • class <nom classe> implements <nom interface> [, <nom interface>] { … }
    • Définition:
interface <nom> [extends <nom> [, <nom>]]
{
    // Properties
    <prop name>: <prop type>;

    // Methods
    <method name>(<params>): <return type>
}
  • Classes:
    • Visibilité:
      • Chaque membre est public par défaut
      • Visibilité private & protected = comme les autres languages objets
      • Constructeur protected : pour empêcher une classe d'être instancié sans passer par une classe dérivée
    • Read only property:
      • Assignable uniquement à déclaration ou bien dans le constructeur
      • readonly <prop name>: <prop type>;
    • Membre static:
      • Est attaché au type plutôt qu'à l'instance
      • N'est pas const par défaut !! Mais peut l'être
    • Classe abstraite:
      • Pour classe de base sans autoriser l'instanciation
      • Pour également imposer une implémentation dans les classes dérivées
    • Utilisation:
      • let obj : <nom classe> = new <nom classe>(<args>);
    • Définition:
class <nom> [extends <nom> [, <nom>]]
{
    // Properties
    <visibility> <prop name>: <prop type>;

    // Get/Setters
    private _var: Number;
    get var(): Number { return this._var; }
    set var(val: Number) { this._var = val; }

    // Methods
    <visibility> constructor(<params>)
    {
        [super([<params>])] // si héritage
    }

    // Surcharge : redéfinition d'une méthode de classe de base
    <visibility> <nom methode> (<params>): <return type>
    {
        // Appel méthode mère : pas obligatoire !
        super.<nom methode>(<params>);
    }
}

// Classe abstraite
abstract <nom>
{
    // Méthode abstraite
    abstract <nom methode>(): <type>;

    // Méthode réelle
    private test(): void { … }
}
  • Functions:
    • Every parameter is assumed to be required by the function (in JavaScript, every parameter is optional)
    • Paramètre optionnel en TS : ?
    • Initialized param: <nom arg>: <type> = <value>
  • Generics:
    • Generic Function:
      • Composant capable d'apporter des fonctionnalités communes sur différents types d'objets
      • Utiliser type variable: function <name><T>(v: T) { … }
      • Appel de la fonction:
        • En passant le type directement
        • En laissant le compilateur deviner le type (inférence)
    • Generic Type:
      • En passant par une interface:
        • En déclarant une interface avec type générique
        • Cette interface déclare la signature des fonctions qu'elle propose
      • En passant par une classe:
        • En déclarant une classe avec type générique
        • Les méthodes s'appuient sur le type passé en paramètre
    • Extension:
      • En général il faut déclarer une interface avec les propriétés attendues dans l'implem
      • Ensuite utiliser un generic type qui peut etendre cette interface: function <name><T extends interf>(…)
  • Enum:
    • Numeric ou string-based
      • String-based : chaque clé doit être explicitement initialisée
      • Numeric : peut être initialisé depuis une expression TS (ex: retour de fonction)
    • Démarre à 0 par défault
  • Namespaces:
    • Permet de regrouper des définition sous un objet chapeau pour éviter les collisions de noms
    • Le namespace doit explicitement exporter les définitions / objets qui doivent être accessibles
    • Namespace multi fichiers:
      • Dans les fichiers "enfants" il faut préciser quel est le fichier "père"
      • /// <reference path="nom_fichier.ts" />
      • Compilation en fichier unique: tsc --outFile fichier1.ts fichier2.ts etc…
  • Modules:
    • Les objets & déclarations sont privés sauf si explicitement exporté (export)
    • Relationships between modules are specified in terms of imports and exports at the file level
    • Un module doit être importé pour être utilisé:
      • Résolution au runtime
      • Loader par défaut:
        • CommonJS pour Node.js
        • RequireJS pour les navigateurs
    • Tout fichier qui comporte un import ou export au début est considéré comme un module
    • Les fichiers qui n'en ont pas sont ajouté au scope global
    • Syntaxe:
      • Export: export <définition / déclaration>
      • Import:
        • import { <nom définition ou déclaration exportés> [as <new name>] } from <chemin>;
        • Import * as <nom var> from <chemin>;
    • NE PAS UTILISER DE NAMESPACE AVEC LES MODULES : car cela ajoute très peu de valeur
      • Les modules sont natif à JS depuis ECMAScript 2015