TypeScript 介紹
TypeScript 是加上型別定義後的 JavaScript
安裝
使用指令安裝 TypeScript
bash
npm install -D typescript使用指令產生設定檔 tsconfig.json
bash
npx tsc --init一般設定
初始化完成後,會有非常多預設設定,也有一些預設是註解掉的,可以依需求開啟
更多設定說明參考: TypeScript 編譯配置 tsconfig.json compilerOptions 全解析
json
{
// 編譯設定
"compilerOptions": {
// 程式碼根目錄
"rootDir": "./src",
// 編譯輸出目錄
"outDir": "./dist",
// 模組設定,參考下方說明
"module": "commonjs",
"target": "esnext",
// 使 TypeScript 能夠更好地與 CommonJS 模組兼容, 允許以 ES 模組方式導入 CommonJS 模組
"esModuleInterop": true,
// 包含的型別定義檔,預設自動包含所有 @types 開頭的套件
"types": [],
// 應該包含哪些內建的型別定義,如 dom 為網頁用的 document 型別
"lib": [],
// 產生對應的 .map 檔案,能將編譯後的 JavaScript 對應回 TypeScript 程式碼
"sourceMap": true,
// 產生 .d.ts 類型定義檔案
"declaration": true,
// 產生 .d.ts.map 檔案
"declarationMap": true,
// 是否會給不確定的索引取值加上 undefined
// 舉例參考: https://github.com/hacker0limbo/my-blog/issues/21
"noUncheckedIndexedAccess": false,
// 是否允許給可選屬性 undefined 值,設定為 true 為不允許
"exactOptionalPropertyTypes": true,
// Style Options
// 是否在 function 的碼路徑未明確返回值時報錯。
"noImplicitReturns": true,
// 設定是否要求在覆蓋基類方法時必須明確使用 override 關鍵字。
"noImplicitOverride": true,
// 有未使用的變數時是否出錯
"noUnusedLocals": true,
// 有未使用的 function 參數時是否出錯
"noUnusedParameters": true,
// 是否不允許 switch case 穿透
"noFallthroughCasesInSwitch": true,
// 控制物件 key 的存取方式
"noPropertyAccessFromIndexSignature": true,
// 嚴格模式,建議開啟
"strict": true,
// 每個檔案將被獨立編譯
"isolatedModules": true,
// 只有 "import xxx" 沒給值的副作用會檢查是否有效,無效時拋出錯誤
// https://www.51cto.com/article/793699.html
"noUncheckedSideEffectImports": true,
// 控制 TypeScript 如何判斷檔案是純程式碼腳本還是模組
// 設置為 force 使 TypeScript 將所有檔案視為模組, 避免了使用全域變數引起的錯誤
"moduleDetection": "force",
// 跳過對 .d.ts 的型別檢查
"skipLibCheck": true,
},
// 編譯 src 資料夾內的檔案
"include": ["src"],
// 排除 node_modules
"exclude": ["node_modules"],
}模組設定
TypeScript 編譯的模組設定大致分為幾種:
module: 編譯後 JS 的模組系統commonjs: requireesnext: import/export
target: 產生出的 JS 語法版本,與模組系統無關- 決定是否保留箭頭函數等 JS 新語法
- 常用
esnext
moduleResolution: 如何解析 import 路徑classic: 廢棄node或node10: 與 Node.js 原生 require 相同,可不寫副檔名node16以後含nodenext: 與 Node.js 原生 module 相同,不管 package.json 設定的 type 是什麼都必須副檔名bundler: 給vite等打包工具使用的模式,TypeScript 不會解析 module,假設打包工具會處理
verbatimModuleSyntax: 控制 TypeScript 編譯前後 module 語法是否保持一致true: import/export 不會被 TypeScript 轉成 requirefalse: 預設,允許轉換
TIP
CommonJS 仍然是基於 ECMAScript 語法,只是匯入匯出不一樣
所以才會出現 module 是 commonjs,target 卻是 esnext 的情況
設定範例: Node.js 開發環境
json
"compilerOptions": {
"module": "commonjs",
"target": "esnext",
"moduleResolution": "node",
"verbatimModuleSyntax": false
}設定範例: Vite 前端專案
json
"compilerOptions": {
"module": "esnext",
"target": "esnext",
"moduleResolution": "bundler",
"verbatimModuleSyntax": true
}執行
Node.js 沒有完整支援 TypeScript,需要依賴 ts-node 或 tsx 等套件執行
TIP
Node.js v22.18.0 後的版本,加入了執行 TypeScript 的實驗性功能
TIP
Bun 可以直接執行 TypeScript
如果需要檔案存檔時自動重啟,一樣可以使用 nodemon
nodemon 預設以 ts-node 執行 TypeScript
bash
npm i -D ts-node nodemon指定 nodemon 執行 .ts 檔
json
"scripts": {
"dev": "nodemon src/index.ts",
}注意
ts-node 只會解析被 import 的檔案,如果是 .d.ts 等不需要引用的型別宣告會被忽略
需要在 tsconfig.json 加上設定才不會出現型別錯誤
json
{
"compilerOptions": {
// TypeScript 設定
},
"ts-node": {
"files": true
}
}編譯部署
使用 tsc 指令,將 TypeScript 編譯成 JavaScript後部署執行
json
{
"scripts": {
// 先編譯成 JavaScript
"build": "tsc",
// 編譯完成後,執行編譯出的檔案
"start": "node dist/index.js"
}
}