Node.js 当测试失败时,如何打印请求和响应?

Node.js 当测试失败时,如何打印请求和响应?,node.js,jestjs,supertest,Node.js,Jestjs,Supertest,我正在使用Supertest和Jest测试Node.js API 示例测试具有以下格式 it('Read a note for a user', (done) => { request(graphqlURL) .post('/graphql') .set(baseHeaders()) .send({ query: graphQLQuery }) .end((err, res) =

我正在使用Supertest和Jest测试Node.js API

示例测试具有以下格式

it('Read a note for a user', (done) => {
      request(graphqlURL)
        .post('/graphql')
        .set(baseHeaders())
        .send({
          query: graphQLQuery
        })
        .end((err, res) => {
          expect(res.status).toBe(200);          
          done();
        })

    });
当前,当预期失败时,将记录以下内容

expect(received).toBe(expected) // Object.is equality

    Expected: 200
    Received: 404

我还希望将请求和响应与失败的测试一起记录,以便在调试时有更多的上下文


是否有一种方法可以只打印失败的测试?您可以这样打印响应:

it('Read a note for a user', (done) => {
  request(graphqlURL)
    .post('/graphql')
    .set(baseHeaders())
    .send({
      query: graphQLQuery
    })
    .end((err, res) => {
      if(!expect(res.status).toBe(200)) console.log('res',res) // print response
      expect(res.status).toBe(200);          
      done();
    })

  });

expect
通过在期望失败时抛出
错误来工作

错误
消息
属性是测试报告中打印的内容

我假设如果您想使用现有的期望值,并且只想用额外的数据来增加失败消息,您可以捕获
错误
,将额外的数据附加到
消息
属性,然后像这样再次抛出
错误

it('Read a note for a user', (done) => {
  request(graphqlURL)
    .post('/graphql')
    .set(baseHeaders())
    .send({
      query: graphQLQuery
    })
    .end((err, res) => {
      try {
        expect(res.status).toBe(200);
      } catch (err) {
        // --- add additional data to the error message here ---
        err.message = `${err.message}\n\nfailing query: ${graphQLQuery}`;
        throw err;  // throw the error so test fails as expected
      }
      done();
    })
});
您可以创建一个日志,记录期望失败时的响应:

expect.extend({
  statusCode(expected, response) {
    const { status } = response
    const pass = expected === status

    if (pass) {
      return {
        message: () =>
          `expected ${status} to be ${expected}`,
        pass: true
      }
    } else {
      return {
        message: () =>
          `expected ${status} to be ${expected}. Response: ${response}`,
        pass: false
      }
    }
  }
})
然后在测试中,使用自定义匹配器而不是典型的
expect

it('Read a note for a user', (done) => {
  request(graphqlURL)
    .post('/graphql')
    .set(baseHeaders())
    .send({
      query: graphQLQuery
    })
    .end((err, res) => {
      expect.statusCode(200, res)     
      done()
    })
})

不幸的是。但是,您可以将关于请求的任意信息添加到自定义匹配器的签名中。

如果您为正文添加了额外的expect,如果它与预期的不匹配,则将记录它。在状态代码expect之前使用此expect将产生所需的效果。

我只想在预期失败时打印响应。在这种情况下,无论测试通过还是失败,都将打印响应。您现在可以检查,如果预期失败,仍然不会打印响应。只有当
err
是一个真实的值时,它才会打印出来。我正在寻找一种更通用的方法,这在另一个答案中有建议。谢谢你的帮助:)这在很大程度上解决了我的问题。不过有点小打嗝。
console.log
语句与测试报告分开打印。测试失败的报告将与该测试的相应
控制台.log
语句分开打印。这使得将请求响应与相应的失败测试相匹配变得单调乏味。有没有关于如何缓解这种情况的想法?@dsinecos我更新了我的答案,将额外的数据添加到
错误的
消息
属性中,因此它会被打印在测试报告中感谢一吨@brian住在户外,这解决了我的问题谢谢,这是我考虑的方法之一。我看到的缺点是,我必须为不同类型的比较编写自定义匹配器。您共享了状态代码的匹配器。在测试中,我还将比较响应体的不同部分。据我所知,我必须为每个人编写一个自定义匹配器?这有意义吗?您可以编写一个类似的带有日志记录的自定义匹配器,将supertest响应与另一个对象进行比较,并验证该对象是否是响应的子集。因此,类似于
expect.toMatchObject
的东西,但是带有修改后的消息。我接受了另一个答案。我担心的是,这会限制我可以在回复中使用的匹配器的数量,或者我最终会重写Jest提供的匹配器。谢谢你的帮助:)