1. 程式人生 > >[規範]CommonJS規範

[規範]CommonJS規範

概述

CommonJS是伺服器端模組的規範,Node.js採用了這個規範。

根據CommonJS規範,一個單獨的檔案就是一個模組。每一個模組都是一個單獨的作用域,也就是說,在該模組內部定義的變數,無法被其他模組讀取,除非定義為global物件的屬性。

global.warming = true;

上面程式碼的waiming變數,可以被所有模組讀取。當然,這樣做是不推薦,輸出模組變數的最好方法是使用module.exports物件。

var i = 1;
var max = 30;

module.exports = function () {
  for (i -= 1; i++ < max; ) {
    console.log(i);
  }
  max *= 1.1;
};

上面程式碼通過module.exports物件,定義了一個函式,該函式就是模組外部與內部通訊的橋樑。

載入模組使用require方法,該方法讀取一個檔案並執行,最後返回檔案內部的module.exports物件。假定有一個一個簡單的模組example.js。

// example.js

console.log("evaluating example.js");

var invisible = function () {
  console.log("invisible");
}

exports.message = "hi";

exports.say = function () {
  console.log(message);
}

使用require方法,載入example.js。

// main.js

var example = require('./example.js');

這時,變數example就對應模組中的module.exports物件,於是就可以通過這個變數,使用example.js模組提供的各個方法。

require方法預設讀取js檔案,所以可以省略js字尾名,所以上面的程式碼往往寫成下面這樣。

var example = require('./example');

js檔名前面需要加上路徑,可以是相對路徑(相對於使用require方法的檔案),也可以是絕對路徑。如果省略路徑,node.js會認為,你要載入一個核心模組,或者已經安裝在本地 node_modules 目錄中的模組。如果載入的是一個目錄,node.js會首先尋找該目錄中的 package.json 檔案,載入該檔案 main 屬性提到的模組,否則就尋找該目錄下的 index.js 檔案。

下面的例子是使用一行語句,定義一個最簡單的模組。

// addition.js

exports.do = function(a, b){ return a + b };

上面的語句定義了一個加法模組,做法就是在exports物件上定義一個do方法,那就是供外部呼叫的方法。使用的時候,只要用require函式呼叫即可。

var add = require('./addition');

add.do(1,2)
// 3

再看一個複雜一點的例子。

// foobar.js

function foobar(){
        this.foo = function(){
                console.log('Hello foo');
        }

        this.bar = function(){
                console.log('Hello bar');
        }
}
 
exports.foobar = foobar;

呼叫該模組的方法如下:

var foobar = require('./foobar').foobar,
    test   = new foobar();
 
test.bar(); // 'Hello bar'

有時,不需要exports返回一個物件,只需要它返回一個函式。這時,就要寫成module.exports。

module.exports = function () {
  console.log("hello world")
}

AMD規範與CommonJS規範的相容性

CommonJS規範載入模組是同步的,也就是說,只有載入完成,才能執行後面的操作。AMD規範則是非同步載入模組,允許指定回撥函式。由於Node.js主要用於伺服器程式設計,模組檔案一般都已經存在於本地硬碟,所以載入起來比較快,不用考慮非同步載入的方式,所以CommonJS規範比較適用。但是,如果是瀏覽器環境,要從伺服器端載入模組,這時就必須採用非同步模式,因此瀏覽器端一般採用AMD規範。

AMD規範使用define方法定義模組,下面就是一個例子:

define(['package/lib'], function(lib){
 
    function foo(){
        lib.log('hello world!');
    } 
 
    return {
        foo: foo
    };
});

AMD規範允許輸出的模組相容CommonJS規範,這時define方法需要寫成下面這樣:

define(function (require, exports, module){
    var someModule = require("someModule");
    var anotherModule = require("anotherModule");    

    someModule.doTehAwesome();
    anotherModule.doMoarAwesome();

    exports.asplode = function (){
        someModule.doTehAwesome();
        anotherModule.doMoarAwesome();
    };
});
---------------
引自:
http://javascript.ruanyifeng.com/nodejs/commonjs.html