異步模塊定義(Asynchronous Module Definition,簡稱 AMD)API 描述了一種定義模塊的機制,模塊及其依賴模塊能夠經過這種機制進行加載。該機制特別適用於瀏覽器。數組
本規範曾被稱爲 Modules Transport/C,但本規範主要不是用來傳輸已有的 CommonJS 模塊,而是用來定義模塊。瀏覽器
本規範只定義了一個函數 define,該函數是一個自由變量,或者說是一個全局變量。函數簽名以下:異步
define(id?, dependencies?, factory);
第一個參數 id 指定了即將定義的模塊的 id。該參數是可選的,若是未指定該參數,則模塊的 id 默認爲模塊加載器請求該腳本時使用的模塊 id。若是指定該參數,參數值必須是一個絕對 id(不容許使用相對 id)。函數
第二個參數 dependencies 是一個數組,包含即將定義的模塊全部依賴模塊名稱。依賴模塊必須在執行工廠函數以前完成解析,解析結果做爲參數傳遞給工廠函數,工廠函數的參數順序與 dependencies 參數所包含依賴模塊順序保持一致。依賴模塊 id 能夠爲相對 id,所謂相對是指相對於即將定義的模塊而言。若是 dependencies 中出現 require
, exports
或 module
字樣,則對應的參數應被解析爲 CommonJS 模塊規範中所定義的自由變量 require, exports 或 module。dependencies 參數是可選的,該參數缺省值爲 ["require", "exports", "module"]。若是工廠函數的參數列表長度小於 3,那麼加載器能夠選擇使用工廠函數參數列表長度所對應的 dependencies 參數來調用工廠函數。工具
第三個參數 factory 是一個函數,它用來初始化一個模塊或對象。若是 factory 是一個函數,那它應該只被執行一次。若是 factory 是一個對象,那麼它應該做爲模塊的輸出物進行賦值。ui
若是 id 和 dependencies 所有缺省,則模塊加載器應掃描工廠函數體中包含的 require 語句來肯定依賴模塊。爲此,工廠函數的第一個參數應命名爲 "require"。某些狀況下加載器能夠選擇不去掃描依賴模塊,例如代碼大小限制,或者函數對象缺乏 toString 方法。只要 id 或 dependencies 有一個被指定實參,則加載器就不該再掃描工廠函數來肯定依賴模塊。code
爲了可以清楚代表當前全局函數 define 是否符合 AMD API,任何一個全局函數 define 都應擁有一個 amd
屬性,該屬性值爲一個對象。這樣能夠避免現有的 Javascript 代碼中存在的全局函數 define 不符合 AMD API 的衝突。對象
define.amd 對象應擁有的屬性不在本規範中給出說明。實現了 AMD API 的做者能夠利用 amd 屬性來通知別人,他的實現中除了基本的 AMD API,還額外提供了什麼支持。ip
define.amd 屬性代表當前 AMD 實現符合本規範所定義的 API。若是還有另外一個版本的 API,那麼將在 define 函數上添加另外一個屬性,例如 define.amd2 來表示該實現符合另外一個版本的 API。ci
如下示例想要說明某個實現支持加載多個版本的模塊:
define.amd = { multiversion: true };
最簡單的定義:
define.amd = {};
一個腳本中能夠屢次調用 define 函數,define 函數的調用順序不影響大局。先定義的模塊能夠指定後定義的模塊做爲依賴模塊。模塊加載器負責延遲加載未解析的依賴模塊直到整個腳本都加載完畢,以此來阻止非必要的請求。
定義一個 id 爲 "alpha" 的模塊,它有一個依賴模塊 beta。
define("alpha", ["require", "exports", "beta"], function (require, exports, beta) { exports.verb = function () { return beta.verb(); } });
定義一個匿名模塊,模塊的 id 來自於源文件名。
define(['alpha'], function (alpha) { return { verb: function () { return alpha.verb() + 2; } }; });
定義一個自由模塊(沒有依賴其餘模塊)。
define({ add: function (x, y) { return x + y; } });
本規範保留了全局變量 define
,*包的元數據異步定義 API and
做爲保留關鍵字以備將來其餘 CommonJS API 使用。模塊加載器不該該在此函數上添加額外的方法或屬性。
本規範保留了全局變量 require
提供給模塊加載器使用。模塊加載能夠自由使用該全局變量,它們可使用該變量,並向該變量添加屬性或函數,甚至能夠選擇不使用 require。
define 函數的調用推薦使用 define(...)
的形式,以便靜態分析工具能夠順利工做。
本規範曾使用 require.def()
做爲入口方法。模塊加載器能夠將 define()
設置爲 require.def()
的別名以向後兼容。
PS:本規範從 CommonJS 官方英文版本轉譯而來,斜體部分表示譯文存在商榷。