exports
- 多数の関数やオブジェクト(定数とか)を返す時に使いやすい
- 循環参照しているモジュール構成でも問題ない
想定される使い方
var hoge = require('./hoge');
var h = new hoge.Hoge(hoge.SPEC.FUGA);
var x = hoge.util(h);
module.exports
- 単一のクラスや単一の関数を返す時に使いやすい
- 循環参照しているモジュール構成の時に問題がおきる
- 自プロジェクト内で依存関係が少ない場合に向いている(npmで取ってきたモジュール以外はrequireしないほうがいい)
想定される使い方
var Hoge = require('./hoge');
var hoge = new Hoge();
循環参照のケース
以下のようなケースにおいてmodule.exportsを使ってモジュールを外部に出すと問題が起きる
main.js
var TestManager = require('./test_manager');
var test = TestManager.instance.create()
test.ok()
test.js
var TestManager = require('./test_manager');
var Test = module.exports = function(){
this.initialize();
}
Test.prototype.initialize = function(){
TestManager.instance.add(this);
}
Test.prototype.ok = function(){
console.log("ok");
}
Test.prototype.dispose = function(){
TestManager.instance.remove(this);
}
test_manager.js
var Test = require('./test');
var TestManager = function(){
this.tests = [];
}
TestManager.prototype.create = function(){
return new Test();
}
TestManager.prototype.add = function(test){
this.tests.push(test);
}
TestManager.prototype.remove = function(test){
this.tests = this.tests.filter(function(v){ return v !== test });
}
module.exports = {
instance : new TestManager()
}
console
$ node main.js
c:\Users\you2\x\test.js:7
TestManager.instance.add(this);
^
TypeError: Cannot read property 'add' of undefined
at Test.initialize (c:\Users\you2\x\test.js:7:25)
at new module.exports (c:\Users\you2\x\test.js:4:10)
at TestManager.create (c:\Users\you2\x\test_manager.js:7:12)
at Object.<anonymous> (c:\Users\you2\x\main.js:4:33)
at Module._compile (module.js:460:26)
at Object.Module._extensions..js (module.js:478:10)
at Module.load (module.js:355:32)
at Function.Module._load (module.js:310:12)
at Function.Module.runMain (module.js:501:10)
at startup (node.js:129:16)