Javascript Mocha在运行CasperJS测试时不考虑超时或已完成回调

Javascript Mocha在运行CasperJS测试时不考虑超时或已完成回调,javascript,mocha.js,casperjs,Javascript,Mocha.js,Casperjs,这就是我试图用casperjs和摩卡咖啡解决的问题。我试图在页面上测试元素的文本值,看看它是否在一段时间内更新。。。5-10秒。我的想法是获取值,将其推入一个数组,等待500毫秒,然后重复,直到数组有20个项目。大约10秒。然后在数组上运行下划线/lodash的..uniq函数,并测试数组长度是否为>1 我遇到的问题是,mocha并没有等待测试完成,因为说明测试是成功/失败的。我想我可以增加摩卡咖啡的暂停时间,但这并没有造成任何影响。请参阅下面的代码。我已经对它的可读性进行了评论 it('has

这就是我试图用casperjs和摩卡咖啡解决的问题。我试图在页面上测试元素的文本值,看看它是否在一段时间内更新。。。5-10秒。我的想法是获取值,将其推入一个数组,等待500毫秒,然后重复,直到数组有20个项目。大约10秒。然后在数组上运行下划线/lodash的
..uniq
函数,并测试数组长度是否为
>1

我遇到的问题是,mocha并没有等待测试完成,因为说明测试是成功/失败的。我想我可以增加摩卡咖啡的暂停时间,但这并没有造成任何影响。请参阅下面的代码。我已经对它的可读性进行了评论

it('has elements whose values update', function () {
  // 20 seconds, which should be plenty of time
  this.timeout(20000);

  casper.then(function() {
        // The test array
    var values = [],
        // So we can stop the intervals
        intervalId;

    function getValue () {
      // Grab element's text value
      var value = casper.evaluate(function () { return $('#element').text(); });

      // Push in to our test array
      values.push(value);

      // 20 * 500ms == 10 seconds or 10000ms
      // When set to 500ms, this block never runs. The test passes before it has a chance to
      if (values.length === 20) {

        // Stop it from checking the value any further
        clearInterval(intervalId);

        // Test to see we've had more than one unique value in the 10 seconds
        expect(_.uniq(values).length).to.be.gt(1);
      } 
    } 

    // Wait for the value on the page to populate
    // It defaults to '-' when the page loads
    casper.waitFor(function () {
      return this.evaluate(function () {
        return $('#element').text() !== '-';
      });

    // Start the check with a delay of 500ms between each check
    }, function then() {
      intervalId = setInterval(getValue, 500);
    });
  });
});
当间隔值设置为500ms时,在摩卡进入下一个测试之前,我在
值中得到2-3个元素值。更奇怪的是,当我
console.log(值)
确定测试通过后,他们在屏幕上打印。原因是
values.length
永远不会达到10,因此永远不会调用
expect
调用。假设测试通过。以下是500毫秒间隔的测试输出:

Dashboard
✓ has elements whose values update (202ms)
Values: ["20,832,022"]
Values: ["20,832,022","20,832,372"]
Values: ["20,832,022","20,832,372","20,832,722"]

✓ has the page title of leads (41ms)

2 passing (11s)
Dashboard

✓ has elements whose values update (341ms)
Values: ["20,400,667"]
Values: ["20,400,667","20,400,718"]
Values: ["20,400,667","20,400,718","20,400,718"]
Values: ["20,400,667","20,400,718","20,400,718","20,400,769"]
Values: ["20,400,667","20,400,718","20,400,718","20,400,769","20,400,769"]
Values: ["20,400,667","20,400,718","20,400,718","20,400,769","20,400,769","20,400,820"]
Values: ["20,400,667","20,400,718","20,400,718","20,400,769","20,400,769","20,400,820","20,400,820"]
Values: ["20,400,667","20,400,718","20,400,718","20,400,769","20,400,769","20,400,820","20,400,820","20,400,871"]
Values: ["20,400,667","20,400,718","20,400,718","20,400,769","20,400,769","20,400,820","20,400,820","20,400,871","20,400,871"]
Values: ["20,400,667","20,400,718","20,400,718","20,400,769","20,400,769","20,400,820","20,400,820","20,400,871","20,400,871","20,400,922"]
Final Values: ["20,400,667","20,400,718","20,400,718","20,400,769","20,400,769","20,400,820","20,400,820","20,400,871","20,400,871","20,400,922"]

✓ has the page title of leads (41ms)

2 passing (8s)
即使没有20个项目,它也会通过。由于某个地方超时,它从不检查它。以下是50毫秒间隔的输出:

Dashboard
✓ has elements whose values update (202ms)
Values: ["20,832,022"]
Values: ["20,832,022","20,832,372"]
Values: ["20,832,022","20,832,372","20,832,722"]

✓ has the page title of leads (41ms)

2 passing (11s)
Dashboard

✓ has elements whose values update (341ms)
Values: ["20,400,667"]
Values: ["20,400,667","20,400,718"]
Values: ["20,400,667","20,400,718","20,400,718"]
Values: ["20,400,667","20,400,718","20,400,718","20,400,769"]
Values: ["20,400,667","20,400,718","20,400,718","20,400,769","20,400,769"]
Values: ["20,400,667","20,400,718","20,400,718","20,400,769","20,400,769","20,400,820"]
Values: ["20,400,667","20,400,718","20,400,718","20,400,769","20,400,769","20,400,820","20,400,820"]
Values: ["20,400,667","20,400,718","20,400,718","20,400,769","20,400,769","20,400,820","20,400,820","20,400,871"]
Values: ["20,400,667","20,400,718","20,400,718","20,400,769","20,400,769","20,400,820","20,400,820","20,400,871","20,400,871"]
Values: ["20,400,667","20,400,718","20,400,718","20,400,769","20,400,769","20,400,820","20,400,820","20,400,871","20,400,871","20,400,922"]
Final Values: ["20,400,667","20,400,718","20,400,718","20,400,769","20,400,769","20,400,820","20,400,820","20,400,871","20,400,871","20,400,922"]

✓ has the page title of leads (41ms)

2 passing (8s)
我得到更多的50毫秒,但这只是半秒的测试。页面上的一些其他值需要更长的时间才能更新,这是不可行的

我尝试将
done
回调传递给
it
语句,但mocha忽略了它,不等待调用它

这是工具的局限性还是我用错了

我尝试使用下面的方法使用done回调

it('has elements whose values update', function (done) {

它仍然忽略了我已将测试标记为异步。在500毫秒时,它仍然没有到达if语句或done调用。在50毫秒时,它会抛出以下错误:

done() called multiple times

我正在使用。这会影响它吗?

摩卡casperjs似乎没有使用默认的
done
。它知道测试步骤已经完成,因为它使用CasperJS的控制流。在您的情况下,您可以通过调用
setInterval
来中断控制流

最好重构代码,使用对
getValue
的递归调用,如下所示:

function getValue () {
  // Grab element's text value
  var value = this.evaluate(function () { return $('#element').text(); });

  // Push in to our test array
  values.push(value);

  // 20 * 500ms == 10 seconds or 10000ms
  // When set to 500ms, this block never runs. The test passes before it has a chance to
  if (values.length === 20) {
    // Test to see we've had more than one unique value in the 10 seconds
    expect(_.uniq(values).length).to.be.gt(1);
  } else {
    this.wait(500, getValue);
  }
} 

// Wait for the value on the page to populate
// It defaults to '-' when the page loads
casper.waitFor(function () {
  return this.evaluate(function () {
    return $('#element').text() !== '-';
  });

// Start the check with a delay of 500ms between each check
}, function then() {
  this.wait(500, getValue);
});
这使得
getValue
成为一个casper步骤

另一个不需要太多重构的解决方案是让第二个
waitFor
沿着中断的控制流运行。这需要一个半全局变量
someGlobalVariable
。也许可以使用
intervalId
,但最好使用
someGlobalVariable=false在顶部

intervalId = setInterval(getValue, 500);
this.waitFor(function check(){
    return someGlobalVariable;
}, function then(){
   // do something else
}, null, 20000);
就让它停止吧

expect(_.uniq(values).length).to.be.gt(1);
someGlobalVariable = true;