fishbar / jscoverage

jscoverage tool, written in pure js, both node or javascript support
Other
90 stars 21 forks source link

throw `[jscoverage] unknow ENV!` error when define variable `window` #24

Open hotoo opened 10 years ago

hotoo commented 10 years ago

https://github.com/fishbar/jscoverage/blob/master/lib/jscoverage.js#L36

    if (typeof global === 'object') {
      BASE = global;
    } else if (typeof window === 'object') {
      BASE = window;
    } else {
      throw new Error('[jscoverage] unknow ENV!');
    }

when my code has variable window,

var window = this; // this ref to window.
console.log(typeof window);

will console log object run in node, build as cmd module and run in web, or run in phantom. but throw error [jscoverage] unknow ENV! here, why?

ref

fishbar commented 10 years ago

没看懂你的意思。。。, 运行环境能描述一下么?

hotoo commented 10 years ago

背景

  1. spm 使用了 jscoverage 来生成测试覆盖率
  2. detector 模块中书写了 var window = this 这样的代码,在浏览器中运行时指向 window
  3. 使用 spm test 运行测试最终会调用 jscoverage 模块来生成覆盖率
  4. 但是测试 detector 模块时,jscoverage 抛出 [jscoverage] unknow ENV! 异常。

分析

看了 jscoverage 的代码:

    if (typeof global === 'object') {
      BASE = global;
    } else if (typeof window === 'object') {
      BASE = window;
    } else {
      throw new Error('[jscoverage] unknow ENV!');
    }

这里抛出了异常,但是实际上,即使 detector 中重定义 window 变量,typeof window 还是等于 "object" 的,不知道为什么 jscoverage 这里会抛出这个异常。

fishbar commented 10 years ago

"detector 模块中书写了 var window = this 这样的代码" 这句有可能会影响到,因为jscoverage的这段inject在代码的最前面, 当你的代码中出现 var window = this 作为一个全局的声明, 会将window重新define(如果window已经存在的话) (部分js引擎的解析貌似是这个样子) 当执行到这个statement时才赋值为 this, 所以会出现window为undefined的情况,也就命中了jscoverage的判断。

我去看看 spm test 做了什么