考虑此测试设置:
var expect = require('chai').expect;
var fs = require('fs');
describe('my test', function() {
var dataArr;
// get data
before(function(done) {
fs.readFile('myArray.json', 'utf8', function (err, data) {
dataArr = JSON.parse(data);
done();
});
});
// test data
dataArr.forEach(function(val, index) {
it('Testing element no ' + (index+1), function(done) {
expect(val).to.be.cool;
done();
});
});
});
此测试返回错误Cannot read property 'forEach' of undefined
,因为循环在before()
之前执行。
我在使用嵌套it
的SO上发现this approach,但这似乎是一种肮脏的解决方法(对mocha nested it
进行搜索证明了这一点)。
对于这个不太常见的(?)问题,没有任何干净的解决方案吗?
答案 0 :(得分:0)
我认为不存在任何更清洁的解决方案。
在您的示例中,在评估dataArr时未定义它,这意味着forEach成员尚不存在,因为dataArr当时还不是数组。它将在it()的回调函数范围内定义,因为it()回调函数是在“之前”回调之后调用的。
因此嵌套的“描述”解决方案行之有效,因为它可以固定评估顺序,以便在该点定义dataArr。
所以已经提到的解决方法是这样的:
var assert = require('assert');
var fs = require('fs');
describe('my test', function() {
var dataArr;
// get data
before(function(done) {
dataArr = ["cool", "cool", "cool"]; // or fs.readFile or require
done();
});
// test it
it('test after data setup', function() {
describe('the tests', function() {
// now the dataArr is defined!
dataArr().forEach(function(val, index) {
it('Testing element no ' + (index+1), function(done) {
assert.equal(val, "cool");
done();
});
});
});
});
});
另一方面,如果您不更改dataArr,则可以在声明的位置立即评估它,例如:
var assert = require('assert');
var fs = require('fs');
describe('my test', function() {
const dataArr = ["cool", "cool", "cool"]; // or dataArr = require('testfile.json');
before(function(done) {
done();
});
// test it
// now the dataArr is defined!
dataArr().forEach(function(val, index) {
it('Testing element no ' + (index+1), function(done) {
assert.equal(val, "cool");
done();
});
});
});
答案 1 :(得分:0)
测试是同步定义的。是通过异步done
调用而不是dataArr.forEach
推迟的测试功能。
在这种情况下,异步readFile
没有任何好处。这样会更简单:
before(function() {
const data = fs.readFileSync('myArray.json', 'utf8');
dataArr = JSON.parse(data);
});
根本不需要readFile
。读取文件不是测试的一部分,应该执行一次。 Node.js本机支持导入JSON文件:
var expect = require('chai').expect;
var dataArr = require('./myArray.json');
答案 2 :(得分:0)
您正在从Mocha手中执行forEach
方法,应该将所有逻辑移到it
方法内
因此,如下更新代码:
it('Testing elements', function(done) {
expect(dataArr).all.to.be.cool;
});