typescript tips & tricks

Download Typescript tips & tricks

Post on 21-Jan-2018

211 views

Category:

Software

0 download

Embed Size (px)

TRANSCRIPT

  1. 1. TYPESCRIPT TIPS & TRICKS Ori Calvo, 2017 oric@trainologic.com https://trainologic.com
  2. 2. 2 Objectives 2017 Ori Calvo 2 Cover all the good to know details about Typescript This is not an introduction session
  3. 3. 3 The Challenge 2017 Ori Calvo 3 Write today modern JavaScript code Even before browsers support that Solution: Compiler ESX ES5 Alternatives Typescript Babel CoffeeScript Traceur
  4. 4. 4 Getting Started 2017 Ori Calvo 4 npm install typescript Write some Typescript code Compile it with node_modules/.bin/tsc Run the generated JavaScript Use source map to debug the TypeScript
  5. 5. 5 Good to Know 2017 Ori Calvo 5 Partial typeDecoratorsBarrelHow does import/export work Down-level support for async/await Down-level generator support User defined type guard union/intersecti on type String EnumsCreate NPM package --initstrictNullChecksstrict master option Generic parameter defaultModule augmentations --declarationTyped map using object object typeMixincheckJs & allowJs noImplicitAnyUntyped importstslibObject spread & restkeyof Return value from ctor Configuration Inheritance --alwaysStrictType guardsNon null assertion nevertype of thisGlob Supportpaths--traceResolution Wildcard module name script vs. module--lib--noUnusedXXXWhy use target es5 with module es6 Trailing commas
  6. 6. 6 script vs. module 2017 Ori Calvo 6 Only files which use the import/export syntax are considered modules Other are considered plain scripts Module does not pollute the global scope Script does
  7. 7. 7 script vs. module 2017 Ori Calvo 7 Below code does not work Remove the export keyword and code compiles successfully export function xxx() { } interface Contact { id: number; name: string; } var x: Contact = { id: 1, name: "Ori", };
  8. 8. 8 import/export 2017 Ori Calvo 8 export function run() { console.log("run"); } import {run} from "./module1"; run(); import * as module1 from "./module1"; module1.run();
  9. 9. 9 import/export 2017 Ori Calvo 9 Part of ECMAScript 2015 No easy way to support under ES5 Must select a module standard amd commonjs umd es2015
  10. 10. 10 import/export 2017 Ori Calvo 10 Most browsers do not supports import/export Coming Chrome 62 will Therefore, must use a module loader Webpack Rollup Fusebox SystemJS
  11. 11. 11 Barrel 2017 Ori Calvo 11 Rollup exports from several modules into a single convenient module
  12. 12. 12 async/await 2017 Ori Calvo 12 function delay(ms) { return new Promise(function(resolve) { setTimeout(function() { resolve(); }, ms); }); } async function run() { await delay(500); console.log("AFTER"); }
  13. 13. 13 async/await 2017 Ori Calvo 13 Part of ECMAScript 2017 Allow for easier implementation of asynchronous functions Is supported for down-level browsers too Debugging is challanging
  14. 14. 14 Decorator 2017 Ori Calvo 14 Attach metadata to methods/classes Like C# attribute Java annotation Can intercept function invocation
  15. 15. 15 Decorator 2017 Ori Calvo 15 class Contact { @Profile() run() { console.log("run"); } } function Profile() { return function(target,propertyKey: string, descriptor: PropertyDescriptor) { const original = target[propertyKey]; target[propertyKey] = function() { console.log("BEFORE"); const retVal = original.apply(this, arguments); console.log("AFTER"); return retVal; } return target; } }
  16. 16. 16 Create NPM package 2017 Ori Calvo 16 Enable declaration option Use es2015 module settings Bundle all files into UMD format Rollup can help Add package.json main option inside package.json should point to the UMD bundle npm publish
  17. 17. 17 String Enums 2017 Ori Calvo 17 Enums can now be of type string enum Color { red = "Red", green = "Green", blue = "Blue", } const c: Color = Color.red; var Color; (function (Color) { Color["red"] = "Red"; Color["green"] = "Green"; Color["blue"] = "Blue"; })(Color || (Color = {}));
  18. 18. 18 Union Type 2017 Ori Calvo 18 Create a new type which one of the specified interface A { id: number, } interface B { name: string, } type C = A | B; const c1: C = { id: 1, }; const c2: C = { name: "Ori", };
  19. 19. 19 Intersection Type 2017 Ori Calvo 19 Define new type which has properties of all the others interface A { id: number, } interface B { name: string, } type C = A & B; const c1: C = { id: 1, name: "Ori", };
  20. 20. 20 Object.assign 2017 Ori Calvo 20 Using previous syntax we can now define Object.assign in a type safe way interface ObjectConstructor { assign(target: T, source: U): T & U; assign(target: T, source1: U, source2: V): T & U & V; assign(target: T, source1: U, source2: V, source3: W): T & U & V & W; }
  21. 21. 21 Type Guard 2017 Ori Calvo 21 The following compiles successfully class A { } class B extends A { run() { } } function doSomething(a: A) { if(a instanceof B) { a.run(); } }
  22. 22. 22 Challenge 2017 Ori Calvo 22 However, the following does not compile successfullyclass A { } class B extends A { run() { } } function isB(a: A) { return a instanceof B; } function doSomething(a: A) { if(isB(a)) { a.run(); } } Property 'run' does not exist on type 'A'.
  23. 23. 23 User Type Guard 2017 Ori Calvo 23 We can fix that class A { } class B extends A { run() { } } function isB(a: A): a is B { return a instanceof B; } function doSomething(a: A) { if(isB(a)) { a.run(); } }
  24. 24. 24 Class Augmentation 2017 Ori Calvo 24 An interface can extend existing class class A { run() { } } interface A { doSomething(); } function main() { const a = new A(); a.doSomething(); } main();
  25. 25. 25 Module Augmentation 2017 Ori Calvo 25 Extend a class exported from a module export class A { run() { } } module1 import {A} from "./module1"; declare module "./module1" { interface A { doSomething(); } } function main() { const a = new A(); a.doSomething(); } Applicatio n code
  26. 26. 26 Null Checks 2017 Ori Calvo 26 The following does compile successfully class A { run() { } } function run(a: A) { a.run(); } function main() { run(null); }
  27. 27. 27 --strictNullChecks 2017 Ori Calvo 27 If on (default is off), the compiler assume that any type is not assignable with null or undefined Now, the following code does not compile { "compilerOptions": { "strictNullChecks": true } } function main() { run(null); }
  28. 28. 28 Allow null 2017 Ori Calvo 28 class A { run() { } } function run(a: A|null) { if(a) { a.run(); } } function main() { run(null); } Without the if the error object is possibly null is reported
  29. 29. 29 --allowJs 2017 Ori Calvo 29 Tells the Typescript compiler to allow import of a JS file The JS file will be verified But only for general syntax errors Type safe errors are not reported import/export will be converted to the specified module system
  30. 30. 30 --checkJs 2017 Ori Calvo 30 Tells Typescript compiler to verify Type checks as much as it can Sending parameters to a function Types are calculated based on initialization Can use JSDoc to annotate code with types For example, function g(/** @type{string} */ a) { a = 12; }
  31. 31. 31 Mixin 2017 Ori Calvo 31 Create a new class out of an existing one and add some features to it class A { constructor(name: string) { } } type Constructor = new(...args: any[]) => T; function createClass(Base: T, id) { return class extends Base { id: number = id; } } var B = createClass(A, 5); var b = new B("Ori"); console.log(b.id);
  32. 32. 32 Typed map using object 2017 Ori Calvo 32 class Point { constructor(private x: number, private y: number) { } } const map: {[key: string]: Point} = {}; map["abc"] = new Point(5, 10);
  33. 33. 33 keyof 2017 Ori Calvo 33 interface Person { id: number; } type K1 = keyof Person; // id function get(obj: T, name: K): T[K] { return obj[name]; } var x: Person = {id:5}; get(x, "id");
  34. 34. 34 Partial 2017 Ori Calvo 34 interface Person { id: number; name: string; } type PartialPerson = Partial; const x: PartialPerson = { id: 1, };
  35. 35. THANK YOU Ori Calvo, 2017 oric@trainologic.com https://trainologic.com