Cheat sheet TypeScript
Cập nhật lần cuối
Kiểu cơ bản
Các kiểu nguyên thủy và cách chú thích kiểu cho biến.
| Thao tác | Cú pháp |
|---|---|
| String | let name: string = "Ada"; |
| Number | let age: number = 25; |
| Boolean | let ok: boolean = true; |
| Mảng các phần tử kiểu T | let xs: number[] = [1, 2, 3]; |
| Mảng generic | let xs: Array<string> = []; |
| Tuple | let pair: [string, number] = ["a", 1]; |
| Any (bỏ kiểm tra kiểu) | let x: any = 1; |
| Unknown (any an toàn hơn) | let x: unknown = JSON.parse(s); |
| Void (không trả về) | function log(): void { … } |
| Never (không bao giờ trả về) | function fail(): never { throw … } |
| Null / undefined | let n: null = null; |
Suy luận kiểu và chú thích kiểu
Khi nào để TS tự suy luận và khi nào nên chú thích.
| Thao tác | Cú pháp |
|---|---|
| Suy luận từ giá trị | let count = 0; // number |
| Chú thích tường minh | let count: number = 0; |
| Tham số của hàm | function add(a: number, b: number) { … } |
| Kiểu trả về | function add(a: number, b: number): number { … } |
| Hàm mũi tên | const sq = (x: number): number => x * x; |
| Ép kiểu (type assertion) | const el = input as HTMLInputElement; |
| Const assertion (literal) | const dirs = ["up", "down"] as const; |
| Khẳng định khác null | el!.focus(); |
Interface
Mô tả hình dạng của một đối tượng.
| Thao tác | Cú pháp |
|---|---|
| Khai báo | interface User { id: number; name: string; } |
| Thuộc tính tùy chọn | interface User { age?: number; } |
| Thuộc tính chỉ đọc | interface User { readonly id: number; } |
| Chữ ký phương thức | interface Logger { log(msg: string): void; } |
| Mở rộng một interface khác | interface Admin extends User { role: string; } |
| Chữ ký chỉ mục | interface Map { [key: string]: number; } |
| Cài đặt trong một lớp | class Db implements Logger { … } |
Type alias và union
Đặt tên cho một kiểu và kết hợp các kiểu bằng | và &.
| Thao tác | Cú pháp |
|---|---|
| Type alias | type ID = string | number; |
| Type alias cho đối tượng | type User = { id: number; name: string }; |
| Kiểu union | type Status = "idle" | "loading" | "done"; |
| Kiểu giao (intersection) | type Admin = User & { role: string }; |
| Kiểu literal | type Yes = "yes"; |
| Nullable | type Maybe<T> = T | null | undefined; |
| Type alias cho hàm | type Handler = (e: Event) => void; |
Hàm
Tham số có kiểu, kiểu trả về và overload.
| Thao tác | Cú pháp |
|---|---|
| Tham số tùy chọn | function greet(name?: string) { … } |
| Tham số mặc định | function greet(name = "friend") { … } |
| Tham số rest | function sum(...ns: number[]): number { … } |
| Kiểu hàm | let fn: (a: number) => number; |
| Interface gọi được như hàm | interface Fn { (x: number): number; } |
| Chữ ký overload | function f(x: string): string; function f(x: number): number; function f(x: any) { return x; } |
| Kiểu trả về void bị bỏ qua | const cb: () => void = () => 42; // ok |
Lớp
Lớp với access modifier và parameter property.
| Thao tác | Cú pháp |
|---|---|
| Khai báo một lớp | class User { name: string; } |
| Hàm khởi tạo | constructor(name: string) { this.name = name; } |
| Thuộc tính khai báo qua tham số | constructor(public name: string) {} |
| Public / private / protected | private id: number; |
| Trường chỉ đọc | readonly id: number; |
| Thành viên static | static count = 0; |
| getter / setter | get name() { return this._name; } |
| Kế thừa | class Admin extends User { … } |
| Lớp trừu tượng | abstract class Shape { abstract area(): number; } |
Generic
Kiểu dùng lại được, nhận tham số là các kiểu khác.
| Thao tác | Cú pháp |
|---|---|
| Hàm generic | function id<T>(x: T): T { return x; } |
| Gọi với kiểu tường minh | id<string>("hi"); |
| Interface generic | interface Box<T> { value: T; } |
| Type alias generic | type Pair<A, B> = [A, B]; |
| Lớp generic | class Stack<T> { items: T[] = []; } |
| Ràng buộc bằng extends | function len<T extends { length: number }>(x: T) { return x.length; } |
| Tham số kiểu mặc định | interface Box<T = string> { value: T; } |
| Toán tử keyof | type K = keyof User; // "id" | "name" |
| Kiểu truy cập theo chỉ mục | type Name = User["name"]; |
Thu hẹp kiểu (narrowing)
Thu hẹp một union về một kiểu duy nhất lúc chạy.
| Thao tác | Cú pháp |
|---|---|
| Kiểm tra bằng typeof | if (typeof x === "string") { … } |
| Kiểm tra bằng instanceof | if (e instanceof Error) { … } |
| Toán tử in | if ("name" in obj) { … } |
| Thu hẹp bằng so sánh bằng | if (status === "done") { … } |
| Thu hẹp theo truthy/falsy | if (value) { … } |
| Type guard tự viết | function isUser(x: any): x is User { return "id" in x; } |
| Union phân biệt (discriminated union) | type Shape = { kind: "sq"; size: number } | { kind: "ci"; r: number }; |
| Kiểm tra bao quát mọi trường hợp bằng never | const _: never = shape; |
Enum
Tập hằng số có tên.
| Thao tác | Cú pháp |
|---|---|
| Enum số | enum Direction { Up, Down, Left, Right } |
| Enum chuỗi | enum Status { Idle = "IDLE", Done = "DONE" } |
| Dùng một giá trị | let d: Direction = Direction.Up; |
| Const enum (được nhúng thẳng) | const enum Color { Red, Green, Blue } |
| Union các literal (cách hiện đại) | type Status = "idle" | "done"; |
Utility type
Các kiểu trợ giúp có sẵn để biến đổi kiểu đã có.
| Thao tác | Cú pháp |
|---|---|
| Biến mọi thuộc tính thành tùy chọn | Partial<User> |
| Biến mọi thuộc tính thành bắt buộc | Required<User> |
| Biến mọi thuộc tính thành chỉ đọc | Readonly<User> |
| Chọn một tập con các khóa | Pick<User, "id" | "name"> |
| Bỏ một hoặc nhiều khóa | Omit<User, "password"> |
| Đối tượng với các khóa cho trước | Record<string, number> |
| Loại khỏi một union | Exclude<"a" | "b" | "c", "a"> |
| Chỉ giữ lại từ một union | Extract<"a" | "b", "a" | "c"> |
| Loại bỏ null / undefined | NonNullable<string | null> |
| Kiểu trả về của hàm | ReturnType<typeof fn> |
| Tuple tham số của hàm | Parameters<typeof fn> |
| Kiểu của promise sau khi await | Awaited<Promise<string>> |
Module
Import và export giữa các tệp.
| Thao tác | Cú pháp |
|---|---|
| Export có tên | export function add(a: number, b: number) { … } |
| Export mặc định | export default class User { … } |
| Re-export | export { User } from "./user"; |
| Import có tên | import { add } from "./math"; |
| Import mặc định | import User from "./user"; |
| Chỉ import kiểu | import type { User } from "./user"; |
| Import tất cả | import * as math from "./math"; |
| Tham chiếu triple-slash | /// <reference types="node" /> |
Những thiết lập tsconfig cần biết
Các cờ trình biên dịch đáng biết.
| Tùy chọn | Tác dụng |
|---|---|
"strict": true | Bật mọi kiểm tra ở chế độ strict (nên dùng). |
"target": "ES2022" | Phiên bản JavaScript mà tsc xuất ra. |
"module": "ESNext" | Hệ thống module trong đầu ra. |
"moduleResolution": "bundler" | Phân giải module theo cách các bundler hiện đại làm. |
"jsx": "react-jsx" | Bật JSX cho React 17 trở lên. |
"esModuleInterop": true | Import mặc định gọn hơn từ module CommonJS. |
"skipLibCheck": true | Bỏ kiểm tra kiểu trong node_modules (build nhanh hơn). |
"noEmit": true | Chỉ kiểm tra kiểu, để bundler lo phần xuất code. |
Cú pháp TypeScript bạn dùng nhiều nhất, gom trong một trang. Cheat sheet TypeScript này là bảng tra cứu nhanh cho TS hằng ngày: kiểu cơ bản, interface, type alias, generic, union, thu hẹp kiểu (narrowing) và các utility type có sẵn. Vì TypeScript được xây dựng trên JavaScript, hãy để cheat sheet JavaScript ở gần để tra phần cú pháp nền tảng.
Mọi thứ ở đây đều là TypeScript chuẩn, biên dịch được bằng tsc và chạy ở mọi nơi JavaScript hiện đại chạy được. Sao chép phần bạn cần, hoặc chạy thử bất kỳ đoạn code nào ngay trong playground TypeScript, không cần cài đặt gì. Mới làm quen với kiểu dữ liệu? Khóa học TypeScript tương tác miễn phí của Coddy giúp bạn xây dựng chúng từ nền JavaScript.
Câu hỏi thường gặp về cheat sheet TypeScript
Cheat sheet TypeScript này có miễn phí không?
Có. Cheat sheet TypeScript này hoàn toàn miễn phí, không cần đăng ký. Lưu trang lại và quay lại bất cứ khi nào bạn cần tra một kiểu, một interface hay một utility type.
Interface và type alias khác nhau thế nào?
interface không diễn đạt được. Quy tắc thường dùng: dùng interface cho hình dạng đối tượng công khai, và type cho union, tuple và các kiểu được tính toán.any và unknown khác nhau thế nào?
any bỏ hoàn toàn việc kiểm tra kiểu: trình biên dịch cho bạn làm bất cứ điều gì với nó. unknown an toàn về kiểu: bạn phải thu hẹp nó (bằng typeof, instanceof hoặc một type guard) trước khi dùng. Hãy ưu tiên unknown cho giá trị đến từ nguồn bên ngoài như JSON.parse hay fetch, vì nó buộc bạn kiểm tra dữ liệu trước khi dùng.Có cần học JavaScript trước TypeScript không?
Có. TypeScript là JavaScript cộng thêm một hệ thống kiểu ở bên trên, nên mọi kỹ năng JavaScript đều dùng lại được. Nếu bạn vẫn đang xây nền tảng JS (mảng, đối tượng, async/await), cheat sheet JavaScript là điểm khởi đầu tốt, và khóa học JavaScript miễn phí của Coddy dạy cùng các nội dung đó theo cách tương tác.
Có thể luyện tập TypeScript online không?
Có. Mở playground TypeScript để chạy bất kỳ đoạn code nào trong cheat sheet này ngay trên trình duyệt, không cần cài đặt gì. Khi muốn học có lộ trình, hãy học từ trang khóa học JavaScript rồi áp dụng các kiểu trên trang này lên trên.