From 2072166bdd9265aaaa27c4ee777ec0350cc8aeaa Mon Sep 17 00:00:00 2001 From: Yisroel Baum Date: Mon, 3 Aug 2026 20:28:51 +0300 Subject: [PATCH] test sets dashboard --- .../website/cypress/e2e/sets-dashboard.cy.ts | 120 ++++++++++++++++++ 1 file changed, 120 insertions(+) create mode 100644 frontend/website/cypress/e2e/sets-dashboard.cy.ts diff --git a/frontend/website/cypress/e2e/sets-dashboard.cy.ts b/frontend/website/cypress/e2e/sets-dashboard.cy.ts new file mode 100644 index 0000000..7e3bbca --- /dev/null +++ b/frontend/website/cypress/e2e/sets-dashboard.cy.ts @@ -0,0 +1,120 @@ +const authenticatedUser = { + id: 7, + email: 'user@example.com', +} + +function interceptAuthenticatedUser(): void { + cy.intercept('GET', '**/api/me', { + statusCode: 200, + body: { user: authenticatedUser }, + }).as('me') +} + +describe('sets dashboard', () => { + beforeEach(() => { + interceptAuthenticatedUser() + }) + + it('shows every available set by name', () => { + cy.intercept('GET', '**/api/sets', (request) => { + expect(request.headers.accept).to.equal('application/json') + request.reply({ + statusCode: 200, + body: { + sets: [ + { id: 41, name: 'Bible' }, + { id: 58, name: 'Course' }, + { id: 92, name: 'Fitness Program' }, + ], + }, + }) + }).as('sets') + + cy.visit('/dashboard') + cy.wait('@me') + cy.wait('@sets') + + cy.get('h1').should('have.text', 'Available sets') + cy.get('ul[aria-label="Available sets"] h2').then(($headings) => { + expect([...$headings].map((heading) => heading.textContent)).to.deep.equal([ + 'Bible', + 'Course', + 'Fitness Program', + ]) + }) + cy.get('ul[aria-label="Available sets"]') + .should('not.contain.text', '41') + .and('not.contain.text', '58') + .and('not.contain.text', '92') + .find('a, button') + .should('not.exist') + }) + + it('shows loading and empty catalog states', () => { + cy.intercept('GET', '**/api/sets', { + delay: 500, + statusCode: 200, + body: { sets: [] }, + }).as('sets') + + cy.visit('/dashboard') + cy.wait('@me') + cy.get('[role="status"]').should('have.text', 'Loading sets...') + cy.wait('@sets') + + cy.get('[role="status"]').should( + 'have.text', + 'No sets are available yet.', + ) + }) + + it('shows malformed catalog responses as errors', () => { + cy.intercept('GET', '**/api/sets', { + statusCode: 200, + body: { sets: [{ id: 41, name: 12 }] }, + }).as('sets') + + cy.visit('/dashboard') + cy.wait('@me') + cy.wait('@sets') + + cy.get('[role="alert"]').should( + 'contain.text', + "We couldn't load the available sets.", + ) + }) + + it('retries after a catalog request fails', () => { + let requestCount = 0 + cy.intercept('GET', '**/api/sets', (request) => { + requestCount += 1 + request.alias = `sets${requestCount}` + + if (requestCount === 1) { + request.reply({ statusCode: 500 }) + return + } + + request.reply({ + statusCode: 200, + body: { sets: [{ id: 41, name: 'Bible' }] }, + }) + }) + + cy.visit('/dashboard') + cy.wait('@me') + cy.wait('@sets1') + + cy.get('[role="alert"]').should( + 'contain.text', + "We couldn't load the available sets.", + ) + cy.contains('button', 'Try again').click() + cy.wait('@sets2') + + cy.get('ul[aria-label="Available sets"] h2').should( + 'have.text', + 'Bible', + ) + }) +})