【问题标题】:Multiple requires of same module seem to affect scope of each successive require同一模块的多个要求似乎会影响每个连续要求的范围
【发布时间】:2015-08-26 11:26:13
【问题描述】:

我创建了以下 3 个文件:

base.js

var base = {};

base.one = 1;
base.two = 2;
base.three = 3;

base.bar = function(){

  console.log( this.three );

};

a.js

var base = require('./base');
base.three = 6;
module.exports = base;

b.js

var base = require('./base');
module.exports = base;

test.js

var test_modules = ['a','b'];

test_modules.forEach( function( module_name ){
  require( './' + module_name ).bar();
});

然后像这样运行 test.js:

node ./test.js

它输出这个:

6
6

为什么我在'a.js'中设置模块'base'的属性'three'时,会影响到'b.js'中的对象?

【问题讨论】:

    标签: node.js module scope


    【解决方案1】:

    当您require() 一个模块时,它会被评估一次 并缓存,以便同一模块的后续require()s 不必从磁盘加载,从而获得相同的导出对象.因此,当您更改导出的属性时,对该模块的所有引用都会看到更新后的值。

    【讨论】:

      【解决方案2】:

      您正在为base 模块引入global 状态。

      模块a 突变base 然后也将其导出,这意味着对base 的任何进一步引用都将具有更新的值。

      最好通过test.js中的以下脚本来演示

      var testModules = ['b', 'a'];
      testModules.forEach(function(module) {
        require('./' + module).bar();
      });
      

      现在当你运行 node test.js 时,你会看到

      3
      6
      

      为什么?

      因为包含模块的顺序发生了变化。

      我该如何解决?

      简单,摆脱全局状态。一种选择是使用这样的原型

      var Base = function() {
        this.one = 1;
        this.two = 2;
        this.three = 3;
      };
      Base.prototype.bar = function() {
        console.log(this.three);
      };
      module.exports = Base;
      

      然后,在a.js内部

      var Base = require('./base');
      var baseInstance = new Base();
      baseInstance.three = 6;
      module.exports = baseInstance;
      

      b.js里面

      var Base = require('./base');
      module.exports = new Base();
      

      现在当你运行你原来的test.js,输出应该是

      6
      3
      

      【讨论】:

        猜你喜欢
        • 1970-01-01
        • 2013-09-14
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        相关资源
        最近更新 更多