Cypress.io API Automation Tips & Tricks

/* Examples for method, url, headers, body to use in reusable custom commands as a parameters*/

method : 'GET/POST/DELETE/PUT',  /* Anyone method should be used */
url : 'https://localhost:8080/api/v1', 
headers : { 
     Authorization : 'Bearer API_KEY',
     'Content-Type' : 'application/json'
},
body : {
     name : 'abc',
     email : 'abc@gmail.com'
}        

/* Custom Reusable Command for POST & PUT Request Methods */

Cypress.Commands.add("apiRequestWithBody", (method, url, headers, body) => { 
    cy.request({ 
         method,
         url,
         headers,
         body, 
         failOnStatusCode: false
     })
})        

/* Custom Reusable Command for GET & DELETE Request Methods */

Cypress.Commands.add("apiRequestWithoutBody", (method, url, headers) => { 
    cy.request({ 
         method,
         url,
         headers,
         failOnStatusCode: false
     })
})        

/* API Validations Assertions for Status Code for POST & PUT Request */

POST & PUT Request 

cy.apiRequestWithBody('POST', url, headers, body).then((response) => {
   expect(response.status).to.equal(201)
})

cy.apiRequestWithBody('PUT', url, headers, body).then((response) => {
   expect(response.status).to.eq(201)
})        

/* API Validations Assertions for Status Code for GET & DELETE Request */

GET & DELETE Request

cy.apiRequestWithoutBody('GET', url, headers).then((response) => {
   expect(response.status).to.eq(200)
})

cy.apiRequestWithoutBody('DELETE', url, headers, body).then((response) => {
   expect(response.status).to.eq(204)
})        

/* API Validations Assertions for Response Time less than 5 seconds for POST & PUT Request */

cy.apiRequestWithBody('POST', url, headers, body).then((response) => {
   expect(response.duration).to.be.lessThan(5000)
})

cy.apiRequestWithBody('PUT', url, headers, body).then((response) => {
   expect(response.duration).to.be.lessThan(5000)
})        

/* API Validations Assertions for Response Time less than 5 seconds for GET & DELETE Request */

cy.apiRequestWithoutBody('GET', url, headers).then((response) => {
   expect(response.duration).to.be.lessThan(5000)
})

cy.apiRequestWithoutBody('DELETE', url, headers).then((response) => {
   expect(response.duration).to.be.lessThan(5000)
})        

/* API Validations Assertions for Content Header should be application/json POST & PUT Request */

cy.apiRequestWithBody('POST', url, headers, body).then((response) => {   
  expect(response.headers['content-type']).to.include('application/json')
})

cy.apiRequestWithBody('PUT', url, headers, body).then((response) => {
  expect(response.headers['content-type']).to.include('application/json')
})        

/* API Validations Assertions for Content Header should be application/json GET & DELETE Request */

cy.apiRequestWithoutBody('GET', url, headers).then((response) => {  
  expect(response.headers['content-type']).to.include('application/json')
})

cy.apiRequestWithoutBody('DELETE', url, headers).then((response) => {
  expect(response.headers['content-type']).to.include('application/json')
})        

/* API Schema Validations */

Add in e2e.js or e2e.ts

import chaiJsonSchema from 'chai-json-schema'
chai.use(chaiJsonSchema)

install node package of "chai-json-schema"        
const jsonSchema = {
        type: 'object',
        properties: {
          accessToken: { type: 'string' },
          refreshToken: { type: 'string' },
        },
        required: ['accessToken', 'refreshToken'],
}

cy.apiRequestWithBody('POST', url, body).then((response) => {
   expect(response.body).to.be.jsonSchema(jsonSchema)
})        

/* To Test GET Request */

cy.request(“https://localhost:8080/api/posts/1”).then((response) => {
      expect(response.body).to.have.property('code', 200)
})        

/* To Test POST Request */

cy.request({
        method: 'POST',
        url: 'https://localhost:3000/api/posts',
        body: {
            id : 2,
            title : 'api'
        }
}).then((response) => { 
          expect(response.body).has.property('title','api')
})        

/* To Test PUT Request */

cy.request({
       method: ‘PUT’,
       url: ‘https://localhost:3000/api/posts/2’,
       body: { 
            id : 2,
            title : 'Test API'
       }
}).then((response) => { 
      expect(response.body).has.property('title','Test API')
})        

/* To Test DELETE Request */

cy.request({
       method : 'DELETE',
       url: 'https://localhost:3000/api/post/2'
 }).then((response) => {
      expect(response).to.be.empty;
 })	        

/* To Update Existing Created Record by PUT Request */

const userId = 456

const updateData = {
     id: userId,
     name: 'abc',
     email: 'test@gmail.com',
 }
 
cy.request({
      method: 'PUT',
      url: `https://localhost:8080/api/v1/users/${userId}`,
      body: updateData,
      failOnStatusCode: false
}).then((response) => {
      expect(response.status).to.eq(201)
})        

/* To Spy & Stub Network Requests & Responses by intercept cypress command */

cy.intercept({
      method : 'POST',
      url : 'https://localhost:8080/login'
}).as('LoginURL')
cy.wait('@LoginURL')        

/* To Create a Fixture data file & load it in test by cy.intercept */

users.json

[
  {
    "id": 1,
    "name": "abc",
    "email": "pqr@gmail.com"
  }
]        
cy.fixture('users').then((users) => {
  cy.intercept('GET', '/api/users', users).as('getUsers');
});        
cy.visit('/users');
cy.wait('@getUsers');
cy.get('.user-list').should('contain', 'abc');        

/* To make POST Request directly via API & verify all data */

cy.request({
  method: 'POST',
  url: 'https://localhost:8080/api/v1/data', 
  body: {
    name: 'test_1',
    email: 'test@gmail.com',
    designation: 'qa_engineer',
    role: 'provide_quality'
  }
}).as('data_creation')

/* To Verify the response of the POST request */

cy.get('@data_creation').then((response) => {
  expect(response.status).to.eq(201)
  expect(response.body).to.have.property('id')
  expect(response.body).to.have.property('name', 'test_1')
  expect(response.body).to.have.property('email', 'test@gmail.com')
  expect(response.body).to.have.property('designation', 'qa_engineer')
  expect(response.body).to.have.property('role', 'provide_quality')
})        

/* To Verify the created data via a GET request */

cy.get('@data_creation').then((response) => {
  const id = response.body.id

  cy.request({
    method: 'GET',
    url: `https://localhost:8080/api/v1/data/${id}`
  }).as('getData')

  cy.get('@getData').then((getResponse) => {
   expect(getResponse.status).to.eq(200)
   expect(getResponse.body).to.have.property('id', id);
   expect(getResponse.body).to.have.property('name', 'test_1')
   expect(getResponse.body).to.have.property('email', 'test@gmail.com')
   expect(getResponse.body).to.have.property('designation', 'qa_engineer')
   expect(getResponse.body).to.have.property('role', 'provide_quality')
  })
})        

/* To create test data using a POST request method & verify all response validations */

cy.intercept('POST', 'https://localhost:8080/api/v1/data', (req) => {
}).as('data_creation');

/* Fill up the Form */ 

cy.get('input[name="name"]').type('test_1')
cy.get('input[name="email"]').type('test@gmail.com')
cy.get('input[name="designation"]').type('qa_engineer')
cy.get('input[name="role"]').type('provide_quality')
cy.get('form').submit()

/* Verify Request Payload */

cy.wait('@data_creation').its('request.body').should((body) => {
  expect(body).to.have.property('name', 'test_1')
  expect(body).to.have.property('email', 'test@gmail.com')
  expect(body).to.have.property('designation', 'qa_engineer')
  expect(body).to.have.property('role', 'provide_quality')
})

/* Verify Response */

cy.wait('@data_creation').then((response_data) => {
  const responseBody = response_data.response.body
  expect(response_data.response.status).to.eq(201)
  expect(responseBody).to.have.property('id')
  expect(responseBody).to.have.property('name', 'test_1')
  expect(responseBody).to.have.property('email', 'test@gmail.com')
  expect(responseBody).to.have.property('designation', 'qa_engineer')
  expect(responseBody).to.have.property('role', 'provide_quality')
})        
Sebastian Clavijo Suero

Staff QA Engineer/SDET @ KUBRA || Engineer in Computer Science || Cypress and Playwright Independent Contributor || Blogger || Accessibility — Creator of: WICK-A11Y, CYPRESS-AJV-SCHEMA-VALIDATOR, and PW-API-PLUGIN

7 个月

Nice article Pushkar Deshpande! It covers a subject commonly forgotten, JSON schema validation. Have you checked out this other plugin for advance JSON schema validations in Cypress? https://dev.to/sebastianclavijo/cypress-ajv-schema-validator-plugin-the-brave-vigilante-for-your-api-contracts-5cfe

Kailash Pathak

â””? ? Microsoft? Most Valuable Professional (MVP) ? Linkedin Top Quality Assurance Voice ? DZone Core Member ? Applitools Ambassador | Read My Blog at qaautomationlabs.com | AWS,PMI-ACP?,ITIL? PRINCE2 Practitioner?

8 个月

Nice one

Miranda Boyden

Strategic Transformation Executive | Founder @ HOBOSX & Military Allies – Empowering Business & Nonprofit Support for Military & Veteran Communities | Certified AI Transformation Leader

8 个月

Unleash your testing potential with Cypress API tips & tricks! ???? #Testing #Automation

Adhip Ray

Startups Need Rapid Growth, Not Just Digital Impressions. We Help Create Omni-Channel Digital Strategies for Real Business Growth.

8 个月

Excited to dive into these Cypress API automation tips! Streamlining our testing processes with advanced techniques like those Cypress offers is crucial for enhancing software quality and efficiency. Thanks for sharing these insights it's always great to stay ahead in the automation game!

要查看或添加评论,请登录

Pushkar Deshpande的更多文章

社区洞察

其他会员也浏览了