Welcome to OGeek Q&A Community for programmer and developer-Open, Learning and Share
Welcome To Ask or Share your Answers For Others

Categories

0 votes
215 views
in Technique[技术] by (71.8m points)

testing - How to share response data across multiple suites?

Let's say we have the following suite:

describe('Devices', () => {
    describe('Master Data Set-Up', () => {
        it('should create the device if necessary', () => {
            cy.createDevice()
                its('body.id')
                .as('deviceId');
        });
    });
    describe('Test Suite 1', () => {
        it('should allow to send data to device', () => {
            cy.get('@deviceId').then((deviceId) => {
                cy.sendData(deviceId, 'Some Data');
            });
        });
    });
});

So, we have a set up suite that creates master data. This is a simplified version, actually it contains a couple of it specs and I'd like to keep it like that because it's better to read in the Cypress output.

Then, there is the actual test suite that want's to use data that has previously been created. In this case a server generated id that should be used for another REST call.

This is assuming, that cy.createDevice and cy.sendData are custom commands available that internally use cy.request.

When running that, cy.get('@deviceId') fails because aliases are not shared across describe blocks AFAIK. I tried to use let deviceId but it's undefined as it is not yet available when the test specs are processed.

What is a proper way to do this?


与恶龙缠斗过久,自身亦成为恶龙;凝视深渊过久,深渊将回以凝视…
Welcome To Ask or Share your Answers For Others

1 Reply

0 votes
by (71.8m points)

Upvote for @ArekKhatry's idea, but to be safe I would obtain the the id in a before(). If you ever run tests in parallel, grabbing data from one test to use in another would be flaky.

Note that running cy.createDevice().its('body.id') in the before() still gives you the same test coverage as running inside it(), i.e it tests that the request succeeds and the return value has an id.

The file should be written to cypress/fixtures, otherwise it will write to the project root causing untidy pollution of the file structure.

Also, the id is returned from cy.request() as a number, but must be stringifyed in order to write to a text file.

Here's my variant

describe('Devices', () => {
  before(() => {
    cy.createDevice()           
      .its('body.id')
      .then(id => {
        cy.writeFile('cypress/fixtures/deviceId.txt', id.toString());
        cy.log(`Created device: ${id}`);
      });
  });

  describe('Test Suite 1', () => {
    it('should allow to send data to device', () => {

      cy.fixture('deviceId')               // can use simpler cy.fixture here
        .then(device_id => {               // returned as a string here
          const id = parseInt(device_id);  // may need to parse to number?   
          cy.sendData(id, 'Some Data');
        })
    });
  });
});

与恶龙缠斗过久,自身亦成为恶龙;凝视深渊过久,深渊将回以凝视…
OGeek|极客中国-欢迎来到极客的世界,一个免费开放的程序员编程交流平台!开放,进步,分享!让技术改变生活,让极客改变未来! Welcome to OGeek Q&A Community for programmer and developer-Open, Learning and Share
Click Here to Ask a Question

...