Cypress 中的异步特性


Cypress 基于 node.js 服务器构建,并使用 Javascript 编程语言。任何依赖于 node.js 的内容本质上都是异步的,因此 Cypress 命令也以这种模式工作。

当我们在测试用例中有一组测试步骤时,所有步骤都会并行开始执行,而不会等待前一个步骤完成。在同步执行中,每个测试步骤按顺序运行,只有在前一个步骤执行完成后,我们才会进入下一步。

因此,在像 Cypress 这样的异步执行中,即使测试步骤是按顺序设计的,每个测试步骤也都是相互独立的。简而言之,在异步模式下,每个步骤都不会考虑前一个步骤执行的结果或状态,而只是简单地运行每个步骤。

Cypress 提供了一个包装器,确保其命令的测试执行按照开发顺序发生。因此,这些命令会同时执行,但它们会被排队。但是,如果 Javascript 命令与 Cypress 命令一起工作,它仍然是异步的。

示例

现在让我们执行一段 Cypress 代码:

// test suite
describe('Tutorialspoint Test', function () {
   // test case
   it('Test Case1', function (){
      // test step to launch a URL
      cy.visit("https://tutorialspoint.com/index.htm");
      // enter test in the edit box
      cy.get('#gs_50d > tbody > tr > td'). should('have.length',2);
      // locate element with get and find method
      cy.get('#gs_50d > tbody > tr > td'). find('input')
      //enter test in the edit box
      .type('Cypress');
      console.log('Tutorialspoint');
   });
});

在触发上述代码执行时,如果我们打开浏览器控制台,我们会在浏览器加载之前就发现 Tutorialspoint 打印在上面。这证实了 console.log 测试步骤没有等待其他测试步骤,并立即在控制台中打印。

因此,我们看到,由于 console.log 是一个 Javascript 命令,它不会像 Cypress 复合命令那样进行排队,而是继续执行。Cypress 通过 promise 处理来顺序执行其步骤。

Promise 是一种编程语言,用于确定 Cypress 命令的状态。Promise 有三种状态,如下所示:

  • 已解决(Resolved) - 如果测试步骤执行没有失败,则处于此状态。

  • 挂起(Pending) - 如果正在等待测试步骤执行结果,则处于此状态。

  • 已拒绝(Rejected) - 如果测试步骤执行失败,则处于此状态。

只有在前一个命令或 promise 响应已解决后,Cypress 中的以下命令才会执行。我们可以使用 then() 方法在 Cypress 代码中实现 promise。

示例

以下代码描述了在 Javascript 中为每个 Cypress 复合命令实现的 promise。这种实现使代码变得混乱且冗长。

// test suite
describe('Tutorialspoint Test', function () {
   // test case
   it('Test Case1', function (){
      return cy.visit('https://tutorialspoint.com/index.htm')
      .then(() => {
         return cy.get('.product');
      })
      .then(($element) => {
         return cy.click($element);
      })
   })
})

Cypress 在内部处理 promise,并借助包装器来解决它们,我们可以实现我们的代码而无需考虑 promise 的状态。因此,代码的可读性大大提高。

上述 Cypress 代码,不使用 promise。

// test suite
describe('Tutorialspoint Test', function () {
   // test case
   it('Test Case1', function (){
      cy.visit('https://tutorialspoint.com/index.htm')
      cy.get('.product').click();
   })
})

因此,Cypress 会考虑到测试用例中的下一步只有在前一个命令或 promise 处于已解决状态时才会执行。

更新于: 2020年8月5日

351 次浏览

启动您的 职业生涯

通过完成课程获得认证

开始学习
广告