javascript-如何测试控制器中是否正在调用方法?

这是有关使用Mocha在Sails JS中进行异步测试的问题.

我正在使用supertest库在Sails JS中编写控制器测试.我想检查是否在HTTP POST上调用了一个方法到我们的控制器.为此,我对方法进行了测试,并期望在end()中调用它,如下所示:

request(sails.hooks.http.app)
    .post('heartbeat/create')
    .send('device: 1')
    .end(function(err, res) {
        expect(publishCreateStub.called).to.be.true;
        done();
    });

当我运行它时,期望会失败,因为断言时不会调用该方法.但是,当我将期望值放入setTimeout中时,它可以正常工作:

request(sails.hooks.http.app)
    .post('heartbeat/create')
    .send('device: 1')
    .end(function(err, res) {
        setTimeOut(function() {
            expect(publishCreateStub.called).to.be.true;
            done();
        }, 1000);
    });

没有setTimeout,有什么方法可以使测试通过吗?

这是我正在测试的代码部分:HeartbeatController#create

您还可以通过发送拉取请求来帮助我们解决问题:https://github.com/multunus/one-mdm/issues/1

解决方法:

实际的问题是您的控制器不等待publishCreate被调用.因此,您以201 Created进行响应,而不检查是否已创建任何东西.

Heartbeat.findOne或Heartbeat.publishCreate都有可能失败,但您会更新.

要解决此问题,您应该修改控制器,在Heartbeat Promise回调内移动响应部分:

create: function (req, res, next) {
  if(req.isSocket) {
    Heartbeat.watch(req);
  }

  Heartbeat.create(req.body)
    .exec(function(error, heartbeat) {
      if(error) {
        res.status(422);
        return res.send('Invalid heartbeat data');
      }

      Heartbeat.findOne(heartbeat.id).populate('device').then(function(newHeartbeat) {
        Heartbeat.publishCreate(newHeartbeat.device);
      }).then(function() {
        // success
        res.status(201);
        res.json({
          device: heartbeat.device
        });
      }, function(err) {
        // something bad happened
        next(err);
       });

    });
}

在我的示例中,我将实际的错误处理委托给下一个快速的错误处理中间件:

next(err);

但是您可以决定自己处理错误,例如:

res.status(400);
res.send('Can not publish Heartbeat create');
上一篇:javascript-我如何期望Mocha测试失败?


下一篇:测试框架 Mocha 实例教程