diff --git a/cypress/e2e/default/learn/challenge-hot-keys.ts b/cypress/e2e/default/learn/challenge-hot-keys.ts deleted file mode 100644 index ea1bc032012..00000000000 --- a/cypress/e2e/default/learn/challenge-hot-keys.ts +++ /dev/null @@ -1,107 +0,0 @@ -import { selectors } from '../../../support/selectors'; - -const hotKeySelectors = { - instructions: '.challenge-instructions', - instructionsPanel: '.instructions-panel', - editorContainer: '.monaco-editor' -}; - -const links = { - classic1: - '/learn/responsive-web-design/basic-html-and-html5/say-hello-to-html-elements', - classic2: - '/learn/responsive-web-design/basic-html-and-html5/headline-with-the-h2-element', - frontEnd1: - '/learn/front-end-development-libraries/front-end-development-libraries-projects/build-a-random-quote-machine', - frontEnd2: - '/learn/front-end-development-libraries/front-end-development-libraries-projects/build-a-markdown-previewer', - backEnd1: - '/learn/back-end-development-and-apis/back-end-development-and-apis-projects/timestamp-microservice', - backEnd2: - 'learn/back-end-development-and-apis/back-end-development-and-apis-projects/request-header-parser-microservice', - video1: - '/learn/scientific-computing-with-python/python-for-everybody/introduction-why-program', - video2: - 'learn/scientific-computing-with-python/python-for-everybody/introduction-hardware-architecture' -}; - -// It's possible for the location to change before the new page has loaded, so -// we wait for these titles to be present: -const titles = { - classic2: 'Headline with the h2 Element', - frontEnd2: 'Build a Markdown Previewer', - backEnd2: 'Request Header Parser Microservice', - video2: 'Introduction: Hardware Architecture' -}; - -describe('The hotkeys should work correctly', () => { - beforeEach(() => { - cy.login(); - cy.visit('/settings'); - // enable shortcuts - cy.get('form[data-testid="fcc-enable-shortcuts-setting"]').within(() => { - cy.contains('On').click(); - }); - }); - it('should be possible to navigate to the next challenge/projects and previous', () => { - cy.visit(links.classic1); - cy.focused().type('{esc}'); - cy.focused().type('n'); - cy.url().should('include', links.classic2); - cy.contains(titles.classic2); - cy.focused().type('p'); - cy.url().should('include', links.classic1); - cy.visit(links.frontEnd1); - cy.focused().type('{esc}').type('n'); - cy.url().should('include', links.frontEnd2); - cy.contains(titles.frontEnd2); - cy.focused().type('p'); - cy.url().should('include', links.frontEnd1); - }); - - it('should be possible to navigate to the next (and previous) video', () => { - cy.visit(links.video1); - cy.focused().type('{esc}').type('n'); - cy.url().should('include', links.video2); - cy.contains(titles.video2); - cy.focused().type('p'); - cy.url().should('include', links.video1); - }); - - it('should be possible to navigate to the next (and previous) backend project', () => { - cy.visit(links.backEnd1); - cy.focused().type('{esc}').type('n'); - cy.url().should('include', links.backEnd2); - cy.contains(titles.backEnd2); - cy.focused().type('p'); - cy.url().should('include', links.backEnd1); - }); - - it('should be possible to focus on the editor with pressing "e"', () => { - cy.visit(links.classic1); - cy.get(hotKeySelectors.editorContainer).click(); - cy.focused().as('editor').type('{esc}'); - cy.get(hotKeySelectors.instructions).click().type('e'); - cy.get('@editor').should('have.focus'); - }); - - it('should be possible to press ctrl enter to run the test', () => { - cy.visit(links.classic1); - cy.get(hotKeySelectors.instructions).click().type('{ctrl}{enter}'); - cy.get(selectors.dataCy.outputText).contains('// running tests'); - }); - - it('should be possible to go to navigation view by pressing escape', () => { - cy.visit(links.classic1); - cy.get(hotKeySelectors.editorContainer).click(); - cy.focused().as('editor').type('{esc}'); - cy.get('@editor').should('not.have.focus'); - }); - - it('it should be possible to focus on the instructions by pressing r', () => { - cy.visit(links.classic1); - cy.get(hotKeySelectors.editorContainer).type('{esc}'); - cy.get(selectors.dataCy.outputText).click().type('r'); - cy.get(hotKeySelectors.instructionsPanel).should('have.focus'); - }); -}); diff --git a/e2e/hotkeys.spec.ts b/e2e/hotkeys.spec.ts index adf8a0c5ce0..d3db5845fd1 100644 --- a/e2e/hotkeys.spec.ts +++ b/e2e/hotkeys.spec.ts @@ -7,6 +7,21 @@ import { getEditors } from './utils/editor'; const course = '/learn/javascript-algorithms-and-data-structures/basic-javascript/comment-your-javascript-code'; +const links = { + frontEnd1: + '/learn/front-end-development-libraries/front-end-development-libraries-projects/build-a-random-quote-machine', + frontEnd2: + '/learn/front-end-development-libraries/front-end-development-libraries-projects/build-a-markdown-previewer', + backEnd1: + '/learn/back-end-development-and-apis/back-end-development-and-apis-projects/timestamp-microservice', + backEnd2: + 'learn/back-end-development-and-apis/back-end-development-and-apis-projects/request-header-parser-microservice', + video1: + '/learn/python-for-everybody/python-for-everybody/introduction-why-program', + video2: + '/learn/python-for-everybody/python-for-everybody/introduction-hardware-architecture' +}; + test.use({ storageState: 'playwright/.auth/certified-user.json' }); test.beforeAll(async ({ request }) => { @@ -20,6 +35,16 @@ test.beforeAll(async ({ request }) => { }); }); +test.beforeEach(async ({ page }) => { + await page.goto('/settings'); + const keyboardShortcutGroup = page.getByRole('group', { + name: translations.settings.labels['keyboard-shortcuts'] + }); + await keyboardShortcutGroup + .getByRole('button', { name: translations.buttons.on, exact: true }) + .click(); +}); + test.afterEach( async ({ request }) => await authedRequest({ @@ -32,15 +57,7 @@ test.afterEach( }) ); -test('User can interact with the app using the keyboard', async ({ page }) => { - // Enable keyboard shortcuts - await page.goto('/settings'); - const keyboardShortcutGroup = page.getByRole('group', { - name: translations.settings.labels['keyboard-shortcuts'] - }); - await keyboardShortcutGroup - .getByRole('button', { name: translations.buttons.on, exact: true }) - .click(); +test('User can use shortcuts in and around the editor', async ({ page }) => { // TODO: getByRole('alert', name: // translations.flash['keyboard-shortcut-updated']) did not find the alert. // Should it a) be an alert and b) have a name? @@ -73,8 +90,52 @@ test('User can interact with the app using the keyboard', async ({ page }) => { await page.keyboard.press('e'); await expect(getEditors(page)).toBeFocused(); - await page.keyboard.press('Control+Enter'); - await expect(page.getByText('running test')).toBeVisible(); - - // Show shortcuts (shift+/) is covered by the shortcuts-modal tests + await getEditors(page).press('Escape'); + await page.keyboard.press('r'); + await expect(page.locator('.instructions-panel')).toBeFocused(); +}); + +test('User can use shortcuts to navigate between frontend projects', async ({ + page +}) => { + await page.goto(links.frontEnd1); + await expect(page.locator('#editor-layout')).toBeFocused(); + await page.keyboard.press('Escape'); + await page.keyboard.press('n'); + + await page.waitForURL(links.frontEnd2); + await expect(page.locator('#editor-layout')).toBeFocused(); + await page.keyboard.press('p'); + await page.keyboard.press('Escape'); + await page.waitForURL(links.frontEnd1); +}); + +test('User can use shortcuts to navigate between backend projects', async ({ + page +}) => { + await page.goto(links.backEnd1); + await expect(page.locator('#editor-layout')).toBeFocused(); + await page.keyboard.press('Escape'); + await page.keyboard.press('n'); + + await page.waitForURL(links.backEnd2); + await expect(page.locator('#editor-layout')).toBeFocused(); + await page.keyboard.press('p'); + await page.keyboard.press('Escape'); + await page.waitForURL(links.backEnd1); +}); + +test('User can use shortcuts to navigate between video-based challenges', async ({ + page +}) => { + await page.goto(links.video1); + await expect(page.locator('#editor-layout')).toBeFocused(); + await page.keyboard.press('Escape'); + await page.keyboard.press('n'); + + await page.waitForURL(links.video2); + await expect(page.locator('#editor-layout')).toBeFocused(); + await page.keyboard.press('p'); + await page.keyboard.press('Escape'); + await page.waitForURL(links.video1); });