# ES6 的module語法 ###### tags: `分享` --- 之前在使用 vue-cli 時接觸到 `export default {something}`, 在寫 JS 的 17 題題目時用到 `module.exports = something` --- | |module.exports / require|export / import| |-|--------|---| |實作標準|**CommonJs**|**ES6**| |可能會聽到|**Node.js module**|**ES module(ESM)**| |export|`module.exports = something`|`export default something`| |import|`require("./something.js")`|`import something from "./something.js"`| --- 為什麼會分成兩種(或者更多)方式啊? --- ## 稍微考古一下 --- JavaScript 在 ES6 之前只有兩種 scope 1. 全域範圍 2. 函式範圍 並沒有模組化的概念, 所以那時候如果要把 JavaScript 做**模組化** 就只能用 **物件**、**閉包**、**立即函式** 來封裝成模組 --- ![](https://i.imgur.com/VJbEynQ.png) --- 之後出現一些實作標準 (但不是真正的 JavaScript 標準) 例如: 1. Asynchronous Module Definition (AMD) 2. **CommonJs** 來實現在寫 JavaScript 時的模組化 --- npm 裡面你所安裝的模組, 幾乎都是用 CommonJs 的 node.js module --- CommonJs 的 module.export / require 並沒有辦法在瀏覽器上使用, 因此 webpack 打包出來的網頁程式碼都是使用 立即函式 --- 所以平常在 webpack 這類的工具環境下引入模組並且打包的時候, webpack 就會把瀏覽器看不懂的 commonjs 語法轉換成瀏覽器看的懂的語法, 用的方式大概就是把模組內的程式碼轉換成 閉包+立即函式 再安插進去 --- 等到 ES6 誕生後,JavaScript 才有原生的模組語法可以使用 --- 來細部看一下 --- # CommonJS 的 module.exports --- 當 webpack 在打包的時候看到 `require` 這個*標記*的時候會去執行某個函式把位置裡的程式碼做轉換並且安插 --- ``` // something.js var something = "any string" module.export = something ========================================== // main.js const something = require(./something.js) console.log(something) ``` --- # ES6 的 export / import 1. Named export (Zero or more exports per module) 3. Default export (One per module) --- # Named export 1. ``` export const superNumberOne = 1 / export function getNumber() {}``` 3. ``` const superNumberOne = 1; function getNumber() {} export {superNumberOne, getNumber} // 可以用 as 取別名 // export { superNumberOne as one, getNumber} --- # Default export 1. ``` export default 1; 5. ``` export default function() {} / export default class 3. ``` const superNumberOne = 1 export default number1 3. ``` const superNumberOne = 1 function getNumber() {} export {superNumberOne as one, getNumber as default} 可以把 default 當作是一個特別的**簡稱**, 一個 js file 只能有**一個** default, export default 的內容**不一定**要事先宣告 --- # import 1. ``` import anyName from "module.js" // import default 2. ``` import * as anyName from "module.js" // import every thing 3. ``` import {default as anyName, superNumberOne as one, getNumber} from "module.js" 3. ``` import anyName, {superNumberOne as one, getNumber} from "module.js" //等同於 3. 5. ``` import "module.js" // Import an entire module for side effects only --- 大概就是這樣~
{"metaMigratedAt":"2023-06-15T15:17:04.237Z","metaMigratedFrom":"Content","title":"ES6 的module語法","breaks":true,"contributors":"[{\"id\":\"111acc36-4797-4d6c-9b0f-ac6f5795c573\",\"add\":4077,\"del\":1470}]"}
    210 views