0
votes

In Cypress I am using cy.route() for sending the below request, but cypress is not identifying the below request send. In the route url there is a openHash value which will be different for every POST request. Is there any way to ignore the openHash value or accept what ever value displays there.

So far I have tried by giving the url in following ways in route.

 url: '**/student/details.php?viewDetails=project&stdCount=1&sectionID=1&openHash=**',
 url: '**/student/details.php?viewDetails=project&stdCount=1&sectionID=1&openHash=**&ajaxCall=true**',

I believe while using cy.route() the POST url need to match exactly. Could someone please advise

Cypress version: 5.4.0

Student.feature

Feature: Update student details

Background: User logged in to application
        Given I should load all of the routes required for tests

Scenario: Update student details
        When I am logged in as the student user
        And I click on "Student" subtab
        And I should see details displayed

Step definition:

import { Then, When, And } from "cypress-cucumber-preprocessor/steps";

before(() => {
  Then('I should load all of the routes required for tests', () => {
        cy.server();
        cy.route({
           method: 'POST',
           url: '**student/details.php?viewDetails=project&stdCount=1&sectionID=1&openHash=5fc8329a76e73&ajaxCall=true**',
           delay: 2000
        }).as('getStudentTabDetails');
    })
})   


Then('I am logged in as the student user', () => {
  cy.get('[name=loginUsername]').type("Student1");
  cy.get('[name=loginPassword]').type("somePassword1", { sensitive: true });
  cy.contains('Login').click();
})


Then('I click on {string} subtab', (student) => {
  cy.get('#main a').contains(student).click({force:true});
});
  
Then('I should see details displayed', () => {
  cy.wait('@getStudentTabDetails', { timeout: 5000 });
});
    

Error: CypressError Timed out retrying: cy.wait() timed out waiting 5000ms for the 1st request to the route: getStudentTabDetails. No request ever occurred.

1
I think in cy.route2 there is a pathname option - Matches like 'path', but without query params, so should ignore everything after the '?'.Ackroydd
@Ackroydd I have added the feature step and step definition line to the question. On click on Student tab, the application will send the POST request. I am trying to grab that request using the line I should see details displayedsoccerway
Thanks, that's clear now. cy.route() requires cy.server() before it, so that's the first step. cy.route2() is better for your requirement.Ackroydd
I am using cy.server() in my test. Will try with cy.route2()soccerway
Please provide the complete test in the question, otherwise it is difficult to help.Ackroydd

1 Answers

1
votes

Cypress.minimatch is a tool that can be used for checking the route matchers.

By default Cypress uses minimatch to test glob patterns against request URLs.

If you’re struggling with writing the correct pattern you can iterate much faster by testing directly in your Developer Tools console.

The two routes you show in the question actually pass the minimatch test.

const url = 'http://example/student/details.php?viewDetails=project&stdCount=1&sectionID=1&openHash=5fc8329a76e73&ajaxCall=true';

const pattern1 = '**/student/details.php?viewDetails=project&stdCount=1&sectionID=1&openHash=**';
console.log( Cypress.minimatch(url, pattern1) );  // true

const pattern2 = '**/student/details.php?viewDetails=project&stdCount=1&sectionID=1&openHash=**&ajaxCall=true**';
console.log( Cypress.minimatch(url, pattern2) );  // true

Here is a Cypress fiddle that shows how to use the new intercept method to handle query parameters.

/// <reference types="@cypress/fiddle" />

const test = {
  html: `
    <p class="text-lg"></p>
    <script>
      setTimeout(() => {
        const url = 'http://example/student/details.php?viewDetails=project&stdCount=1&sectionID=1&openHash=5fc8329a76e73&ajaxCall=true';
        window.fetch(url, { method: 'POST'});
      }, 1000);
    </script>
  `,
  test: `
  cy.intercept({
    method: 'POST',
    url: '/student/details.php',
    query: {
      viewDetails: 'project',   // whatever query parts you care about
      stdCount: '1',
      sectionID: '1'
    }
  }, {})                 // Added an empty stub here, as my url does not actually exist
  .as('getStudentTabDetails');
  cy.wait('@getStudentTabDetails')
  `
}

it('', () => {
  cy.runExample(test)
});

The POST is made with native fetch(), which would not be captured in the old cy.route() method without using a polyfill.