javascript – 脚本vs命令行中节点中的全局变量赋值

前端之家收集整理的这篇文章主要介绍了javascript – 脚本vs命令行中节点中的全局变量赋值前端之家小编觉得挺不错的,现在分享给大家,也给大家做个参考。
我有以下脚本:
/* script.js */
var bar = "bar1";

function foo() {
    console.log('this.bar: ' + this.bar);
    console.log('global.bar: ' + global.bar);
}
foo();

运行节点script.js返回:

this.bar: undefined
global.bar: undefined

但是,从节点命令行环境中,再现相同的脚本会返回:

this.bar: bar1
global.bar: bar1

此外,如果我从var bar =“bar1”更改我的变量声明;到global.bar =“bar1”;运行上述代码的两种方法都返回:

this.bar: bar1
global.bar: bar1

有什么不同?在运行脚本时,全局变量赋值与在同一环境中复制脚本有何不同?

解决方法

因为每个节点模块都被包装在一个IIFE中,所以默认情况下不属于全局范围.

我们可以看到它发生在src / node.js,在NativeModule函数中.

NativeModule.require = function(id) {
    // ...
    var nativeModule = new NativeModule(id);

    nativeModule.cache();
    nativeModule.compile();

    return nativeModule.exports;
};

跟踪之后,我们来看看编译:

NativeModule.prototype.compile = function() {
    var source = NativeModule.getSource(this.id);
    source = NativeModule.wrap(source);

    var fn = runInThisContext(source,{ filename: this.filename });
    fn(this.exports,NativeModule.require,this,this.filename);

    this.loaded = true;
};

包装看起来相关,让我们看看它的作用:

NativeModule.wrap = function(script) {
    return NativeModule.wrapper[0] + script + NativeModule.wrapper[1];
};

NativeModule.wrapper = [
    '(function (exports,require,module,__filename,__dirname) { ','\n});'
];

如怀疑,它将您的模块的代码包装在一个IIFE中,这意味着您不会在全局范围内运行.

另一方面,REPL by default在全球范围内运行.遵循REPL代码是meh,但它基本归结为this line

if (self.useGlobal) {
    result = script.runInThisContext({ displayErrors: false });
} else {
    result = script.runInContext(context,{ displayErrors: false });
}

这看起来与我有关.

猜你在找的JavaScript相关文章