I want to create a custom Cypress find
command like so to utilize a data-test
attribute.
cypress/support/index.ts
declare global {
namespace Cypress {
interface Chainable {
/**
* Custom command to get a DOM element by data-test attribute.
* @example cy.getByTestId('element')
*/
getByTestId(selector: string): Chainable<JQuery<HTMLElement>>;
/**
* Custom command to find a DOM element by data-test attribute.
* @example cy.findByTestId('element')
*/
findByTestId(selector: string): Chainable<JQuery<HTMLElement>>;
}
}
}
cypress/support/commands.ts
Cypress.Commands.add('getByTestId', (selector, ...args) => {
return cy.get(`[data-test=${selector}]`, ...args);
});
Cypress.Commands.add(
'findByTestId',
{ prevSubject: 'element' },
(subject, selector) => {
return subject.find(`[data-test=${selector}]`);
}
);
Here subject
is of type JQuery<HTMLElement>
and not Cypress.Chainable<JQuery<HTMLElement>>
, so subject.find
is not chainable with others methods.
I get the following errors from Typescript.
No overload matches this call.
Overload 1 of 4, '(name: "findByTestId", options: CommandOptions & { prevSubject: false; }, fn: CommandFn<"findByTestId">): void', gave the following error.
Overload 2 of 4, '(name: "findByTestId", options: CommandOptions & { prevSubject: true | keyof PrevSubjectMap<unknown> | ["optional"]; }, fn: CommandFnWithSubject<"findByTestId", unknown>): void', gave the following error.
Overload 3 of 4, '(name: "findByTestId", options: CommandOptions & { prevSubject: "element"[]; }, fn: CommandFnWithSubject<"findByTestId", JQuery<HTMLElement>>): void', gave the following error.ts(2769)
cypress.d.ts(22, 5): The expected type comes from property 'prevSubject' which is declared here on type 'CommandOptions & { prevSubject: false; }'
Desired usage
cy.getByTestId('some-element')
.findByTestId('some-test-id')
.should('have.text', 'Text');
How could I fix this?
CodePudding user response:
I may be off the mark, but subject.find(...)
is using jQuery find.
Perhaps you want cy.wrap(subject).find(...)
which should yield the Cypress.Chainable wrapper.
CodePudding user response:
Had to add a cy.wrap
command around the JQuery element like so.
Cypress.Commands.add(
'findByTestId',
{ prevSubject: 'element' },
(subject, selector) => {
return cy.wrap(subject).find(`[data-test=${selector}]`);
}
)