javascriptcypresscypress-custom-commands

Getting an error using Cypress.Commands.overwriteQuery


I am getting this error while overwriting the contains() method.

Cannot read properties of undefined (reading 'hasPreviouslyLinkedCommand') in cypress

Here is the commands.js file:

Cypress.Commands.add("clickOnLinks", (linkText) => {
  cy.get("a").contains(linkText).click();
});

// overwriting contains()
// passing the same parameter for the contains method

Cypress.Commands.overwriteQuery(
  "contains",
  (originalFn, subject, filter, text, options = {}) => {
    // determine if the filter argument was passed

    if (typeof text === "object") {
      options = text;
      text = filter;
      filter = undefined;
    }
    options.matchCase = false;

    return originalFn(subject, filter, text, options);
  }
);

And this is my test file:

describe("Custom command", () => {
  it("overwriting the custom commands", () => {
    cy.visit("https://magento.softwaretestingboard.com/");

    // calling clickOnLinks command to click on the links
    cy.clickOnLinks("RADIANT TEE").should("exist");
    // verifying after performing click action

    cy.get("span[class='base']").should("have.text", "Radiant Tee");
  });
});

I'm using the latest version of cypress - 12.7.0

I have tried using this one as well but no luck - Cypress.Commands.overwriteQuery

What am I missing? Can anyone help?


Solution

  • The main problem is the this binding of originalFn not being set, can be fixed with originalFn.bind(this).

    I took the parameter naming and resolution from the source, and defaulted the options (aka userOptions) to {} in case they are not passed.

    There is a weird thing - the prevSubject is no longer present. That might have happened when contains changed from a command to a query, but haven't figured out how it get's the prevSubject(s) yet.

    In any case, this is passing with cy.get('a').contains('RADIANT TEE').

    I haven't tested other variations yet.

    Cypress.Commands.overwriteQuery(
      "contains",
      function (contains, filter, text, userOptions = {}) {
    
        // This is parameter resolution from Cypress v12.7.0 source
        if (Cypress._.isRegExp(text)) {
          // .contains(filter, text)
          // Do nothing
        } else if (Cypress._.isObject(text)) {
          // .contains(text, userOptions)
          userOptions = text
          text = filter
          filter = ''
        } else if (Cypress._.isUndefined(text)) {
          // .contains(text)
          text = filter
          filter = ''
        }
    
        userOptions.matchCase = false;
    
        let contains0 = contains.bind(this)    // this line fixes the error
    
        return contains0(filter, text, userOptions)
      }
    )