TIL, 2022-08-04, TS features
const
assertions are the killer new TypeScript feature
as const
(constant assertion)- No literal types in that expansion should be widened.
- Object literals get
readonly
properties. - Array literals become
readonly
.
let x = 'x'; <- this can be widened
x = 'y';
let y = 'x' as const; <- this cannot
y = 'z';
const setCount = (n: number) => {
return {
type: 'SET_COUNT',
payload: n
}
}
The return value of `setCount(123)` can still be changed.
const setCount = (n: number) => {
return {
type: 'SET_COUNT',
payload: n
} as const
}
The return value can then not be changed.
Other things that const
assertions can remove - Adding a type of ReturnType
for the returns.
const hello = () => {
return [1, 2, 3] as const;
}
let aw = hello();
aw.push(1); <- Errors out due to `as const` assertion
Promise
- Async version of loading JSON where mistakes can happen:
import fs = require('fs');
function loadJSON(filename: string, cb: (error: Error) => void) {
fs.readFile(filename, function (err, data) {
if (err) return cb(err);
// Contain all your sync code in a try catch
try {
var parsed = JSON.parse(data);
}
catch (err) {
return cb(err);
}
// except when you call the callback
return cb(null, parsed);
});
}
- Promise: a promise can be either
pending
,fulfilled
, orrejected
.
const promise = new Promise((resolve, reject) => {
resolve(123);
});
promise.then((res) => {
console.log('I get called:', res === 123); // I get called: true
});
promise.catch((err) => {
// This is never called
});
- Quickly creating an already resolved promise:
Promise.resolve(result)
-
Quickly creating an already rejected promise:
Promise.reject(error)
- Reading a file with Promise:
import fs = require('fs');
function readFileAsync(filename: string): Promise<any> {
return new Promise((resolve,reject) => {
fs.readFile(filename,(err,result) => {
if (err) reject(err);
else resolve(result);
});
});
}
Top 5 TypeScript Features You Should Master
- Tuple types allow you to express an array with a fixed number of elements as
const
. - Mapped types:
Readonly
,ReurnType
,NonNullable
. - Narrowing via Type guards: Using a function whose return type is a
type predicate
and it returnstrue/false
.
TypeScript: A Gentle Introduction to Mapped Types
keyof
gets the keys of an object.- Iterating over keys of objects:
[P in keyof T]: T[P]
. - Conditional typing.
never
andinfer
.Partial
: Makes all keys optional.
Master TypeScript’s Type Guards
TypeScript 4.1’s Advanced Mapped Types
- Mapped types: Making a type based on another type. Ex:
Readonly
- Can add a
-
to removereadonly
interface, and same with?
. - Recursive conditional types - it’s okay.
- Template literal types -
Uppercase
,Lowercase
,Capitalize
Uncapitalize
). - Remapping type:
interface Person {
name: string;
surname: string;
email: string;
}
type UpdateFactory<T> = {
[P in keyof T as `set${Capitalize<string & P>}`]: (key: T[P], item: T) => T;
}
type PersonFactory = UpdateFactory<Person>;
// PersonFactory will now have this methods:
setName: (key: string, item: Person) => Person;
setSurname: (key: string, item: Person) => Person;
setEmail: (key: string, item: Person) => Person;