4

我正在尝试使用 nyc 获取覆盖率报告,如果我不使用 cross-env 插件,它会很好地工作。

cross-env NODE_ENV=test nyc mocha --ui bdd --reporter spec --colors --require babel-core/register tests --recursive

执行此命令,代码覆盖率将无法正常运行,结果如下:

 31 passing (1s)

----------|----------|----------|----------|----------|-------------------|
File      |  % Stmts | % Branch |  % Funcs |  % Lines | Uncovered Line #s |
----------|----------|----------|----------|----------|-------------------|
All files |        0 |        0 |        0 |        0 |                   |
----------|----------|----------|----------|----------|-------------------|

但是,如果我运行nyc mocha --ui bdd --reporter spec --colors --require babel-core/register tests --recursive它,它将按预期工作。

---------------------|----------|----------|----------|----------|-------------------|
File                 |  % Stmts | % Branch |  % Funcs |  % Lines | Uncovered Line #s |
---------------------|----------|----------|----------|----------|-------------------|
All files            |    79.45 |    64.29 |    35.71 |    84.62 |                   |
 constants           |      100 |      100 |      100 |      100 |                   |
  index.js           |      100 |      100 |      100 |      100 |                   |
 db                  |    77.05 |    64.29 |    33.33 |    83.02 |                   |
---------------------|----------|----------|----------|----------|-------------------|

问题是我需要设置 env 变量才能使用允许我正确运行测试的 rewire 插件(事实上,大多数测试都因此而失败)。

这是我的 .bebelrc

{
  "presets": ["es2015"],
  "env": {
    "test": {
      "plugins": ["istanbul", "babel-plugin-rewire"]
    }
  }
}

注意:我认为这个问题与 babel-plugin-rewire 有关。实际上,即使删除跨环境并将插件集合放在根目录中也会给我相同的空覆盖结果。

4

1 回答 1

2

我在 babel 配置文件和插件周围找到了解决这个问题的方法。为了避免这种情况,最好使用最后一个 env 预设。我还创建了一个 repo来重现错误并且有一个类似于这篇文章的自述文件。

重新布线/跨环境

使用默认命令(使用 rewire 和 cross-env)运行测试将生成一个空的覆盖率报告:

npm run test

此命令将仅执行测试,它们都将通过

npm run test:cov

这将执行前面的test脚本,但会添加覆盖率报告,结果为空

----------|----------|----------|----------|----------|-------------------|
File      |  % Stmts | % Branch |  % Funcs |  % Lines | Uncovered Line #s |
----------|----------|----------|----------|----------|-------------------|
All files |        0 |        0 |        0 |        0 |                   |
----------|----------|----------|----------|----------|-------------------|

无需重新布线/跨环境

从测试脚本中删除cross-env NODE_ENV=test将避免加载重新布线并生成正确的覆盖率。副作用是使用重新布线的测试将失败。

npm run test2

将在没有 的情况下运行脚本cross-env,因此 babel 不会加载 rewire 插件,因此一项测试将失败。

npm run test:cov2

此命令将使用前面的test2脚本并生成覆盖率。在这种情况下,将正确生成覆盖率报告。

------------------|----------|----------|----------|----------|-------------------|
File              |  % Stmts | % Branch |  % Funcs |  % Lines | Uncovered Line #s |
------------------|----------|----------|----------|----------|-------------------|
All files         |    64.29 |      100 |    54.55 |    66.67 |                   |
 src              |       75 |      100 |       60 |    85.71 |                   |
  a-dependency.js |      100 |      100 |      100 |      100 |                   |
  a-module.js     |       60 |      100 |        0 |       75 |                 6 |
 tests            |       60 |      100 |       50 |       60 |                   |
  test.js         |       60 |      100 |       50 |       60 |... 23,24,26,27,28 |
------------------|----------|----------|----------|----------|-------------------|

但由于缺少重新布线插件,它不正确。

babelrc (es2015)

{
  "presets": ["es2015"],
  "env": {
    "test": {
      "plugins": ["istanbul", "rewire"]
    }
  }
}

这是解决方案中使用的 babel 配置文件。从插件集合中删除rewire插件将生成并清空覆盖,npm run test:cov但不使用npm run test:cov2(不使用跨环境)。

如果我这样修改babelrc

{
  "presets": ["es2015"],
  "plugins": ["istanbul", "rewire"]
}

(有npm run test:cov跨环境)和npm run test:cov2(没有跨环境)。将生成一个空结果。

如果我删除两个插件

{
  "presets": ["es2015"]
}

两个命令(有和没有跨环境)都会生成覆盖结果(部分,因为一个测试会失败)

仅从插件集合中删除istanbul将生成一个完整的覆盖文件,这将是结果(如预期的那样)

------------------|----------|----------|----------|----------|-------------------|
File              |  % Stmts | % Branch |  % Funcs |  % Lines | Uncovered Line #s |
------------------|----------|----------|----------|----------|-------------------|
All files         |      100 |      100 |      100 |      100 |                   |
 src              |      100 |      100 |      100 |      100 |                   |
  a-dependency.js |      100 |      100 |      100 |      100 |                   |
  a-module.js     |      100 |      100 |      100 |      100 |                   |
 tests            |      100 |      100 |      100 |      100 |                   |
  test.js         |      100 |      100 |      100 |      100 |                   |
------------------|----------|----------|----------|----------|-------------------|

babelrc (环境)

在围绕上一个es2015预设解决了这个问题之后,我转向了那个env。安装它npm install babel-preset-env --save-dev然后我以这种方式修改了我的 babelrc。

{
  "presets": [
    ["env", {
      "targets": {
        "node": "current"
      }
    }]
  ],
  "env": {
    "test": {
      "plugins": ["istanbul", "rewire"]
    }
  }
}

在这种情况下npm run test可以正常工作并npm run test:cov生成正确的覆盖率报告。并且不会有跨端或重新布线的问题。

结论

es2015如果在使用预设时与 babel 结合使用,rewire 和 cross-env 都会以某种方式产生问题。使用这个预设生成报告显然足以istanbul从 babel 插件中删除并仅使用 rewire(在这种情况下它也适用于 cross-env)。

我宁愿建议升级到env预设并按照建议使用 babel 插件(除非它为您的项目创建其他问题)

环境

> node --version
v9.4.0
> npm --version
5.6.0
>ver
Microsoft Windows [Version 10.0.16299.309]

在 MacOS 上观察到相同的行为

于 2018-04-04T07:23:30.987 回答