← Back to Docs
Recipe

Cypress Patterns

Reusable selectors, commands, and test architecture for Meridian's E2E suite.

data-cy Selectors

Every interactive element carries a data-cy attribute. Never couple tests to CSS classes or text content.

cy.get('[data-cy=license-key-input]').type('XXXX-YYYY-ZZZZ')
cy.get('[data-cy=activate-button]').click()
cy.get('[data-cy=activation-success-toast]')
  .should('be.visible')

Custom Commands

Wrap repeated flows in commands.ts. Login, license activation, and session seeding are one-liners in specs.

Cypress.Commands.add('login', (email, pw) => {
  cy.session([email, pw], () => {
    cy.visit('/login')
    cy.get('[data-cy=email-input]').type(email)
    cy.get('[data-cy=password-input]').type(pw)
    cy.get('[data-cy=submit-button]').click()
    cy.url().should('include', '/dashboard')
  })
})

Network Stubs

Intercept KeyAuth and Upstash calls so tests never hit live infrastructure. Fixtures live in cypress/fixtures/.

cy.intercept('POST', '**/api/1.2/activate', {
  statusCode: 200,
  fixture: 'activation-success.json'
}).as('activate')
cy.wait('@activate')

Base URL & Env

Set baseUrl in config and use CYPRESS_ env vars for secrets. Never hardcode credentials.

Full E2E pipeline runs on every PR via GitHub Actions. See CI/CD guide for workflow details.