更新2019
对于当今的所有Webpack和Broccolis,Gulps和Grunts,TypeScript和AltScripts,以及create-react-apps等,这都是毫无用处的,但是如果您只使用普通的,旧的VanillaJS,并且想要制作同构,这可能是您最好的选择:
var global
try {
global = Function('return this')();
} catch(e) {
global = window;
}
即使在--use_strict
in节点中使用时,Function构造函数调用也将起作用,因为Function构造函数始终在全局非严格范围内执行。
如果Function构造函数失败,那是因为您所在的浏览器eval
被CSP标头禁用。
当然,与杰诺的方式(节点替换),它们也不允许该功能的构造,在这种情况下,它回到枚举对象,如global
,module
,exports
,globalThis
和window
,然后鸭式检查这是全球详尽... :-/
疯狂的一线解决方案(原始):
var global = Function('return this')() || (42, eval)('this');
。
。
。
作品
- 在每个环境中(我测试过)
- 在严格模式下
- 甚至在嵌套范围内
更新2014年9月23日
如果最新浏览器中的HTTP标头明确禁止eval,则此操作现在可能会失败。
一种解决方法是尝试/捕获原始解决方案,因为只有浏览器才能运行此类JavaScript子集。
var global;
try {
global = Function('return this')() || (42, eval)('this');
} catch(e) {
global = window;
}
Example:
---
(function () {
var global = Function('return this')() || (42, eval)('this');
console.log(global);
(function () {
"use strict";
var global = Function('return this')() || (42, eval)('this');
console.log(global);
}());
(function () {
var global = Function('return this')() || (42, eval)('this');
console.log(global);
}).call('someNewContext');
}());
Tested:
---
* Chrome v12
* Node.JS v0.4.9
* Firefox v5
* MSIE 8
Why:
---
In short: it's some weird quirk. See the comments below (or the post above)
In `strict mode` `this` is never the global, but also in `strict mode` `eval` operates in a separate context in which `this` *is* always the global.
In non-strict mode `this` is the current context. If there is no current context, it assumes the global. An anonymous function has no context and hence in non-strict mode assumes the global.
Sub Rant:
There's a silly misfeature of JavaScript that 99.9% of the time just confuses people called the 'comma operator'.
var a = 0, b = 1;
a = 0, 1;
(a = 0), 1;
a = (0, 1);
a = (42, eval);
a('this');