JavaScript中的独立执行上下文

JavaScript中的独立执行上下文,javascript,scope,Javascript,Scope,我试图在JavaScript中的一个空的独立执行上下文中执行一段代码。在下面的示例中,我尝试隔离执行范围。我想做的是在没有全局变量的上下文中执行函数 (function() { 'use strict'; var scope = Object.create(null); var isolated = function() { 'use strict'; console.log(document); // Trying to get undefined

我试图在JavaScript中的一个空的独立执行上下文中执行一段代码。在下面的示例中,我尝试隔离执行范围。我想做的是在没有全局变量的上下文中执行函数

(function() {
  'use strict';

  var scope = Object.create(null);
  var isolated = function() {
    'use strict';
    console.log(document); // Trying to get undefined
                           // but traces `document`.
  };

  isolated.call(scope);
})();
我认为取消全局变量很简单,但是太多了

var isolated = function(window, document, location /* etc */) {
  // ...
};

isolated.call(scope, undefined, undefined, undefined /* etc */);

有更好的方法吗?

使用我的MentalJS解析器隔离环境。然后,您可以通过自定义代码来选择它可以访问哪些对象/变量

默认情况下,它允许访问文档,但您可以防止这种情况,在这里自定义环境,然后您可以选择是否有权访问数学等。

在javascript本身中没有好的方法可以做到这一点(但请参阅Gareth Hayes的答案了解另一个选项)

有两种不好的方法

(function() {
  var scope = Object.create(null);
  var obscurer = {};
  for (var key in this) {
     obscurer[key] = undefined;
  }

  with (obscurer) {
    var isolated = function() {
      'use strict';
      console.log(document);
    };
  }

  isolated.call(scope);
})();
请注意,您实际上会得到一个错误,因为console没有定义,而不是文档,尽管您可以通过不在Obscher对象中阻塞“console”来解决这个问题。你可能会发现你需要比你意识到的更多的全球人

您还只阻塞了窗口的可枚举属性。如果您也意识到要阻止的不可计算属性,则必须将它们添加到遮光器中

当然,对使用
意味着你不能再使用严格模式了,每个人都会瞧不起你


如果您在节点中而不是在浏览器中工作,则有更多有趣的选项可用。

可以在没有ECMA6的情况下使用包含可信需求保护代码的IIFE来完成此操作,您可以将不可信需求隔离代码注入其中(参见示例)

如果您将上述内容放在Chrome的控制台中,您将获得:

    primitiveArg is: This is shared
    VM117:29 ReferenceError: hostingFuncPrivatePrimitive is not defined
            at <anonymous>:26:17
            at <anonymous>:11:5
            at <anonymous>:16:3
    VM117:12 sharedObject is: {"mumu":"mimi"}
    VM117:13 hostingFuncPrivateObject is: {"this_is_mine":true}
primitiveArg是:这是共享的
VM117:29引用错误:未定义hostingFuncPrivatePrimitive
时间:26:17
时间:11:5
时间:16:3
VM117:12共享对象是:{“mumu”:“mimi”}
VM117:13 hostingFuncPrivateObject是:{“这是我的”:true}

P.S.S:我知道我在晚会上迟到了,但也许这对任何人都有帮助。

Window。Trime.Actudio。调用(窗口,1)绕过这个沙箱。我得到“Type Error:Window是未定义的”,但是,是的,我不会真的认为这个方法是安全的。据我所知,如果不解析输入代码,就无法创建安全的沙盒。即使这样,也可能会犯很多错误(例如,人们经常忘记函数构造函数让他们评估代码)。这是一个特定于Firefox的向量。我每晚都在Firefox的控制台上运行它,所以我不知道是Firefox版本还是控制台让它对我起作用。我想这突出了一点,如果你真的在寻求安全,有很多边缘案例需要考虑。很有意思的是,知道弗洛伦特为什么要这么做……它也可以在铬上工作,实际上是32.0.1700.72米。但这是我的观点,你错过了一件事,这是一个完全的旁路,而如果你使用解析器和白名单,它对攻击的抵抗力更强。使用web workers怎么样?我在EcmaScript 6中找到了一种方法,用(context){…}
调整
,这样我们分配的任何新变量都将进入context对象,而不是全局/窗口对象。更多信息请点击此处:
    primitiveArg is: This is shared
    VM117:29 ReferenceError: hostingFuncPrivatePrimitive is not defined
            at <anonymous>:26:17
            at <anonymous>:11:5
            at <anonymous>:16:3
    VM117:12 sharedObject is: {"mumu":"mimi"}
    VM117:13 hostingFuncPrivateObject is: {"this_is_mine":true}