如何 return 来自 Cypress 自定义命令的 HTTP 响应主体?

How to return HTTP response body from Cypress custom command?

我正在尝试编写一个向端点发送 POST 请求的自定义 Cypress 命令,然后我想将响应主体存储在我的测试中。

这是 Postman 中响应正文的样子:

这是我在 cypress/support/commands.js 中的自定义命令,为简单起见,我删除了请求正文值:

Cypress.Commands.add('createStudent', (email) => {
    cy.request({
        method: `POST`,
        url: `myUrl`,
        body: {}
      }).then((resp) => {
        return resp
      });
});

这是我的规范文件中的代码:

let response = cy.createStudent(email);
cy.log(response)

但是,当我 运行 代码时,我得到以下对象而不是响应主体:

谁能告诉我哪里出错了,以及 return 实际 HTTP 响应正文需要做哪些更改?

如果您只会在 Cypress 链中使用该值,您可以简单地为命令添加别名。

Cypress.Commands.add('createStudent', (email) => {
    cy.request({
        method: `POST`,
        url: `myUrl`,
        body: {}
      }).as('student');
});
...
cy.createStudent();
cy.get('@student').then((response) => {
  cy.log(response.body) // assuming you'd want to log the response body.
});
// OR
cy.get('@student').its('body').should('eq', { foo: 'bar' });
// the above example doesn't work with logging, but I'm guessing you don't _just_ want to log the response

如果您可能 在其他时间 在 Cypress 链之外需要变量,您总是可以将变量存储在 Cypress.env().

Cypress.Commands.add('createStudent', (email) => {
    cy.request({
        method: `POST`,
        url: `myUrl`,
        body: {}
      }).then((res) => {
          Cypress.env('student', res);
      });
});
...
cy.createStudent().then(() => {
  cy.get('foo').should('have.text', Cypress.env('student').body.foo);
});
// key point is referencing the entire response by `Cypress.env('student')`

如果您查看控制台消息,会显示一个类型 $Chainer,它是您实际想要的结果(响应)的包装对象。

Chainer 是 Cypress 能够重试最初失败但可能在超时期限(通常为 4 秒)内成功的查询的基础。

但这意味着您不能使用return值。相反,您需要使用 .then().

“展开”值
Cypress.Commands.add('createStudent', (email) => {
  cy.request({
    method: 'POST',
    url: 'myUrl',
    body: {...}
  })
  // The response is put on the "chain" upon exit of the custom command
  // You need nothing else here to get the raw response
})

cy.createStudent().then(response => {
  cy.log(response)
});

您可以添加一个步骤来从响应中提取详细信息,例如

Cypress.Commands.add('createStudent', (email) => {
  cy.request({
    method: 'POST',
    url: 'myUrl',
    body: {...}
  })
  .then(response => {
    expect(response.success).to.eq(true)   // check expected response is good
    return response.body.id                // pass on just the id
  })
})

cy.createStudent().then(id => {
  cy.log(id)
});