import '@testing-library/cypress/add-commands'; import 'cypress-real-events'; // https://docs.cypress.io/api/commands/hover Cypress.Commands.add('hover', (selector: string) => { if (!selector) { throw new Error('You must provide a valid selector to hover over.'); } return cy.get(selector).then(($el) => { if ($el.length === 0) { throw new Error(`No elements found for selector: ${selector}`); } if (Cypress.browser.name !== 'firefox') { return cy.wrap($el).realHover(); } return cy.wrap($el).trigger('mouseover', { force: true }); }); }); const calcDiffPct = (target: number, actual: number) => { try { const diff = (200 * Math.abs(target - actual)) / (target + actual); const side = actual > target ? 'ABOVE' : 'BELOW'; return { diff: Math.round(diff * 100) / 100, side }; } catch { return { diff: 0, side: '' }; } }; Cypress.Commands.add( 'verifyPerformance', ({ testName, execute, threshold = 0.5, expectedRenderDurationInMs = 100 }) => { let startTime = 0; const allowableDurationInMs = expectedRenderDurationInMs * (1 + threshold); cy.wrap(null) .then(() => { startTime = performance.now(); cy.log(`[${Math.round(startTime)}ms] Starting validation`); }) .then(() => execute()) .then(() => { const endTime = performance.now(); const durationInMs = Math.round(endTime - startTime); const { diff, side } = calcDiffPct(expectedRenderDurationInMs, durationInMs); const logMsg = `Test "${testName}" took ${durationInMs}ms to render (${diff}% ${side} ${expectedRenderDurationInMs}ms expectation)`; cy.log(`[${Math.round(endTime)}ms] ${logMsg}`); assert( allowableDurationInMs >= durationInMs, `${logMsg}, but should take less than ${allowableDurationInMs}ms` ); }); } );